JSON to Zod schema
freeGenerate a runtime-validated Zod schema with z.infer type aliases.
import { z } from "zod";
export const AddressSchema = z.object({
street: z.string(),
city: z.string(),
country: z.string(),
postalCode: z.string(),
});
export type Address = z.infer<typeof AddressSchema>;
export const RootSchema = z.object({
id: z.string().uuid(),
name: z.string(),
email: z.string().email(),
age: z.number().int(),
bio: z.null(),
address: AddressSchema,
tags: z.array(z.string()),
createdAt: z.string().datetime({ offset: true }),
verified: z.boolean(),
});
export type Root = z.infer<typeof RootSchema>;
export const rootSchema = RootSchema;
Generate a Zod schema from any JSON sample, complete with `z.infer` type aliases so you get a runtime validator and the matching TypeScript type from one declaration. Built on the same schema IR as the JSON → TypeScript tool, so nested optionals, structural dedup, and format-aware string detection all carry over — UUID fields emit `.uuid()`, ISO timestamps emit `.datetime({ offset: true })`, emails emit `.email()`.
Common use cases
- Validating API responses at runtime. Drop in a representative payload, paste the schema into your fetcher, and wrap each response in `schema.parse()` for end-to-end type safety with runtime guarantees.
- tRPC / Hono / Next.js route handlers. Use the generated schema as the `input` / `output` for tRPC procedures or Hono validators. The `z.infer` aliases give you the matching TypeScript type for handlers and clients.
- Form data validation. Pair with `react-hook-form` + `@hookform/resolvers/zod` to get form validation that matches your backend schema exactly.
- Configuration file parsing. Load `config.json` with `schema.parse(JSON.parse(file))` to catch malformed config at startup with a precise error path instead of failing at first use.
Frequently asked
What Zod version is the output compatible with?
Zod v3+. The emitter avoids v4-only constructs and stays on the stable subset that hasn't moved in the last two majors.
Should I turn on `.strict()`?
Turn it on if you want extra (unknown) keys in the input to fail validation. Useful for closed-world configs and API contracts; leave off for forward-compatible APIs where new fields are expected.
Why is my date field a `z.string().datetime()` instead of `z.date()`?
JSON has no date type — values come through as strings. `z.string().datetime()` validates the ISO 8601 format. If you want a `Date` instance after parsing, chain `.transform((s) => new Date(s))`.
Can I disable the format refinements?
Yes — flip the 'Format refinements' switch off. The output becomes plain `z.string()` for every string field, useful when you don't want stricter validation than your data actually provides.
Why do I see both `UserSchema` and `userSchema`?
PascalCase schema constants follow the type names; the lower-case alias matches your chosen schema name. They reference the same value — keep whichever fits your codebase convention.
Does the URL save my options?
Yes — root name, strict mode, and refinements are all encoded as query parameters for shareable links.