YAML vs JSON vs TOML : forces, usages et les pièges de typage implicite de YAML
Le domaine de prédilection de chaque format
Chaque format de sérialisation de données excelle dans son propre domaine. JSON (JavaScript Object Notation, standardisé sous ECMA-404 et RFC 8259) est le langage universel des API HTTP : presque tous les endpoints REST l'utilisent, chaque langage possède un analyseur JSON sans dépendance, et sa grammaire tient en une seule page. YAML (YAML Ain't Markup Language) domine les fichiers de configuration dans les outils DevOps — les manifestes Kubernetes, les workflows GitHub Actions, les playbooks Ansible et les fichiers Docker Compose sont tous en YAML. Ses chaînes multilignes et son support des commentaires le rendent bien plus confortable que JSON pour les fichiers que les humains éditent quotidiennement. TOML (Tom's Obvious, Minimal Language) est le choix canonique pour la configuration au niveau du projet : Cargo.toml pour les packages Rust, pyproject.toml pour les métadonnées de build Python, et la configuration des sites Hugo utilisent tous TOML.
Ces différences de domaine ne sont pas accidentelles — elles reflètent les priorités de conception de chaque format. JSON privilégie l'interopérabilité et le déterminisme ; YAML privilégie la lisibilité humaine et l'expressivité ; TOML privilégie la sécurité des types et l'analyse prévisible. Comprendre ces priorités facilite le choix du bon outil et évite d'importer les hypothèses d'un format dans l'espace problème d'un autre.
Le typage implicite de YAML : le problème de la Norvège
Le piège le plus tristement célèbre de YAML est sa coercition de type implicite agressive. En YAML 1.1 (la version utilisée par la plupart des analyseurs jusqu'à récemment, y compris PyYAML < 6.0 et Psych de Ruby avant 4.0), un scalaire sans guillemets est testé contre une séquence d'expressions régulières pour déterminer son type. Les tests booléens correspondent à yes, no, on, off, true, false — tous sans distinction de casse. Cela a causé un vrai bug d'intégrité des données dans les logiciels utilisant les codes pays ISO 3166-1 alpha-2 : le code de la Norvège est NO, que YAML 1.1 convertit silencieusement au booléen false. Une correspondance comme norway: NO devient {norway: false} à l'exécution — sans erreur, sans avertissement.
YAML 1.2 (publié en 2009, adopté par ruamel.yaml et les analyseurs plus récents) a restreint l'ensemble booléen à seulement true et false (sensible à la casse), éliminant les variantes yes/no/on/off. Cependant, des millions de fichiers de production et les outils qui les lisent s'exécutent encore contre des analyseurs YAML 1.1. La règle de sécurité : toujours mettre entre guillemets les valeurs de chaîne qui pourraient être mal interprétées — codes pays, mots ressemblant à des drapeaux, chaînes d'apparence numérique.
Autres pièges de YAML : tabulations, ancres et séparateurs de documents
L'indentation est la syntaxe de YAML — et les tabulations ne sont jamais valides en indentation YAML. La spécification interdit explicitement les caractères de tabulation en position d'indentation. Pourtant les tabulations sont invisibles dans la plupart des éditeurs par défaut, et une tabulation accidentelle produit une erreur de scanner qui pointe vers le mauvais numéro de ligne dans certains analyseurs. La solution est d'activer 'afficher les espaces blancs' dans votre éditeur et de le configurer pour développer les tabulations en espaces dans les fichiers .yaml.
Les ancres YAML (&) et les alias (*) permettent de réutiliser un nœud dans tout un document, ce qui est vraiment utile pour les longs manifestes Kubernetes avec des specs de conteneur répétées. Mais ils permettent aussi des attaques d'expansion de type 'billion laughs' sur les analyseurs qui ne limitent pas la profondeur des alias. La plupart des analyseurs de production (PyYAML 5.1+, snakeyaml avec SafeLoader) limitent la profondeur des alias ; utilisez toujours les API de chargement sécurisé. Le séparateur de documents --- permet plusieurs documents YAML dans un seul fichier — kubectl apply -f en dépend — mais certains analyseurs ne retournent que le premier document à moins d'itérer explicitement, ignorant silencieusement le reste.
Les types explicites de TOML et son avantage avec les dates
TOML assigne un type à chaque valeur au niveau syntaxique, sans coercition implicite. Les entiers s'écrivent sans guillemets (port = 8080), les flottants nécessitent un point décimal (timeout = 1.5), les booléens sont true ou false en minuscules, et les chaînes nécessitent toujours des guillemets. Cela signifie qu'une faute de frappe produisant un mot sans guillemets est une erreur d'analyse, pas un changement de type silencieux — l'analyseur refuse de charger le fichier plutôt que de continuer avec des données incorrectes. TOML 1.0 spécifie également quatre types de date-heure comme littéraux de première classe : offset_date_time, local_date_time, local_date et local_time.
La syntaxe [table] et [[array of tables]] correspond proprement aux objets imbriqués et aux tableaux d'objets. Un bloc [[servers]] suivi d'un autre bloc [[servers]] ajoute un deuxième élément au tableau servers — explicite, lisible, et impossible à casser avec un espace superflu. La contrepartie : TOML ne prend pas en charge les ancres ni les fichiers multi-documents, donc les hiérarchies de configuration profondes avec des sous-arbres répétés sont plus verbeuses que leurs équivalents YAML.
La rigueur de JSON comme fonctionnalité
La grammaire de JSON n'a pas de fonctionnalités optionnelles, pas de coercition de type et pas de directives au niveau du document. Un analyseur conforme lisant {"active": true} sur n'importe quelle plateforme produira un booléen — pas la chaîne "true", pas l'entier 1. Ce déterminisme explique pourquoi JSON est devenu le format fil par défaut pour les API malgré sa moindre convivialité. RFC 8259 renforce la spécification : un texte JSON est une valeur sérialisée. Les clés dupliquées dans un objet sont explicitement 'ne devrait pas', et l'encodage doit être UTF-8 sans BOM.
L'absence de commentaires est la plainte la plus citée sur JSON. Des solutions de contournement existent : JSON5 (un sur-ensemble avec commentaires et virgules finales), JSONC (utilisé dans settings.json de VS Code), et simplement supprimer les lignes // avant l'analyse. La solution idiomatique pour la configuration nécessitant des commentaires est d'utiliser TOML ou YAML pour l'édition et JSON uniquement comme format d'échange machine, généré par une étape de build.
Choisir le bon format
La règle de décision pratique est simple : JSON pour toute donnée franchissant une frontière de service (API HTTP, files de messages, configuration générée par du code) ; YAML pour les fichiers de configuration que les opérateurs éditent à la main et qui nécessitent des commentaires ou des chaînes multilignes — surtout dans les écosystèmes qui l'imposent (Kubernetes, GitHub Actions) ; TOML pour la configuration au niveau du projet où le typage fort et la structure de fichier plat sont plus importants que l'expressivité de YAML. En cas de doute, favorisez le format que votre écosystème utilise déjà.
Si vous héritez d'un gros fichier de configuration YAML et suspectez des bugs de typage implicite, un audit rapide consiste à le passer dans un linter YAML 1.2 (yamllint, spectral) et à rechercher les valeurs sans guillemets correspondant à des motifs booléens ou numériques. Pour les nouveaux projets, envisagez d'ajouter un schéma (JSON Schema fonctionne pour les trois formats via des outils) — il capture les erreurs de type avant qu'elles n'atteignent la production. Le convertisseur YAML / JSON / TOML de TeaFun vous permet de passer d'un format à l'autre dans le navigateur sans installation.