JSON zu TypeScript

TypeScript-Interfaces aus einem JSON-Beispiel erzeugen.

Über dieses Tool

Füge eine JSON-Antwort ein und erhalte TypeScript-Interfaces dafür. Verschachtelte Objekte werden zu eigenen benannten Interfaces, Arrays von Objekten werden zusammengeführt, sodass optionale Felder mit ? markiert werden, und gemischte Werte werden zu Union-Typen.

So verwendest du es

  1. Füge eine Beispiel-JSON-Antwort deiner API ein.
  2. Lege den Namen des Wurzeltyps fest, zum Beispiel User oder OrderResponse.
  3. Wähle Interface- oder Type-Deklarationen und ob sie exportiert werden sollen.
  4. Kopiere das erzeugte TypeScript in dein Projekt und passe alles an, was das Beispiel nicht zeigen konnte.

Fragen

Wie werden optionale Felder erkannt?
Enthält ein Array mehrere Objekte, wird ein Feld, das in manchen fehlt, mit ? als optional markiert. Ein einzelnes Objekt kann keine optionalen Felder verraten, also gib wenn möglich ein Beispiel mit mehreren Einträgen an.
Warum hat ein Feld den Typ null?
Weil der Wert im Beispiel null war, ist sein echter Typ unbekannt. Ersetze ihn durch etwas wie string | null, sobald du weißt, was die API zurückgibt.
Sollte ich interface oder type verwenden?
Beide eignen sich, um JSON zu beschreiben. Interfaces lassen sich erweitern und zusammenführen und liefern etwas klarere Fehlermeldungen; für Unions brauchst du Type-Aliase. Nimm, was deine Codebasis schon verwendet.
Validiert es Daten zur Laufzeit?
Nein. TypeScript-Typen verschwinden beim Kompilieren. Um Daten zur Laufzeit zu prüfen, nutze zusätzlich zu diesen Typen eine Schema-Bibliothek wie Zod.
Was passiert, wenn die JSON-Wurzel ein Array ist?
Die Wurzel wird zu einem Typalias für ein Array. Mit dem Wurzelnamen User und einem Beispiel wie [{"id": 1}] bekommst du type User = UserItem[] plus ein Interface UserItem für die Elemente. Benenne die Wurzel im Plural, etwa Users, dann bekommst du stattdessen type Users = User[].
Kann ich ein JavaScript-Objekt statt strengem JSON einfügen?
Ja. Einfache Anführungszeichen, Schlüssel ohne Anführungszeichen, abschließende Kommas sowie Pythons True, False und None werden vor dem Generieren der Typen in JSON umgewandelt, Ausgaben von console.log in Node oder aus einer Python-Shell funktionieren also. Werte, die JSON nicht ausdrücken kann, etwa Funktionen oder Klasseninstanzen, führen weiterhin zu einem Fehler.
Warum heißt der Elementtyp eines Arrays DataItem?
Elementtypen werden benannt, indem der Schlüssel des Arrays in den Singular gesetzt wird: users ergibt User und entries ergibt Entry. Hat ein Schlüssel keine Pluralendung, wie data oder children, wird stattdessen Item angehängt, was DataItem und ChildrenItem ergibt. Benenne sie nach dem Einfügen in deinem Editor um, wenn dir andere Namen lieber sind.

TypeScript-Interfaces aus JSON generieren: so geht’s

Füge eine echte API-Antwort ein, und jedes JSON-Objekt wird zu einem benannten TypeScript-Interface. Feldnamen bleiben erhalten, Werte werden auf string, number und boolean abgebildet, und ein verschachteltes Objekt bekommt eine eigene Deklaration, benannt nach seinem Schlüssel – ein Feld address erzeugt also ein Interface Address. Arrays von Objekten werden im Singular benannt: orders ergibt Order[] und categories ergibt Category[]. Setze den Namen des Wurzeltyps auf den Typ, den dein Code verwenden wird, etwa User.

Das erzeugte TypeScript kompiliert so, wie es ist, du kannst es also in eine types.ts einfügen oder herunterladen. Schlüssel, die keine gültigen Bezeichner sind, etwa "first-name" oder "2fa", werden in Anführungszeichen geschrieben. Würden zwei verschachtelte Objekte denselben Namen bekommen, erhält das zweite eine Nummer, etwa Address2. Ein leeres Array wird zu unknown[] und ein leeres Objekt zu Record<string, unknown>, weil das Beispiel nichts über ihren Inhalt verrät.

Wie Union-Typen aus JSON abgeleitet werden

Enthält dasselbe Feld unterschiedliche Arten von Werten, wird sein Typ zu einer Union. Ein Array wie [1, "two", null] wird als (string | number | null)[] typisiert, und ein Feld, das in einem Eintrag ein String und in einem anderen eine Zahl ist, wird zu string | number. Objekte im selben Array werden zu einem Interface zusammengeführt statt zu einer Union verschiedener Formen, und Felder, die nur in einigen davon vorkommen, werden als optional markiert.

Das Zusammenführen passt gut zu Listen von Datensätzen, verdeckt aber Tagged Unions. Mischt ein Array events {"type": "click", "x": 3} und {"type": "key", "code": "Enter"}, bekommst du ein einziges Interface Event mit type als string und sowohl x als auch code optional. Schreib es von Hand in eine Discriminated Union aus zwei Interfaces um, eines mit type: "click" und eines mit type: "key", damit TypeScript anhand des Felds type eingrenzen kann.

JSON zu TypeScript: aus einem Beispiel oder aus einem Schema?

Ein JSON-Beispiel zeigt eine Antwort, nicht den Vertrag. Strings, die eigentlich Datumswerte sind, Enums wie "active" | "banned", numerische IDs, die über 2^53 wachsen können, und Felder, die nur manchmal vorhanden sind, lassen sich an einem einzelnen Beispiel nicht erkennen. Betrachte die erzeugten Interfaces als ersten Entwurf: Füge eine Antwort mit mehreren Array-Einträgen ein und verschärfe die Typen dort, wo du mehr weißt, etwa indem du status: string durch eine Union der erlaubten Werte ersetzt.

Veröffentlicht eine API ein OpenAPI-Dokument oder ein JSON Schema, generiere die Typen lieber daraus, weil es jedes Feld beschreibt, das der Server zurückgeben kann. Typen aus JSON zu erzeugen ist der schnelle Weg für Drittanbieter-APIs ohne Spezifikation, Webhook-Payloads und alte interne Endpunkte. Für Daten, die du nicht kontrollierst, ergänze eine Laufzeitprüfung mit derselben Form, etwa ein Zod-Schema, damit eine geänderte Antwort lautstark scheitert, statt unbemerkt durchzurutschen.

Funktioniert etwas nicht, oder sieht ein Ergebnis falsch aus? Ein Problem mit diesem Tool melden