JSON en TypeScript

Générez des interfaces TypeScript à partir de JSON

À propos de l’outil JSON en TypeScript

L’outil JSON en TypeScript lit un échantillon JSON et écrit les interfaces TypeScript qui le décrivent, avec le moteur quicktype-core, dans votre navigateur. Chaque objet imbriqué devient sa propre interface exportée, et chaque élément d’un tableau est examiné : une clé absente de certains éléments reçoit un point d’interrogation, et une valeur parfois null est typée avec null dans une union. Les clés qui ne sont pas des identificateurs valides, comme first-name, sont écrites entre guillemets. L’outil ne génère que des types : ni classes, ni vérifications à l’exécution, ni enums, dates ou types UUID déduits des valeurs de chaîne.

Exemple

Deux enregistrements d’utilisateurs renvoyés par une API : lastLogin vaut null dans le second, address n’existe que dans le premier, tags est vide dans le second, et manager-id n’est pas un identificateur valide. La sortie ci-dessous est exactement ce qu’écrit « Convertir ».

Entrée JSON

[{"id": 101, "email": "ada@example.com", "role": "admin",
  "lastLogin": "2026-10-01T08:30:00Z",
  "address": {"city": "London", "zip": "N1 9GU"},
  "tags": ["beta"], "manager-id": null},
 {"id": 102, "email": "lin@example.com", "role": "editor",
  "lastLogin": null, "tags": [], "manager-id": 101}]

Sortie TypeScript

export interface Root {
    id:           number;
    email:        string;
    role:         string;
    lastLogin:    null | string;
    address?:     Address;
    tags:         string[];
    "manager-id": number | null;
}

export interface Address {
    city: string;
    zip:  string;
}

Comment générer des interfaces TypeScript à partir de JSON

  1. 1Collez un objet JSON, ou un tableau de plusieurs objets représentatifs, dans « Entrée JSON ».
  2. 2Cliquez sur « Convertir » ; le moteur se charge au premier clic, puis les interfaces remplissent « Sortie TypeScript ».
  3. 3Comparez les clés optionnelles et les unions avec null aux données que votre code recevra réellement.
  4. 4Cliquez sur « Copier », ou sur « Télécharger » pour enregistrer le code sous « types.ts ».

Formats et limites

Entrée
Texte JSON : un objet, ou un tableau d’objets dont les éléments sont fusionnés ; un tableau de valeurs simples donne un message au lieu de code
Sortie
Interfaces TypeScript exportées, une par objet imbriqué, enregistrées sous types.ts
Clés optionnelles
Un point d’interrogation quand une clé manque dans certains éléments du tableau ; null dans une union quand une valeur est null
Non générés
Classes, validation à l’exécution, enums, types date ou UUID (les chaînes restent string)

Usages courants

Typer la réponse d’une API REST
Côté front-end, copiez la réponse de GET /users depuis l’onglet Réseau du navigateur et collez le tableau entier : vous obtenez une interface Root qui décrit un utilisateur, plus une interface par objet imbriqué, pour typer le résultat de l’appel fetch.
Décrire un fichier de paramètres
Un fichier JSON d’indicateurs de fonctionnalités (feature flags) ou de paramètres d’application devient une interface : l’éditeur complète alors ses clés automatiquement et signale une clé mal orthographiée dans le code qui les lit.
Repérer les champs qu’un flux de données omet
En collant 50 enregistrements tirés du journal d’un webhook ou d’un export de données, vous voyez, grâce aux points d’interrogation et aux unions avec null, quelles clés manquent dans certains enregistrements et lesquelles sont parfois null, avant que le code ne suppose qu’elles sont toujours là.

Quel outil choisir

  • Formateur JSON: quand « Convertir » répond par un message « JSON non valide », cet outil affiche la ligne fautive avec un ^ sous le problème : vous pouvez corriger l’échantillon et le coller de nouveau ici.
  • JSON en struct Go: le même moteur quicktype et la même fusion des éléments d’un tableau, mais le code est écrit sous forme de structs Go avec des tags json et des champs int64 ou float64 au lieu d’interfaces TypeScript.
  • TypeScript en JavaScript: la tâche inverse : il retire les annotations de type et les interfaces d’un code source TypeScript pour ne laisser que du JavaScript, et il ne lit pas de JSON.

Où votre JSON est traité

Les interfaces sont générées dans votre navigateur : la page charge le moteur quicktype à votre premier clic, et votre JSON n’est pas envoyé, pas plus que le TypeScript qu’il produit. Si un message d’erreur s’affiche, une copie abrégée de ce message, sans le texte cité, les nombres longs ni les adresses, est envoyée à notre journal des erreurs avec le nom de l’outil ainsi que le nom et la version de votre navigateur, pour que l’outil puisse être corrigé.

Questions fréquentes

L’outil détecte-t-il les champs optionnels ?

Oui, quand vous collez un tableau. Tous les éléments sont fusionnés : une clé absente de certains d’entre eux est écrite avec un point d’interrogation, et une clé qui vaut null dans certains d’entre eux reçoit null dans son type, par exemple null | string. Avec un seul objet, toutes les clés qu’il contient sont obligatoires.

Comment les objets et les tableaux imbriqués sont-ils typés ?

