# Registering value from JSON output

**URL:** <https://forum.ansible.com/t/registering-value-from-json-output/31143>\
**Category:** Ansible Project\
**Created:** [August 27, 2019, 7:44pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143 "2019-08-27T19:44:15Z")\
**Posts on this page:** 8\
**Page:** 1

<div class="post-metadata">

**Author:** ![Cade\_Lambert](https://avatars.discourse-cdn.com/v4/letter/c/278dde/32.png) [@Cade\_Lambert](https://forum.ansible.com/u/Cade_Lambert)\
**Post date:** [August 27, 2019, 7:44pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/1 "2019-08-27T19:44:15Z")

</div>

I’m trying to register the value of a JSON object only when another JSON object is equal to a certain value, but I just can’t figure out how I’d do that.

For example, this is my JSON output which is registered in the variable results\_var:

“output”: {  
“json”: {  
“results”: [  
{  
“name”: “item1”  
“id”: “26”  
}

{  
“name”: “item2”  
“id”: “29”  
}

{  
“name”: “item3”  
“id”: “10”  
}

]  
}  
}

What I’d like to do is place the id into a variable only when the name matches a string.

I was trying something like this but it fails because the variable is a list.

- set\_fact:  
host\_id: “{{ item.id }}”  
when: item.name == “item2”  
loop: “{{ results\_var.output.json.results }}”

---

<div class="post-metadata">

**Author:** ![Kai\_Stian\_Olstad](https://avatars.discourse-cdn.com/v4/letter/k/e19adc/32.png) [@Kai\_Stian\_Olstad](https://forum.ansible.com/u/Kai_Stian_Olstad)\
**Post date:** [August 27, 2019, 7:53pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/2 "2019-08-27T19:53:47Z")

</div>

> I'm trying to register the value of a JSON object only when another JSON  
> object is equal to a certain value, but I just can't figure out how I'd do  
> that.
> 
> For example, this is my JSON output which is registered in the variable  
> results\_var:
> 
> "output": {  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"json": {  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"results": [  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"name": "item1"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"id": "26"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"name": "item2"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"id": "29"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;{  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"name": "item3"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;"id": "10"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;]  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}  
> }

This output looks wired, it's missing commas after } in the list.

> What I'd like to do is place the id into a variable only when the name  
> matches a string.
> 
> I was trying something like this but it fails because the variable is a  
> list.
> 
> &nbsp;&nbsp;&nbsp;- set\_fact:  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;host\_id: "{{ item.id }}"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;when: item.name == "item2"  
> &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;loop: "{{ results\_var.output.json.results }}"

You should always provide the exact error message and probably the all the code too, at fist glance I don't see anything wrong with the code.

---

<div class="post-metadata">

**Author:** ![vbotka](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/vbotka/32/359_2.png) [@vbotka](https://forum.ansible.com/u/vbotka)\
**Post date:** [August 27, 2019, 8:05pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/3 "2019-08-27T20:05:50Z")

</div>

json\_query does the job. For example

&nbsp;&nbsp;&nbsp;&nbsp;- set\_fact:  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;host\_id: "{{ json.results|json\_query('[?name==`item2`].id') }}"

if the data is properly structured.

&nbsp;&nbsp;json:  
&nbsp;&nbsp;&nbsp;&nbsp;results:  
&nbsp;&nbsp;&nbsp;&nbsp;- id: '26'  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;name: item1  
&nbsp;&nbsp;&nbsp;&nbsp;- id: '29'  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;name: item2  
&nbsp;&nbsp;&nbsp;&nbsp;- id: '10'  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;name: item3

Cheers,

&nbsp;&nbsp;-vlado

---

<div class="post-metadata">

**Author:** ![Cade\_Lambert](https://avatars.discourse-cdn.com/v4/letter/c/278dde/32.png) [@Cade\_Lambert](https://forum.ansible.com/u/Cade_Lambert)\
**Post date:** [August 28, 2019, 3:04pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/4 "2019-08-28T15:04:16Z")

</div>

Ok, I guess a little background would help. I’m using the uri module to retrieve a list of hosts in an inventory from our Tower server. It returns the JSON output below. I’ve paired it down to just the pieces I care about. There are two servers in this inventory. I’d like to retrieve the id based on the server name.

ok: [localhost] =\> {  
“host\_list.json.results”: [  
{  
“ansible\_facts\_modified”: null,  
“created”: “2019-08-27T18:50:09.132071Z”,  
“description”: “”,  
“enabled”: true,  
“has\_active\_failures”: false,  
“has\_inventory\_sources”: false,  
“id”: 799,  
“insights\_system\_id”: null,  
“instance\_id”: “”,  
“inventory”: 18,  
“last\_job”: null,  
“last\_job\_host\_summary”: null,  
“modified”: “2019-08-27T18:50:09.132085Z”,  
“name”: “server1”,  
},  
{  
“ansible\_facts\_modified”: “2019-08-28T14:41:17.846100Z”,  
“created”: “2019-08-26T19:28:55.187225Z”,  
“description”: “”,  
“enabled”: true,  
“has\_active\_failures”: false,  
“has\_inventory\_sources”: false,  
“id”: 790,  
“insights\_system\_id”: null,  
“instance\_id”: “”,  
“inventory”: 18,  
“last\_job”: 7879,  
“last\_job\_host\_summary”: 10273,  
“modified”: “2019-08-28T14:41:17.846235Z”,  
“name”: “server2”,

}  
]  
}

I tried json\_query:

- set\_fact:  
host\_id: “{{ host\_list.json.results|json\_query(‘[?name == ‘server2’].id’) }}”

It threw the following error:  
fatal: [localhost]: FAILED! =\> {“msg”: “template error while templating string: expected token ‘,’, got ‘server2’. String: {{ host\_list.json.results|json\_query(‘[?name == ‘server2’].id’) }}”}

---

<div class="post-metadata">

**Author:** ![vbotka](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/vbotka/32/359_2.png) [@vbotka](https://forum.ansible.com/u/vbotka)\
**Post date:** [August 28, 2019, 3:27pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/5 "2019-08-28T15:27:10Z")

</div>

The error is caused by your "improvement". The query works fine when you keep  
the backticks "`" that wrap the argument (both double and single-quotes have  
already been used elsewhere in the string). The tasks below

&nbsp;&nbsp;&nbsp;&nbsp;- set\_fact:  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;host\_id: "{{ results|json\_query('[?name==`server2`].id') }}"  
&nbsp;&nbsp;&nbsp;&nbsp;- debug:  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;var: host\_id

give

&nbsp;&nbsp;&nbsp;&nbsp;"host\_id": [  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;790  
&nbsp;&nbsp;&nbsp;&nbsp;]

Cheers,

&nbsp;&nbsp;-vlado

---

<div class="post-metadata">

**Author:** ![Cade\_Lambert](https://avatars.discourse-cdn.com/v4/letter/c/278dde/32.png) [@Cade\_Lambert](https://forum.ansible.com/u/Cade_Lambert)\
**Post date:** [August 28, 2019, 3:35pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/6 "2019-08-28T15:35:23Z")

</div>

Ah, ok, I missed that those were backticks. So because we used double-quotes to encompass the whole argument, and single-quotes to encompass the json\_query argument, we cannot use single-quotes again to encompass the search string. We need to use something else, in this case backticks, to distinguish the search string?

---

<div class="post-metadata">

**Author:** ![vbotka](https://sea1.discourse-cdn.com/ansible/user_avatar/forum.ansible.com/vbotka/32/359_2.png) [@vbotka](https://forum.ansible.com/u/vbotka)\
**Post date:** [August 28, 2019, 4:25pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/7 "2019-08-28T16:25:03Z")

</div>

Right. It's possible to avoid them and declare a variable for this purpose.

&nbsp;&nbsp;&nbsp;&nbsp;- set\_fact:  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;host\_id: "{{ results|json\_query(query) }}"  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vars:  
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;query: "[?name=='server2'].id"

---

<div class="post-metadata">

**Author:** ![Cade\_Lambert](https://avatars.discourse-cdn.com/v4/letter/c/278dde/32.png) [@Cade\_Lambert](https://forum.ansible.com/u/Cade_Lambert)\
**Post date:** [August 28, 2019, 5:16pm UTC](https://forum.ansible.com/t/registering-value-from-json-output/31143/8 "2019-08-28T17:16:53Z")

</div>

Great, thanks for the help.
