My basic problem is that upon creation of a set of aws servers I want to configure them to know about each other.
Upon creation of each server their details are saved in a registered 'servers' var (shown below). What I really want to be able to do after creation is run a task like so:
- name: Add servers details to all other servers
lineinfile:
dest: /path/to/configfile
line: "servername={{ item.1.private_ip }}"
delegate_to: "{{ item.0.public_dns_name }}"
with_nested:
- list_of_servers
- list_of_servers
Supplying the list twice to 'with_nested' is essential here.
Getting a list of list is easy enough to do with:
"{{ servers.results | map(attribute='tagged_instances') | list }}"
which returns:
[
[ { "private_ip": "ip1", "public_dns_name": "dns1" } , { ... }],
[ { ... }, { ... } ]
]
but how would you turn this into:
[
{ "private_ip": "ip1", "public_dns_name": "dns1" },
{ ... },
{ ... },
{ ... }
]
The 'servers' registered var looks like:
"servers": {
"changed": true,
"msg": "All items completed",
"results": [
{
...
"tagged_instances": [
{
...
"private_ip": "ip1",
"public_dns_name": "dns1",
...
},
{
...
"private_ip": "ip2",
"public_dns_name": "dns2",
...
}
]
},
{
...
"tagged_instances": [
{
...
"private_ip": "ip3",
"public_dns_name": "dn3",
...
},
{
...
"private_ip": "ip4",
"public_dns_name": "dns4",
...
}
]
},
...
]
}
Note: I have a pretty ugly solution by using 'with_flattened' and a debug statement to create a new registered var 'flattened_servers' which I then map over again. But am hoping for a more elegant solution :)
Jinja2 comes with a built-in filter sum
which can be used like:
{{ servers.results | sum(attribute='tagged_instances', start=[]) }}
A bit late, but starting from ansible 2.5 you can do this:
"{{ servers.results | map(attribute='tagged_instances') | list | flatten }}"
You can do list comprehension to convert it to list of dicts.
For example:
- name: Convert
shell: python -c "print [x for b in {{ servers }}['servers']['results'] for x in b['tagged_instances']]"
register: my_list_of_dicts
Assuming that {{ servers }}
variable holds the entire dictionary (not json).
Just wanted to list the "ugly" workaround as the python code did not work for me
- debug: var=item
with_flattened:
- "{{ servers.results|map(attribute='tagged_instances')|list }}"
register: servers_instances_tmp
no_log: True
- set_fact: servers_instances="{{ servers_instances_tmp.results|map(attribute='item')|list }}"
- debug: var=servers_instances
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With