Chaque objet imbriqué devient une interface exportée distincte, nommée d’après sa clé, comme Team pour une clé team, et un tableau d’objets devient un tableau de cette interface. Les tableaux de chaînes ou de nombres deviennent string[] ou number[]. Un arbre qui répète sa propre forme, comme {"name": "a", "children": [{"name": "b", "children": []}]}, donne le type Root[] à children au lieu d’une chaîne sans fin d’interfaces.

Que deviennent les clés qui contiennent des tirets ou des espaces ?

Elles gardent leur orthographe exacte sous forme de noms de propriétés entre guillemets, ce qui est du TypeScript valide : l’interface correspond donc au JSON sans aucun renommage. Les clés qui sont des identificateurs valides, comme nickname, sont écrites sans guillemets.

Puis-je enregistrer le résultat dans un fichier .ts ?

Oui. Après une conversion, une ligne nommée types.ts apparaît sous la sortie avec un bouton « Télécharger » ; sur iPhone et iPad, un bouton « Enregistrer ou partager » s’y ajoute. « Copier » place le même code dans le presse-papiers.

Quel type reçoit un champ dont les valeurs mélangent nombres et chaînes ?

Une union de tous les types trouvés. [{"a": 1}, {"a": "x"}] donne le type number | string à a, et un tableau qui contient 1, "a" et true est typé Array<boolean | number | string>.

Que devient un tableau vide ?

unknown[], car l’échantillon ne dit rien de ses éléments. Collez des enregistrements où ce tableau contient au moins un élément, et le type fusionné devient string[], number[] ou un tableau d’interfaces.

Puis-je choisir le nom de la racine ou obtenir des alias de type au lieu d’interfaces ?

Non. L’interface de premier niveau s’appelle toujours Root, et chaque forme est écrite comme une interface exportée. Renommez Root dans votre éditeur, et remplacez vous-même interface par type si votre base de code préfère les alias.

Et si deux objets imbriqués ont le même nom de clé, mais pas les mêmes champs ?

Chaque forme reçoit sa propre interface, préfixée par son parent : une clé address sous user et une autre sous company deviennent UserAddress et CompanyAddress, et aucune n’écrase l’autre.

Peut-on typer sans risque les ID numériques longs en number ?

Pas toujours. JavaScript ne représente exactement les nombres entiers que jusqu’à 9 007 199 254 740 991, et chaque nombre JSON est typé number ici. Quand le JSON contient un nombre entier au-delà, un commentaire en haut de la sortie indique combien : JSON.parse les arrondit, gardez donc ces ID sous forme de chaînes dans l’API ou lisez-les comme un bigint.

Pourquoi deux clés différentes partagent-elles une interface au nom étrange ?

Les objets qui ont exactement les mêmes champs et les mêmes types sont fusionnés en une seule interface, nommée d’après les clés qui les contiennent. {"home": {"city": "x", "zip": "1"}, "work": {"city": "y", "zip": "2"}} donne le type Home à home et à work ; billing et shipping avec les mêmes champs partagent une interface nommée Ing, la terminaison commune aux deux noms. La forme est juste : renommez l’interface dans votre éditeur.

Quand un objet devient-il { [key : string] : T } au lieu d’une interface ?

Quand ses clés ressemblent à des données plutôt qu’à des noms de champs et que toutes ses valeurs ont un même type. {"byId": {"1": {...}, "2": {...}}} donne le type { [key : string] : ByID } à byId, et des taux de change indexés par USD, EUR, GBP et JPY donnent { [key : string] : number }. Avec seulement USD, EUR et GBP, ou avec des clés qui sont des mots comme red, green et blue, chaque clé reste un champ nommé. C’est une heuristique du moteur : vérifiez donc les objets indexés par des ID ou des codes.

Pourquoi un tableau de chaînes ou de nombres ne donne-t-il aucune interface ?

Un tableau de premier niveau qui ne contient que des valeurs simples, comme ["a", "b"], [1, 2, 3], [] ou [[1]], n’a aucun objet à décrire : le moteur n’écrit donc aucun code, et la page affiche un message à la place. Placez le tableau dans un objet : {"items": ["a", "b"]} donne le type string[] à items.

Pourquoi une date ISO est-elle typée string et non Date ?

Parce que JSON.parse renvoie "2026-10-01T08:30:00Z" sous forme de chaîne, pas de Date. Une interface qui indiquerait Date permettrait au code d’appeler getTime() sur une valeur qui reste du texte à l’exécution. Il en va de même des UUID et des nombres écrits entre guillemets comme "42" : ils restent typés string jusqu’à ce que votre code les convertisse.

L’outil vérifie-t-il que les données correspondent vraiment aux interfaces ?

Non. Les interfaces TypeScript sont effacées à la compilation du code : elles décrivent les données attendues sans vérifier ce qui arrive. La sortie ne contient aucun code de validation ni schéma Zod ; servez-vous-en comme de la forme à suivre quand vous en écrivez un.

Trucs et astuces

  • ✓Renommez l’interface Root après l’avoir collée dans votre projet : ce nom vient de l’outil, pas de vos données.
  • ✓Si le résultat est un message « JSON non valide », ouvrez le même texte dans l’outil Formateur JSON, qui indique la ligne et la colonne de l’erreur.