Conversion 9 min read

Converting JSON to YAML (and Back)

The complete guide to JSON-YAML conversion. Why you'd want to, how to do it, and what edge cases to watch out for.

#yaml #conversion #devops #config

TL;DR

  • JSON → YAML: Usually lossless, gains readability and comments
  • YAML → JSON: Loses comments, anchors, and multi-line strings
  • Use YAML for configs humans edit
  • Use JSON for data exchange between systems
  • Tools: js-yaml, PyYAML, or online converters

JSON vs YAML: Quick Comparison

Both JSON and YAML store the same kind of data. They're like siblings with different personalities:

  • JSON — Strict, precise, machine-friendly
  • YAML — Relaxed, readable, human-friendly

Same data, different vibes. Let's see them side by side:

The Same Data in Both Formats

config.json
json
{
  "server": {
    "host": "localhost",
    "port": 3000,
    "ssl": false
  },
  "database": {
    "connection": "postgres://localhost/myapp",
    "pool": {
      "min": 2,
      "max": 10
    }
  },
  "features": ["auth", "api", "websockets"]
}
config.yaml
yaml
# Server configuration
server:
  host: localhost
  port: 3000
  ssl: false

# Database settings
database:
  connection: postgres://localhost/myapp
  pool:
    min: 2
    max: 10

# Enabled features
features:
  - auth
  - api
  - websockets

Notice the YAML version has comments, no brackets, and is ~30% shorter. This is why DevOps loves YAML for config files.

When to Convert

JSON → YAML: Good For

  • Creating Kubernetes manifests or Docker Compose files
  • Writing configuration files that need comments
  • Making data human-editable
  • Working with CI/CD pipelines (GitHub Actions, CircleCI)

YAML → JSON: Good For

  • Sending data to APIs that expect JSON
  • Storing in databases or localStorage
  • Working with JavaScript applications
  • When you need strict parsing

Basic Conversion Rules

Objects

JSON objects become YAML mappings:

object.json
json
{
  "name": "Alice",
  "age": 30
}

Becomes:

object.yaml
yaml
name: Alice
age: 30

Arrays

JSON arrays become YAML sequences:

array.json
json
{
  "colors": ["red", "green", "blue"]
}

Becomes:

array.yaml
yaml
colors:
  - red
  - green
  - blue

Or inline (flow) style:

array-inline.yaml
yaml
colors: [red, green, blue]

Nested Structures

nested.json
json
{
  "user": {
    "profile": {
      "name": "Bob",
      "settings": {
        "theme": "dark"
      }
    }
  }
}

Becomes:

nested.yaml
yaml
user:
  profile:
    name: Bob
    settings:
      theme: dark

Edge Cases to Watch

1. Strings That Look Like Other Types

YAML is smart (sometimes too smart). It interprets values automatically:

gotcha.yaml
yaml
# These might not be what you expect!
version: 1.0      # Float, not string "1.0"
port: 3000        # Integer
enabled: yes      # Boolean true
country: NO       # Boolean false (Norway problem!)
time: 12:30       # Might be parsed as minutes

To force strings, quote them:

safe.yaml
yaml
version: "1.0"    # String
port: "3000"      # String  
enabled: "yes"    # String
country: "NO"     # String
time: "12:30"     # String
The Norway Problem: In some YAML versions, NO is interpreted as boolean false. Countries like Norway (NO), and values like off, no, false can cause surprise bugs. Always quote ambiguous strings!

2. Multi-line Strings

