diff --git a/src/utils/validators.ts b/src/utils/validators.ts new file mode 100644 index 0000000..971896f --- /dev/null +++ b/src/utils/validators.ts @@ -0,0 +1,48 @@ +import { FormField } from '../types'; + +export interface ValidationError { + fieldId: string; + message: string; +} + +/** + * Validate form values against field definitions. + * Returns an empty array if everything is valid. + */ +export function validateForm( + fields: FormField[], + values: Record, +): ValidationError[] { + const errors: ValidationError[] = []; + + for (const field of fields) { + const value = values[field.id]; + + if (field.required) { + if (value === undefined || value === null || value === '') { + errors.push({ fieldId: field.id, message: `${field.label} is required.` }); + continue; + } + if (Array.isArray(value) && value.length === 0) { + errors.push({ fieldId: field.id, message: `${field.label} is required.` }); + continue; + } + } + + if (value !== undefined && value !== null && value !== '') { + if (field.type === 'number' && typeof value === 'string') { + if (isNaN(Number(value))) { + errors.push({ fieldId: field.id, message: `${field.label} must be a number.` }); + } + } + if (field.type === 'rating') { + const n = Number(value); + if (isNaN(n) || n < 1 || n > 5) { + errors.push({ fieldId: field.id, message: `${field.label} must be between 1 and 5.` }); + } + } + } + } + + return errors; +}