Retour au cours

parser du json et du yaml

Objectifs

  • Comprendre l’utilité des formats JSON et YAML pour les fichiers de configuration et les APIs.
  • Parser (analyser) une chaîne de caractères JSON pour la transformer en Hash Ruby.
  • Générer une chaîne JSON à partir d’un Hash Ruby.
  • Faire de même pour le format YAML.

Dans le développement moderne, les applications communiquent et sont configurées via des formats de données structurés. JSON et YAML sont les deux plus populaires. Ruby dispose de bibliothèques standard pour les manipuler très facilement.

JSON (JavaScript Object Notation)

JSON est le format de facto pour les APIs web. Sa syntaxe est très proche de celle des objets JavaScript.

Lire du JSON (Parser)

Pour travailler avec du JSON, il faut d’abord charger la bibliothèque json.

require 'json'

La méthode JSON.parse prend une chaîne de caractères JSON et la transforme en une structure de données Ruby (généralement un Hash ou un Array).

json_string = '{ "nom": "Alice", "age": 30, "competences": ["Ruby", "Docker"] }'

# Parser la chaîne en un Hash Ruby
donnees = JSON.parse(json_string)

puts donnees.class     # => Hash
puts donnees["nom"]    # => "Alice"
puts donnees["competences"][0] # => "Ruby"

Écrire du JSON (Générer)

Pour convertir un Hash ou un Array Ruby en une chaîne JSON, on utilise la méthode .to_json.

require 'json'

mon_hash = {
  utilisateur: "Bob",
  id: 42,
  actif: true
}

# Convertir le hash en une chaîne JSON
json_output = mon_hash.to_json
puts json_output # => {"utilisateur":"Bob","id":42,"actif":true}

# Pour une sortie formatée et lisible ("pretty")
puts JSON.pretty_generate(mon_hash)

YAML (YAML Ain’t Markup Language)

YAML est un autre format de sérialisation, souvent privilégié pour les fichiers de configuration (comme pour Docker Compose ou GitHub Actions) car il est plus lisible par l’humain (il n’utilise pas d’accolades et est basé sur l’indentation).

Lire du YAML

La bibliothèque yaml fait aussi partie de la bibliothèque standard.

require 'yaml'

# Lire depuis une chaîne
yaml_string = """
---
nom: Alice
age: 30
competences:
  - Ruby
  - Docker
"""
donnees_yaml = YAML.safe_load(yaml_string)
puts donnees_yaml["age"] # => 30


# Lire directement depuis un fichier (très courant)
# Supposons un fichier config.yml
# config = YAML.load_file('config.yml')
# puts config['database']['host']

Note : safe_load est la méthode sécurisée à privilégier sur load.

Écrire du YAML

La méthode .to_yaml convertit un objet Ruby en une chaîne YAML.

require 'yaml'

mon_hash = {
  utilisateur: "Bob",
  id: 42,
  actif: true
}

puts mon_hash.to_yaml

Sortie :

---
:utilisateur: Bob
:id: 42
:actif: true

Bonnes pratiques

  • Toujours utiliser les bibliothèques dédiées. N’essayez jamais de parser du JSON ou du YAML avec des expressions régulières. C’est beaucoup trop complexe et source d’erreurs.
  • Gérez les erreurs de parsing. Si la chaîne JSON ou YAML est mal formée, la méthode parse ou load lèvera une erreur. Dans une vraie application, il faut l’anticiper avec un bloc begin...rescue.
  • JSON pour les machines, YAML pour les humains. C’est une bonne règle générale : utilisez JSON pour la communication entre services (APIs) et YAML pour les fichiers de configuration que vous devez lire et modifier à la main.

Exercices

  1. Parser une API :

    • L’URL https://api.github.com/users/torvalds renvoie des informations sur le créateur de Linux au format JSON.
    • Écrivez un script Ruby qui (en utilisant une bibliothèque comme net/http) récupère le contenu de cette URL, le parse, et affiche le nom (name) et le nombre de followers (followers) de Linus Torvalds.
  2. Créer un fichier de configuration :

    • Créez un hash Ruby représentant une configuration simple pour une application (ex: host, port, database_name).
    • Convertissez ce hash en une chaîne YAML et sauvegardez-la dans un fichier config.yml.
  3. Charger une configuration :

    • Écrivez un autre script qui lit le fichier config.yml que vous venez de créer en utilisant YAML.load_file.
    • Affichez un message de connexion en utilisant les valeurs chargées, par exemple : “Connexion à la base de données sur [host]:[port]”.