view data tests
This commit is contained in:
205
apps/website/lib/builders/view-data/LoginViewDataBuilder.test.ts
Normal file
205
apps/website/lib/builders/view-data/LoginViewDataBuilder.test.ts
Normal file
@@ -0,0 +1,205 @@
|
||||
import { describe, it, expect } from 'vitest';
|
||||
import { LoginViewDataBuilder } from './LoginViewDataBuilder';
|
||||
import type { LoginPageDTO } from '@/lib/services/auth/types/LoginPageDTO';
|
||||
|
||||
describe('LoginViewDataBuilder', () => {
|
||||
describe('happy paths', () => {
|
||||
it('should transform LoginPageDTO to LoginViewData correctly', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result).toEqual({
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
showPassword: false,
|
||||
showErrorDetails: false,
|
||||
formState: {
|
||||
fields: {
|
||||
email: { value: '', error: undefined, touched: false, validating: false },
|
||||
password: { value: '', error: undefined, touched: false, validating: false },
|
||||
rememberMe: { value: false, error: undefined, touched: false, validating: false },
|
||||
},
|
||||
isValid: true,
|
||||
isSubmitting: false,
|
||||
submitError: undefined,
|
||||
submitCount: 0,
|
||||
},
|
||||
isSubmitting: false,
|
||||
submitError: undefined,
|
||||
});
|
||||
});
|
||||
|
||||
it('should handle insufficient permissions flag correctly', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/admin',
|
||||
hasInsufficientPermissions: true,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.hasInsufficientPermissions).toBe(true);
|
||||
expect(result.returnTo).toBe('/admin');
|
||||
});
|
||||
|
||||
it('should handle empty returnTo path', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.returnTo).toBe('');
|
||||
expect(result.hasInsufficientPermissions).toBe(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe('data transformation', () => {
|
||||
it('should preserve all DTO fields in the output', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.returnTo).toBe(loginPageDTO.returnTo);
|
||||
expect(result.hasInsufficientPermissions).toBe(loginPageDTO.hasInsufficientPermissions);
|
||||
});
|
||||
|
||||
it('should not modify the input DTO', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const originalDTO = { ...loginPageDTO };
|
||||
LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(loginPageDTO).toEqual(originalDTO);
|
||||
});
|
||||
|
||||
it('should initialize form fields with default values', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.formState.fields.email.value).toBe('');
|
||||
expect(result.formState.fields.email.error).toBeUndefined();
|
||||
expect(result.formState.fields.email.touched).toBe(false);
|
||||
expect(result.formState.fields.email.validating).toBe(false);
|
||||
|
||||
expect(result.formState.fields.password.value).toBe('');
|
||||
expect(result.formState.fields.password.error).toBeUndefined();
|
||||
expect(result.formState.fields.password.touched).toBe(false);
|
||||
expect(result.formState.fields.password.validating).toBe(false);
|
||||
|
||||
expect(result.formState.fields.rememberMe.value).toBe(false);
|
||||
expect(result.formState.fields.rememberMe.error).toBeUndefined();
|
||||
expect(result.formState.fields.rememberMe.touched).toBe(false);
|
||||
expect(result.formState.fields.rememberMe.validating).toBe(false);
|
||||
});
|
||||
|
||||
it('should initialize form state with default values', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.formState.isValid).toBe(true);
|
||||
expect(result.formState.isSubmitting).toBe(false);
|
||||
expect(result.formState.submitError).toBeUndefined();
|
||||
expect(result.formState.submitCount).toBe(0);
|
||||
});
|
||||
|
||||
it('should initialize UI state flags correctly', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.showPassword).toBe(false);
|
||||
expect(result.showErrorDetails).toBe(false);
|
||||
expect(result.isSubmitting).toBe(false);
|
||||
expect(result.submitError).toBeUndefined();
|
||||
});
|
||||
});
|
||||
|
||||
describe('edge cases', () => {
|
||||
it('should handle special characters in returnTo path', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard?param=value&other=test',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.returnTo).toBe('/dashboard?param=value&other=test');
|
||||
});
|
||||
|
||||
it('should handle returnTo with hash fragment', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard#section',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.returnTo).toBe('/dashboard#section');
|
||||
});
|
||||
|
||||
it('should handle returnTo with encoded characters', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard?redirect=%2Fadmin',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.returnTo).toBe('/dashboard?redirect=%2Fadmin');
|
||||
});
|
||||
});
|
||||
|
||||
describe('form state structure', () => {
|
||||
it('should have all required form fields', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
expect(result.formState.fields).toHaveProperty('email');
|
||||
expect(result.formState.fields).toHaveProperty('password');
|
||||
expect(result.formState.fields).toHaveProperty('rememberMe');
|
||||
});
|
||||
|
||||
it('should have consistent field state structure', () => {
|
||||
const loginPageDTO: LoginPageDTO = {
|
||||
returnTo: '/dashboard',
|
||||
hasInsufficientPermissions: false,
|
||||
};
|
||||
|
||||
const result = LoginViewDataBuilder.build(loginPageDTO);
|
||||
|
||||
const fields = result.formState.fields;
|
||||
Object.values(fields).forEach((field) => {
|
||||
expect(field).toHaveProperty('value');
|
||||
expect(field).toHaveProperty('error');
|
||||
expect(field).toHaveProperty('touched');
|
||||
expect(field).toHaveProperty('validating');
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user