JSON to TypeScript Interface Converter — Zero-Upload
Turn any JSON payload into strict-mode TypeScript: every nested object becomes a named interface, [1, "a"] becomes (number | string)[], missing keys in arrays of objects become optional properties, and a KeyMap const records every renamed key. The generator runs in a Web Worker in your browser — your data never leaves the tab.
Zero upload, ever
Inference and code generation run in a Web Worker inside your browser — payloads with PII never touch a server.
Live 300 ms conversion
Output updates as you type, with mixed-array unions, merged objects, and ISO-8601 dates inferred automatically.
Strict-mode clean
Output compiles under strict tsc with no any — unions, unknown, and null handled explicitly.
Paste JSON to generate a schema
JSON input
Generated schema
Paste JSON on the left — Zod, TypeScript, Pydantic, and Go schemas appear here instantly, generated entirely in your browser.
Technical documentation
From JSON values to strict TypeScript types
Every nested object in your payload becomes its own exported interface, named by its position in the tree — a friends array inside UserProfile yields UserProfileFriendsItem — so deeply nested documents stay readable instead of collapsing into one giant inline literal. Arrays fold their elements together: [1, "a"] becomes (number | string)[], and arrays of arrays merge element-wise. Identical shapes are deduplicated into a single interface and referenced by name.
Optionality is inferred from evidence, not guesses. When an array of objects contains records with different keys, any key missing from at least one element is emitted with a ? — the exact contract a paginated API actually serves. Empty arrays infer unknown[] because an empty sample proves nothing, and null stays null rather than silently becoming undefined.
camelCase types with a KeyMap for the wire format
snake_case and kebab-case keys are converted to camelCase in the interfaces, so your TypeScript follows convention instead of the API's spelling quirks. To preserve the mapping to the original keys, the generator emits an adjacent KeyMap const: export const UserProfileKeyMap = { userName: "user_name" } as const. Use it at your hydration boundary to map parsed JSON onto the typed shape with full type safety.
ISO-8601 strings stay string in the TypeScript output — which is what JSON.parse actually produces at runtime — while the Zod target of the same tool coerces them to Date. That keeps the interfaces honest about what the wire delivers, and lets you layer a parsing step on top when you want richer types.
Why offline conversion matters for JSON with user data
The payloads developers paste into interface generators are usually real: production API responses, CRM exports, analytics events. They carry names, email addresses, phone numbers, and internal IDs — personally identifiable information that privacy laws and most employer security policies prohibit sharing with third parties. A server-side converter means that data leaves your machine, and you are trusting an unknown operator's retention policy and log hygiene with a potential data breach.
This page is a static export: the type engine is pure TypeScript running in a Web Worker inside your browser, with a watchdog that aborts runaway conversions after three seconds. No fetch calls, no telemetry on your payload, no storage. That makes it safe for production data on corporate machines, and it works fully offline once the page is cached — convenient for restricted networks and air-gapped environments.
Using the generated interfaces
The output is plain declaration-only TypeScript that compiles under strict mode with noUncheckedIndexedAccess — paste it next to your API client and annotate fetch responses with it. Interfaces are emitted children-first, so the file reads bottom-up from leaf shapes to the root type, and a root that is not an object gets an export type alias instead (export type Root = (number | string)[]).
For runtime validation, pair the interfaces with the Zod output from the same tool: the schema validates the raw JSON keys, transforms them to camelCase, and its inferred type matches these interfaces. Together they give you a compile-time contract and a runtime guard from a single paste.
Frequently asked questions
Is my JSON sent to a server during conversion?
No. The interface generator runs entirely in your browser inside a Web Worker — there is no backend API. Payloads with emails, names, or other PII are never transmitted, stored, or logged.
How does it handle arrays where objects have different keys?
Object schemas across an array are merged: keys present in every element become required, and keys missing from at least one element become optional with a ? modifier. That mirrors what real APIs return across pages and partial updates.
What do mixed arrays like [1, "a", null] become?
They become union types: (number | string | null)[]. The generator folds every element into a deduplicated union instead of collapsing to any, so your types stay strict.
Why is there a KeyMap const next to my interfaces?
JSON keys in snake_case or kebab-case are renamed to camelCase in the interfaces; the KeyMap records the original key for each renamed property so you can map wire-format data onto the typed shape at your hydration boundary.
Does it work with huge JSON files?
Yes — parsing runs off the main thread and a watchdog aborts anything over three seconds with a clean error, so a pathological paste cannot freeze the tab. Sensible payloads convert in single-digit milliseconds.
Can I use the interfaces commercially?
Yes — the generated TypeScript is yours with no attribution required. It is plain declaration code that compiles with the standard tsc compiler and no dependencies.