I am working with Ansible variables. I have this
all.yml
---
port: 9001
inventory.yml
---
group1:
hosts:
server1:
ansible_host: www.server1.com
server2:
ansible_host: www.server2.com
vars:
port: 9002
group2:
hosts:
server5:
ansible_host: www.server5.com
group3:
hosts:
server7:
ansible_host: www.server7.com
I built a playbook, my-playbook.yml
- hosts: localhost
gather_facts: no
tasks:
- name: Netcat server 5
shell: nc -zv {{ hostvars[item].ansible_host }} {{ port }}
with_items: "{{ groups['group2'] }}"
- name: Netcat server 1 only
shell: nc -zv {{ hostvars['server1']['ansible_host'] }} {{ hostvars[item].port }}
with_items: "{{ groups['group1'] }}"
When I run my ansible playbook:
ansible-playbook -i inventory/inventory.yml playbook.yml
I am expecting to do use port 9001
for server5
(which is in all.yml
) and port 9002
for server1
(which is in the inventory).
However, I can see it's grabbing port 9001
for both.
What am I doing wrong?
You are hitting a group precedence problem. Globally, precedence problems in Ansible can get really tricky especially when you are trying to define variables in different places. This is exactly why the documentation states:
We suggest that you define each variable in one place: figure out where to define a variable, and keep it simple. For examples, see Tips on where to set variables.
In the current case, this is one way to solve the problem:
all
file with default_port: 9001
port
will only be present at specific group level (so never put it back inside your all
file) and only defined for groups overriding the default port.- name: Netcat server 5
shell: nc -zv {{ hostvars[item].ansible_host }} {{ port | d(default_port) }}
with_items: "{{ groups['group2'] }}"
- name: Netcat server 1 only
shell: nc -zv {{ hostvars['server1']['ansible_host'] }} {{ hostvars[item].port | d(default_port) }}
with_items: "{{ groups['group1'] }}"
Note if necessary: d
is an alias to default