I would like to create a list with this dict
{
"v3bf33-srv01": "eu-west0-a",
"v3bf33-srv02": "eu-west0-a",
"v3bf33-srv03": "eu-west0-a",
"v3bf33-srv04": "eu-west0-b",
"v3bf33-srv05": "eu-west0-b",
"v3bf33-srv06": "eu-west0-b",
"v3bf33-srv07": "eu-west0-c",
"v3bf33-srv08": "eu-west0-c",
"v3bf33-srv09": "eu-west0-c",
}
I would like to create a list, so, if a user ask 5 servers, cycle through servers of each value: eu-west0-a
, eu-west0-b
, eu-west0-c
, then, eu-west0-a
, eu-west0-b
.
The result should be a list containing only the server name.
E.g.:
- v3bf33-srv01 #eu-west0-a
- v3bf33-srv04 #eu-west0-b
- v3bf33-srv07 #eu-west0-c
- v3bf33-srv02 #eu-west0-a
- v3bf33-srv05 #eu-west0-b
CodePudding user response:
Given the simplified data for testing
servers:
srv01: a
srv02: a
srv03: a
srv04: b
srv05: b
srv06: b
srv07: c
srv08: c
srv09: c
Create a matrix of the keys
arr: "{{ servers|dict2items|
groupby('value')|
map(attribute=1)|
map('map', attribute='key')|
list }}"
gives
arr:
- [srv01, srv02, srv03]
- [srv04, srv05, srv06]
- [srv07, srv08, srv09]
Transpose the matrix
- set_fact:
tarr: "{{ tarr|d(arr.0)|zip(item)|map('flatten') }}"
loop: "{{ arr[1:] }}"
gives
tarr:
- [srv01, srv04, srv07]
- [srv02, srv05, srv08]
- [srv03, srv06, srv09]
Create the list of servers
list_of_servers: "{{ tarr|flatten }}"
gives
list_of_servers: [srv01, srv04, srv07, srv02, srv05, srv08, srv03, srv06, srv09]
Slice the list
- debug:
var: list_of_servers[:5]
gives the first 5 servers
list_of_servers[:5]: [srv01, srv04, srv07, srv02, srv05]
Example of a complete playbook
- hosts: localhost
vars:
servers:
srv01: a
srv02: a
srv03: a
srv04: b
srv05: b
srv06: b
srv07: c
srv08: c
srv09: c
arr: "{{ servers|dict2items|
groupby('value')|
map(attribute=1)|
map('map', attribute='key')|
list }}"
list_of_servers: "{{ tarr|flatten }}"
tasks:
- set_fact:
tarr: "{{ tarr|d(arr.0)|zip(item)|map('flatten') }}"
loop: "{{ arr[1:] }}"
- debug:
var: list_of_servers[:5]
CodePudding user response:
@Vladimir Botka : I copy past your "Example of a complete playbook"
here the result.
fatal: [localhost]: FAILED! => {"msg": "Invalid data passed to 'loop',
it requires a list, got this instead:
<generator object do_map at 0x7fe97cca3900>, <generator object do_map at
0x7fe97cca39e0>, <generator object do_map at 0x7fe97cca3a50>]. Hint: If you
passed a list/dict of just one element, try adding wantlist=True to your
lookup invocation or use q/query instead of lookup."}