YAML has special syntax for multi-line strings (JSON doesn't):

multiline.yaml
yaml
# Literal block (preserves newlines)
description: |
  This is a long description
  that spans multiple lines.
  Each newline is preserved.

# Folded block (joins lines)
summary: >
  This is also a long description
  but newlines become spaces.
  Good for wrapping long text.

When converting to JSON, these become regular strings with \n:

multiline.json
json
{
  "description": "This is a long description\nthat spans multiple lines.\nEach newline is preserved.\n",
  "summary": "This is also a long description but newlines become spaces. Good for wrapping long text.\n"
}

3. Comments Are Lost

JSON doesn't support comments. When you convert YAML to JSON, all comments disappear. Forever. Gone.

with-comments.yaml
yaml
# IMPORTANT: Production database credentials
database:
  host: prod.db.example.com  # Main replica
  port: 5432

Becomes (no comments):

no-comments.json
json
{
  "database": {
    "host": "prod.db.example.com",
    "port": 5432
  }
}

4. Anchors and Aliases

YAML has a powerful feature for reusing data:

anchors.yaml
yaml
defaults: &defaults
  timeout: 30
  retries: 3

development:
  <<: *defaults
  host: localhost

production:
  <<: *defaults
  host: prod.example.com

When converted to JSON, anchors are resolved (expanded):

expanded.json
json
{
  "defaults": {
    "timeout": 30,
    "retries": 3
  },
  "development": {
    "timeout": 30,
    "retries": 3,
    "host": "localhost"
  },
  "production": {
    "timeout": 30,
    "retries": 3,
    "host": "prod.example.com"
  }
}

Converting in JavaScript

Use the js-yaml library — it's the standard:

install.sh
bash
npm install js-yaml

JSON to YAML

json-to-yaml.js
javascript
import yaml from 'js-yaml';

const jsonData = {
  server: {
    host: 'localhost',
    port: 3000
  },
  features: ['auth', 'api']
};

// Convert to YAML string
const yamlString = yaml.dump(jsonData, {
  indent: 2,
  lineWidth: 80,
  noRefs: true  // Don't use anchors
});

console.log(yamlString);
/*
server:
  host: localhost
  port: 3000
features:
  - auth
  - api
*/

YAML to JSON

yaml-to-json.js
javascript
import yaml from 'js-yaml';

const yamlString = `
server:
  host: localhost
  port: 3000
features:
  - auth
  - api
`;

// Convert to JavaScript object
const data = yaml.load(yamlString);

// Convert to JSON string
const jsonString = JSON.stringify(data, null, 2);

console.log(jsonString);
/*
{
  "server": {
    "host": "localhost",
    "port": 3000
  },
  "features": [
    "auth",
    "api"
  ]
}
*/

Converting in Python

install-python.sh
bash
pip install pyyaml
convert.py
python
import json
import yaml

# JSON to YAML
json_data = {
    "server": {"host": "localhost", "port": 3000},
    "features": ["auth", "api"]
}
yaml_string = yaml.dump(json_data, default_flow_style=False)
print(yaml_string)

# YAML to JSON
yaml_string = """
server:
  host: localhost
  port: 3000
"""
data = yaml.safe_load(yaml_string)
json_string = json.dumps(data, indent=2)
print(json_string)
Security note: Always use yaml.safe_load() in Python, not yaml.load(). The latter can execute arbitrary code from malicious YAML!

Command Line Tools

cli.sh
bash
# Using yq (YAML processor, like jq for YAML)
# JSON to YAML
yq -P input.json > output.yaml

# YAML to JSON
yq -o=json input.yaml > output.json

# Using Python one-liner
# JSON to YAML
python -c "import sys,yaml,json; print(yaml.dump(json.load(sys.stdin)))" < input.json

# YAML to JSON
python -c "import sys,yaml,json; print(json.dumps(yaml.safe_load(sys.stdin),indent=2))" < input.yaml

Online Conversion

Don't want to install anything? Use our tools:

Convert instantly! Use our JSON to YAML converter to transform between formats in your browser. No data leaves your machine.

Best Practices

  • Validate after conversion — Always check the output is valid
  • Quote ambiguous values — Especially numbers-as-strings and country codes
  • Preserve the original — Keep both versions if you need to round-trip
  • Document lost information — Note if comments or anchors were removed
  • Use consistent tooling — Same library across your pipeline

FAQ

Can YAML represent everything JSON can?

Yes. YAML is a superset of JSON. Every valid JSON document is valid YAML. The reverse isn't true — YAML has features JSON lacks.

Which is faster to parse?

JSON is generally faster. It has simpler parsing rules. YAML's flexibility comes with parsing overhead.

Should I convert my JSON configs to YAML?

If humans edit the config and need comments, yes. If it's machine-generated or consumed, JSON is fine.

What about TOML?

TOML is another config format, popular in Python (pyproject.toml) and Rust (Cargo.toml). It's simpler than YAML but less expressive. Different tool for different jobs.

About the Author

AT

Adam Tse

Founder & Lead Developer · 10+ years experience

Full-stack engineer with 10+ years of experience building developer tools and APIs. Previously worked on data infrastructure at scale, processing billions of JSON documents daily. Passionate about creating privacy-first tools that don't compromise on functionality.

JavaScript/TypeScript Web Performance Developer Tools Data Processing