toolgarden.xyz
中文
JSONTypeScriptinterfacetype generationAPI

How to Convert JSON to a TypeScript Interface

Hand-writing TypeScript types for an API response is slow and error-prone. Infer an interface from a real JSON sample and get usable types in seconds.

ToolGarden tools prioritize browser-local processing, so files and text do not need to be uploaded to a server.

Published July 27, 20266 min readBy ToolGarden

The most tedious part of wiring up a new endpoint is often hand-writing TypeScript types from the JSON response. With many fields it is easy to miss one, use the wrong type, or forget that a field is optional.

This step can be fully automated: give the tool a real JSON sample and it infers the type of every field and emits a matching TypeScript interface. Below is how it works, plus the edge cases that trip people up.

A minimal example

Suppose the endpoint returns this JSON:

{
  "id": 1001,
  "name": "ToolGarden",
  "isActive": true,
  "tags": ["json", "pdf"],
  "owner": {
    "email": "hi@example.com",
    "verified": false
  },
  "lastLogin": null
}

From the values, matching TypeScript types can be inferred. Nested objects become their own interfaces and arrays infer their element type:

interface Owner {
  email: string;
  verified: boolean;
}

interface Root {
  id: number;
  name: string;
  isActive: boolean;
  tags: string[];
  owner: Owner;
  lastLogin: null;
}

How are the types inferred?

  • string → string, number → number, boolean → boolean.
  • object → its own interface, named after the field (e.g. owner → Owner).
  • array → element type with [], e.g. an array of strings is string[].
  • null → null (a lone null value cannot reveal the real type; add it manually).
  • A field that has different types across objects → a union type (e.g. string | number).

Edge cases to watch for

1. Optional fields

A single JSON sample cannot tell the tool which fields might be missing. If a field is sometimes returned and sometimes not, mark it optional by hand (add ? after the name). Using samples that cover more cases, or merging several samples, reduces these misses.

2. null vs the real type

A field like lastLogin: null can only be inferred as null. In reality it is usually string | null or number | null. Generate from a sample where the field has a value, or switch it to a union type by hand, to match the real API.

3. Empty and mixed arrays

An empty array [] gives no element type and usually degrades to unknown[] or any[]. A mixed array such as [1, "a"] becomes (number | string)[]. The richer the sample elements, the more accurate the result.

Practical tips when generating types

SituationRecommended approach
Field may be missingAdd ? to mark it optional, or merge multiple samples
Field value is nullChange to T | null (e.g. string | null)
Array is emptySpecify the element type by hand to avoid any[]
Enum-like stringsUse a literal union where useful (e.g. "draft" | "published")
Sample is invalidValidate with a JSON formatter first, then generate

Generated locally, your API data is never uploaded

API responses often carry tokens, emails and user IDs, so pasting them into a tool that uploads your data is risky. ToolGarden's JSON → TypeScript tool infers everything locally in your browser, so the sample never leaves your device — safe to run on a real response.

Summary

Generating a TypeScript interface from JSON saves a lot of hand-typing and cuts down on mistakes. What still needs your attention is what a sample cannot cover: optional fields, the real type behind null, and empty arrays. Fill those in and the generated types are ready to trust in your project.

Frequently asked questions

Q.Does JSON-to-TypeScript upload my API data?

No. ToolGarden's JSON → TypeScript tool infers types locally in your browser, so the JSON sample you paste is never uploaded to any server or logged. Because API responses often include tokens, emails and user IDs, generating types locally keeps those sensitive fields off external services. The resulting interface is shown right on the page for you to copy.

Q.Why is a generated field typed as any or unknown?

This usually happens in two cases: the value is an empty array [], so no element type can be inferred, or the value is null, so it is impossible to tell whether it should be string, number or something else. The fix is to generate from a sample where the field has a real value, or to change it by hand afterwards to an explicit type such as string[] or string | null.

Q.How do I handle fields that are only sometimes returned?

A single JSON sample cannot express that a field might be absent, so by default every generated field is required. If you know some fields are optional, add ? after the field name after generating to mark them optional. A more robust approach is to collect several samples covering different cases, or account for the typical missing fields before generating, which reduces later manual edits.