RH294 Ch 4: Variables, Facts and Magic Variables

Variables let one playbook serve many hosts. Where you define them decides which hosts see them and which value wins.

Places to define variables - Play level: vars: or varsfiles: in the play. - Inventory directories next to the inventory or playbook: groupvars/all.yml, groupvars/dev.yml, hostvars/node1.yml. A host variable beats a group variable, and a child group beats all. - The command line: -e var=value has the highest precedence of all.

ansible-inventory --host node1 shows the variables a host ends up with — a quick way to check your groupvars.

Registered results. register stores a task's return value. For command that includes stdout, stdoutlines, rc and stderr.

yaml - ansible.builtin.command: uname -r register: kernel changedwhen: false - ansible.builtin.debug: msg: "Kernel is {{ kernel.stdout }}"

Facts. At the start of each play, gatherfacts runs the setup module and fills ansiblefacts: ansiblefacts['hostname'], ['fqdn'], ['defaultipv4']['address'], ['distribution'], ['memtotalmb'], ['devices'] and more. Explore them with ansible node1 -m setup (add -a filter=ansibledefaultipv4 to narrow). Set gatherfacts: false when a play does not need them; it saves time.

Custom facts. Put an INI or JSON file ending in .fact in /etc/ansible/facts.d on the managed node. A file webasha.fact with section [app] and name=portal becomes ansiblelocal.webasha.app.name. Executable .fact files are run and must print JSON.

Magic variables are set by Ansible itself: - inventoryhostname: the host name as written in the inventory. - groupnames: the groups the current host belongs to. - groups: every group with its hosts, for example groups['webservers']. - hostvars: all variables and facts of any host, for example hostvars['node2']['ansiblefacts']['defaultipv4']['address']. Facts of another host exist only if they were gathered in this run, so target all when you need everybody's facts.

Common mistakes - Starting a value with {{ without quoting the whole value: msg: "{{ x }}". - Naming a file groupvars/dev for a group that is actually called devs. - Using hostvars[h]['ansiblefacts'] for a host that is not part of the play, which fails with an undefined variable. - Mixing the old ansiblehostname style with ansiblefacts['hostname']; both work, but be consistent.