AnsiblePilot — Master Ansible Automation

AnsiblePilot is the leading resource for learning Ansible automation, DevOps, and infrastructure as code. Browse over 1,400 tutorials covering Ansible modules, playbooks, roles, collections, and real-world examples. Whether you are a beginner or an experienced engineer, our step-by-step guides help you automate Linux, Windows, cloud, containers, and network infrastructure.

Popular Topics

About Luca Berton

Luca Berton is an Ansible automation expert, author of 8 Ansible books published by Apress and Leanpub including "Ansible for VMware by Examples" and "Ansible for Kubernetes by Example", and creator of the Ansible Pilot YouTube channel. He shares practical automation knowledge through tutorials, books, and video courses to help IT professionals and DevOps engineers master infrastructure automation.

Ansible from_json & to_json Filters: Parse & Generate JSON Data (Guide)

By Luca Berton · Published 2024-01-01 · Category: troubleshooting

How to parse and generate JSON in Ansible with from_json, to_json, to_nice_json filters. Convert strings to dicts, format output, API responses.

What Are from_json and to_json Filters?

The from_json and to_json filters convert data between JSON strings and Ansible data structures: • from_json: Parses a JSON string into a dictionary or list • to_json: Converts a variable (dict, list) into a JSON string • to_nice_json: Converts to human-readable formatted JSON

See also: Ansible Read JSON File: lookup file Plugin & from_json (Guide)

from_json: Parse JSON Strings

Use from_json when you receive JSON as a string (from API calls, command output, file reads):

---
- name: Parse JSON data
  hosts: localhost
  vars:
    json_string: '{"name": "web-server", "port": 8080, "enabled": true}'
  tasks:
    - name: Parse JSON string into variable
      ansible.builtin.set_fact:
        server_config: "{{ json_string | from_json }}"

- name: Access parsed data ansible.builtin.debug: msg: "Server {{ server_config.name }} runs on port {{ server_config.port }}"

Parse JSON from Command Output

- name: Get Docker container info
  ansible.builtin.command: docker inspect my-container
  register: docker_output

- name: Parse Docker inspect JSON ansible.builtin.set_fact: container_info: "{{ docker_output.stdout | from_json }}"

- name: Show container IP ansible.builtin.debug: msg: "Container IP: {{ container_info[0].NetworkSettings.IPAddress }}"

Parse JSON from File

- name: Read JSON config file
  ansible.builtin.slurp:
    src: /etc/app/config.json
  register: config_file

- name: Parse file content ansible.builtin.set_fact: app_config: "{{ config_file.content | b64decode | from_json }}"

- name: Use config values ansible.builtin.debug: msg: "Database: {{ app_config.database.host }}:{{ app_config.database.port }}"

to_json: Convert to JSON Strings

Use to_json to convert Ansible variables to JSON format:

- name: Convert variable to JSON
  ansible.builtin.debug:
    msg: "{{ my_dict | to_json }}"

# Output: {"key1": "value1", "key2": "value2"}

Write JSON to File

- name: Write config as JSON file
  ansible.builtin.copy:
    content: "{{ app_config | to_nice_json }}"
    dest: /etc/app/config.json
    mode: '0644'

Send JSON in API Requests

- name: Send data to API
  ansible.builtin.uri:
    url: https://api.example.com/servers
    method: POST
    body: "{{ server_data | to_json }}"
    body_format: json
    headers:
      Content-Type: application/json

See also: Ansible Jinja2 Filters: Transform Data in Playbooks (Complete Reference)

to_nice_json: Human-Readable Output

to_nice_json produces formatted, indented JSON:

- name: Pretty-print JSON
  vars:
    config:
      server:
        name: web-01
        port: 443
      database:
        host: db-01
        port: 5432
  ansible.builtin.debug:
    msg: "{{ config | to_nice_json }}"

Output:

{
    "server": {
        "name": "web-01",
        "port": 443
    },
    "database": {
        "host": "db-01",
        "port": 5432
    }
}

Control Indentation

# 2-space indent
msg: "{{ config | to_nice_json(indent=2) }}"

# Sort keys alphabetically msg: "{{ config | to_nice_json(sort_keys=True) }}"

# Both msg: "{{ config | to_nice_json(indent=2, sort_keys=True) }}"

to_nice_yaml: Convert to YAML Format

Convert variables to readable YAML:

- name: Output as YAML
  ansible.builtin.debug:
    msg: "{{ config | to_nice_yaml }}"

- name: Write YAML file ansible.builtin.copy: content: "{{ config | to_nice_yaml }}" dest: /etc/app/config.yaml

See also: Ansible map vs selectattr vs json_query: Filter Data the Right Way

Common Patterns

Chain Filters

# Read file → decode → parse JSON → extract value
- name: Get database host from JSON config
  ansible.builtin.set_fact:
    db_host: "{{ lookup('file', 'config.json') | from_json | json_query('database.host') }}"

Handle JSON in Loops

- name: Process JSON array
  vars:
    servers_json: '[{"name":"web-1","port":80},{"name":"web-2","port":8080}]'
  ansible.builtin.debug:
    msg: "{{ item.name }} on port {{ item.port }}"
  loop: "{{ servers_json | from_json }}"

Merge and Convert

- name: Merge configs and write JSON
  vars:
    defaults:
      log_level: info
      timeout: 30
    overrides:
      timeout: 60
      debug: true
  ansible.builtin.copy:
    content: "{{ defaults | combine(overrides) | to_nice_json }}"
    dest: /etc/app/config.json

Error Handling

Invalid JSON

- name: Safely parse JSON
  block:
    - name: Parse potentially invalid JSON
      ansible.builtin.set_fact:
        data: "{{ maybe_json | from_json }}"
  rescue:
    - name: Handle parse error
      ansible.builtin.debug:
        msg: "Failed to parse JSON: {{ maybe_json }}"

Default Values

# Use default if key doesn't exist
- name: Safe access with defaults
  ansible.builtin.debug:
    msg: "Port: {{ (json_string | from_json).port | default(8080) }}"

FAQ

What is the difference between from_json and from_yaml?

from_json parses JSON strings only. from_yaml parses YAML strings (which is a superset of JSON). In practice, from_yaml can also parse JSON, but from_json is stricter and preferred when you know the input is JSON.

When do I need from_json vs just accessing the variable?

You need from_json when the data is a string containing JSON, not a parsed data structure. This happens with command output (register), file reads (slurp), and API responses returned as strings. If the variable is already a dict/list, you don't need it.

How do I handle nested JSON with special characters?

Use bracket notation for keys with dots or spaces: {{ (json_str | from_json)['my.key']['with spaces'] }}. For complex nested queries, use the json_query filter with JMESPath syntax.

Related Articles

Ansible Jinja2 Filters GuideAnsible map FilterAnsible dict2items & items2dictAnsible combine Filter

Category: troubleshooting

Browse all Ansible tutorials · AnsiblePilot Home