Calling a loop task to filter and construct final json result in Ansible

Calling a loop task to filter and construct final json result in Ansible

Sometimes you need to :

  • iterate a payload
  • call an API for each item
  • filtering the json result using json_query
  • returning a final result with all the filtered result

With this result you can iterate for another API.

This article talk about how to do that using Ansible, json_query filter

Firstly the structure 2 yaml files, the main.yml that call in a loop the tools/post_api.yml


- hosts:
        uuid: uuid_1
          - item1_attribute1_value1
          - item1_attribute1_value2
          - item1_attribute1_value3
        attribute2: item1_attribute2_value1
        uuid: uuid_2
          - item2_attribute1_value1
          - item2_attribute1_value2
          - item2_attribute1_value3
        attribute2: item2_attribute2_value1
        uuid: uuid_3
          - item3_attribute1_value1
          - item3_attribute1_value2
          - item3_attribute1_value3
        attribute2: item3_attribute2_value1

  - name: Call a task looping the payload
    include_tasks: tools/post_api.yml
    loop: "{{ input_payload }}"
      loop_var: outer_item
    register: get_api_wrapper_result

  - name: Show the final_result
      var: final_result



# Api call will return for first element
#   "some_key": "some_value"
#   "callback_url_1": ""
#   "callback_url_2": ""
#   "callback_url_3": ""
#   "another_key": "another_value"
# }

- name: Call an api for each item
    url: ""
    method: POST
      Accept: "application/json"
      Content-Type: "application/json"
    body: "{{ outer_item }}"
    body_format: json
    return_content: yes
    status_code: 200,201
  register: api_call_result

- debug:
    var: api_call_result.json

- name: Construct the final result
    "final_result": "{{ final_result | default([]) | union([ api_call_result | json_query(jmesquery) ]) }}"
    jmesquery: "{uuid: '{{ outer_item.uuid }}', first_url: json.callback_url_1, third_url: json.callback_url_3}"

Final result

    "final_result": [
            "first_url": "",
            "third_url": "",
            "uuid": "uuid_1"
            "first_url": "",
            "third_url": "",
            "uuid": "uuid_2"
            "first_url": "",
            "third_url": "",
            "uuid": "uuid_3"


For each item in the payload it calls an API (I used to simulate an API) that will return a content depending of the input payload.

I need to use the result of all the loops to call another API but I don’t need all the content so I want to filter it and I want to identify each result with an uuid from the initial loop.


  • input_payload is very classic array payload with an uuid and key/values
  • I call a tools task looping on the input_payload and using an outer_item if we need to loop in the tools task


  • I call an API that return a json with values for the outer_item and register the result for the item in api_call_result
  "some_key": "some_value"
  "callback_url_1": ""
  "callback_url_2": ""
  "callback_url_3": ""
  "another_key": "another_value"


  • I use a set_fact to construct a variable that will contains the union of all the API call
  • final_result | default([]) for first item I need to initiate the final_result as an empty array

  • union([ api_call_result | json_query(jmesquery) ]) I make an union with previous value of final_result and a filtered api_call_result

  • I filter the json using jmespath  setting  uuid with a variable from the outer_item and filtering/renaming 2 of the third url returned by the API
mesquery: "{uuid: '{{ outer_item.uuid }}', first_url: json.callback_url_1, third_url: json.callback_url_3}"


At the end in the main.yml file after calling my task post_api.yml I have a final_result that I can use to interact with another task/API/action.

I used this method to create multiple items from a big input_payload, the API used return urls to an Hashicorp Vault for each item, so I have to call again another API to retrieve the content of the Vault.


Please follow and like us: