ansiblejmespathjson-query

ansible json_query multiple values


From a prior GET api call in ansible I'm getting a json result back.

The api call would look something like this:

- name: Refresh Datadog monitors list
  uri:
    url: http://my.api.com
    return_content: yes
    method: GET
    status_code: 200
    headers:
      Content-Type: "application/json"
  register: results

The result looks something like this (dummy data):

[{
    "name": "bob",
    "id": 13590804,
    "colour": "blue",
    "created": "2019-11-21T07:41:33.148976+00:00",
    "modified": "2019-11-21T07:41:33.148976+00:00",
    "overall_state_modified": "2019-11-25T06:45:08+00:00",
    "overall_state": "OK"
},
{
    "name": "john",
    "id": 123124515,
    "colour": "green",
    "created": "2019-11-21T07:41:33.148976+00:00",
    "modified": "2019-11-21T07:41:33.148976+00:00",
    "overall_state_modified": "2019-11-25T06:45:08+00:00",
    "overall_state": "OK"
},
{
    "name": "carl",
    "id": 3252532,
    "colour": "orange",
    "created": "2019-11-21T07:41:33.148976+00:00",
    "modified": "2019-11-21T07:41:33.148976+00:00",
    "overall_state_modified": "2019-11-25T06:45:08+00:00",
    "overall_state": "OK"
},
{
    "name": "louis",
    "id": 5675467,
    "colour": "purple",
    "created": "2019-11-21T07:41:33.148976+00:00",
    "modified": "2019-11-21T07:41:33.148976+00:00",
    "overall_state_modified": "2019-11-25T06:45:08+00:00",
    "overall_state": "OK"
}]

In a subsequent step I'm looking to do extract just two values from the json so that it looks something like:

[{
        "name": "bob",
        "id": 13590804
    },
    {
        "name": "john",
        "id": 123124515
    },
    {
        "name": "carl",
        "id": 3252532
    },
    {
        "name": "louis",
        "id": 5675467
    }
]

I've tried multiple iterations from different sources to try and get this result such as:

- name: "Display all id's with names"
  debug: msg = "{{ results | json_query '[id, names]')}}"

and

- name: "Display all id's with names"
  debug: msg = "{{ results | json_query '[*][id, names]')}}"

I can appreciate that there's a gap in my knowledge of jmespath, but the documentation is a bit overwhelming and I'm unable to find the exact solution.


Solution

  • Your are looking for the section referenced as filters and multiselect hashes in JMESPath documentation.

    So your task should be:

    - name: "Display all id's with names"
      debug: 
        msg: "{{ results | json_query('[*].{id: id, name: name}') }}"
    

    For the demonstration purpose, given the task:

    - debug:
        msg: "{{ results | json_query('[*].{id: id, name: name}') }}"
      vars:
        results: 
          - name: bob
            id: 13590804
            colour: blue
            created: 2019-11-21T07:41:33.148976+00:00
            modified: 2019-11-21T07:41:33.148976+00:00
            overall_state_modified: 2019-11-25T06:45:08+00:00
            overall_state: OK
          - name: john
            id: 123124515
            colour: green
            created: 2019-11-21T07:41:33.148976+00:00
            modified: 2019-11-21T07:41:33.148976+00:00
            overall_state_modified: 2019-11-25T06:45:08+00:00
            overall_state: OK
          - name: carl
            id: 3252532
            colour: orange
            created: 2019-11-21T07:41:33.148976+00:00
            modified: 2019-11-21T07:41:33.148976+00:00
            overall_state_modified: 2019-11-25T06:45:08+00:00
            overall_state: OK
          - name: louis
            id: 5675467
            colour: purple
            created: 2019-11-21T07:41:33.148976+00:00
            modified: 2019-11-21T07:41:33.148976+00:00
            overall_state_modified: 2019-11-25T06:45:08+00:00
            overall_state: OK
    

    This output will be:

    ok: [localhost] => 
      msg:
      - id: 13590804
        name: bob
      - id: 123124515
        name: john
      - id: 3252532
        name: carl
      - id: 5675467
        name: louis