| name | form-validation |
| description | Form and schema validation across libraries. Trigger: When validating forms, API input, schemas, or runtime data. |
| license | Apache 2.0 |
| metadata | {"version":"1.1","type":"domain"} |
Form Validation
Form/schema validation across Zod, Yup, React Hook Form, Formik. Context-aware.
When to Use
- Validating user input (forms, API requests)
- Runtime schema validation
- Parsing external data with type safety
- Ensuring data conforms to types
- Managing form state with validation
Don't use when:
- Compile-time typing (typescript skill)
- Simple validation (<3 fields)
Critical Patterns
✅ REQUIRED [CRITICAL]: Check Context First
ALWAYS check what the project uses before recommending a library:
✅ REQUIRED: Infer Types from Schemas
const schema = z.object({ name: z.string() });
type User = z.infer<typeof schema>;
const schema = yup.object({ name: yup.string().required() });
type User = yup.InferType<typeof schema>;
interface User { name: string }
const schema = z.object({ name: z.string() });
✅ REQUIRED: Safe Error Handling
const result = schema.safeParse(data);
if (result.success) {
use(result.data);
} else {
handle(result.error);
}
try {
const valid = await schema.validate(data);
} catch (error) {
if (error instanceof yup.ValidationError) {
handle(error);
}
}
const data = schema.parse(input);
✅ REQUIRED: Chain Validations
const email = z.string().email().min(5).max(100);
const email = yup.string().email().required().max(100);
const email = z.string();
Decision Tree
Project has validation library?
→ Yes: Check AGENTS.md or package.json
→ Zod installed? → See references/zod.md
→ Yup installed? → See references/yup.md
→ React Hook Form? → See references/react-hook-form.md
→ Formik? → See references/formik.md
→ No: Recommend modern default (React Hook Form + Zod for React, Zod for Node.js)
Schema validation only (no forms)?
→ Use Zod or Yup (see references for library-specific patterns)
Form management needed (React)?
→ React Hook Form (modern, performant) or Formik (legacy support)
→ See references/react-hook-form.md or references/formik.md
Async validation required?
→ All libraries support it:
- Zod: .parseAsync() or .refine() with async
- Yup: .validate() is async
- React Hook Form: resolver or custom async rules
- Formik: validate prop with async function
Complex nested structures?
→ Zod: z.object() nesting
→ Yup: yup.object() nesting
→ React Hook Form: dot notation (user.address.street)
→ Formik: FieldArray or dot notation
Example
Context-aware validation setup:
import { useForm } from 'react-hook-form';
import { zodResolver } from '@hookform/resolvers/zod';
import { z } from 'zod';
const schema = z.object({
email: z.string().email('Invalid email').min(1, 'Required'),
age: z.number().int().min(18, 'Must be 18+'),
});
type FormData = z.infer<typeof schema>;
function MyForm() {
const { register, handleSubmit, formState: { errors } } = useForm<FormData>({
resolver: zodResolver(schema),
});
return (
<form onSubmit={handleSubmit(data => console.log(data))}>
<input {...register('email')} />
{errors.email && <span>{errors.email.message}</span>}
<input type="number" {...register('age', { valueAsNumber: true })} />
{errors.age && <span>{errors.age.message}</span>}
<button type="submit">Submit</button>
</form>
);
}
Edge Cases
Multiple libs: Use appropriate for context (Zod for API, Yup for legacy Formik).
No library: Recommend RHF + Zod (React) or Zod (Node.js).
Migration: One form/endpoint at a time. Don't mix within same form.
TS strict: All libs need strict: true in tsconfig.
Resources
See references/README.md for complete navigation.