veza/apps/web/src/lib/passwordValidator.test.ts
2025-12-12 21:34:34 -05:00

126 lines
4.6 KiB
TypeScript

import { describe, it, expect } from 'vitest';
import {
validatePasswordStrength,
calculatePasswordStrength,
} from './passwordValidator';
describe('passwordValidator', () => {
describe('validatePasswordStrength', () => {
it('should validate a password with all requirements', () => {
const result = validatePasswordStrength('SecurePass123!');
expect(result.isValid).toBe(true);
expect(result.errors).toHaveLength(0);
expect(result.strength.length).toBe(true);
expect(result.strength.upper).toBe(true);
expect(result.strength.lower).toBe(true);
expect(result.strength.number).toBe(true);
expect(result.strength.special).toBe(true);
});
it('should reject password shorter than 8 characters', () => {
const result = validatePasswordStrength('Test123');
expect(result.isValid).toBe(false);
expect(result.errors).toContain('password must be at least 8 characters');
expect(result.strength.length).toBe(false);
});
it('should reject password longer than 128 characters', () => {
const longPassword = `${'A'.repeat(129)}a1!`;
const result = validatePasswordStrength(longPassword);
expect(result.isValid).toBe(false);
expect(result.errors).toContain(
'password must be less than 128 characters',
);
});
it('should reject password without uppercase letter', () => {
const result = validatePasswordStrength('test123!@#');
expect(result.isValid).toBe(false);
expect(result.errors).toContain(
'password must contain at least one uppercase letter',
);
expect(result.strength.upper).toBe(false);
});
it('should reject password without lowercase letter', () => {
const result = validatePasswordStrength('TEST123!@#');
expect(result.isValid).toBe(false);
expect(result.errors).toContain(
'password must contain at least one lowercase letter',
);
expect(result.strength.lower).toBe(false);
});
it('should reject password without number', () => {
const result = validatePasswordStrength('TestPass!@#');
expect(result.isValid).toBe(false);
expect(result.errors).toContain(
'password must contain at least one number',
);
expect(result.strength.number).toBe(false);
});
it('should reject password without special character', () => {
const result = validatePasswordStrength('TestPass123');
expect(result.isValid).toBe(false);
expect(result.errors).toContain(
'password must contain at least one special character',
);
expect(result.strength.special).toBe(false);
});
it('should accept password exactly 8 characters', () => {
const result = validatePasswordStrength('Test123!');
expect(result.isValid).toBe(true);
expect(result.errors).toHaveLength(0);
});
it('should return multiple errors for password missing multiple requirements', () => {
const result = validatePasswordStrength('test');
expect(result.isValid).toBe(false);
expect(result.errors.length).toBeGreaterThan(1);
});
it('should validate password with various special characters', () => {
const specialChars = ['!', '@', '#', '$', '%', '^', '&', '*', '(', ')'];
specialChars.forEach((char) => {
const password = `Test123${char}`;
const result = validatePasswordStrength(password);
expect(result.isValid).toBe(true);
expect(result.strength.special).toBe(true);
});
});
});
describe('calculatePasswordStrength', () => {
it('should return score 5 for strong password', () => {
const score = calculatePasswordStrength('SecurePass123!');
expect(score).toBe(5);
});
it('should return score 0 for empty password', () => {
const score = calculatePasswordStrength('');
expect(score).toBe(0);
});
it('should return score 2 for password with length and lowercase', () => {
const score = calculatePasswordStrength('testpass');
expect(score).toBe(2); // length + lowercase
});
it('should return score 2 for password with length and uppercase', () => {
const score = calculatePasswordStrength('TESTPASS');
expect(score).toBe(2);
});
it('should return score 3 for password with length, uppercase, and lowercase', () => {
const score = calculatePasswordStrength('TestPass');
expect(score).toBe(3);
});
it('should return score 4 for password with length, uppercase, lowercase, and number', () => {
const score = calculatePasswordStrength('TestPass123');
expect(score).toBe(4);
});
});
});