How to generate a zod schema for react form validation
- Step 1Create a sample form submission JSON — Build a JSON object with your form's field names as keys and realistic sample values as values: { "email": "[email protected]", "age": 25, "acceptTerms": true, "address": { "city": "New York", "zip": "10001" } }.
- Step 2Generate the base Zod schema — Paste the submission JSON and convert. The output is a z.object({ ... }) schema with inferred types for each field.
- Step 3Add validation constraints — Enhance each field: email →’ z.string().email('Invalid email address'), age →’ z.number().min(18, 'Must be 18+').max(120), zip →’ z.string().regex(/^\d{5}$/, 'Invalid zip code'), acceptTerms →’ z.literal(true, { errorMap: () => ({ message: 'Must accept terms' }) }).
- Step 4Integrate with React Hook Form — const form = useForm<z.infer<typeof FormSchema>>({ resolver: zodResolver(FormSchema) }). Field-level errors from schema validation violations are now available as form.formState.errors.email, etc.
Frequently asked questions
How do I add cross-field validation — for example, confirm password must match password?+
Use .refine() or .superRefine() on the z.object(): schema.refine(data => data.password === data.confirmPassword, { message: 'Passwords must match', path: ['confirmPassword'] }). The path array specifies which field shows the error.
How do I handle optional form fields that should only be validated if filled in?+
Use .optional() for completely optional fields: z.string().optional(). For fields that are optional but must be valid if provided: z.string().email().optional(). For empty-string-allowed fields that are technically 'optional': z.string().min(0) or z.union([z.string().email(), z.literal('')]).
Is the form data transmitted to JAD Apps?+
No. Schema generation runs entirely in your browser. Form field data is never transmitted to JAD Apps servers.
Privacy first
Conversion runs locally in your browser. No file is uploaded — only metadata counters are saved for signed-in dashboard stats.