One of the lesser-known but extremely useful features of Ansible is the ability to use custom facts. In this post, we’ll explore what custom facts are, how to create them, and provide a practical example to help you get started.
What are Ansible Custom Facts?
Ansible facts are pieces of information about remote systems that Ansible collects when it runs a playbook. These facts include details such as IP addresses, OS versions, and hardware information. Custom facts allow you to extend this functionality by defining your own facts to meet your specific needs. These can be particularly useful for setting environment-specific variables or for custom configuration management tasks.
How to Use Ansible Custom Facts
Custom facts in Ansible are typically written in JSON or INI format and placed in specific directories on the remote systems. Here’s a step-by-step guide on how to create and use custom facts in Ansible:
- Create the Template (
custom.fact.j2
) in thetemplates
directory.
templates/custom.fact.j2
{
"environment": "{{ my_env }}",
"application_version": "1.2.3",
"datacenter": "us-west"
}
- Deploy the
custom.fact
file using the template and make sure that the facts directory exists.
Create a playbook that uses the my_env
variable and the template file to generate and copy the custom.fact
file to the appropriate hosts, ensuring that the directory /etc/ansible/facts.d
exists.
Playbook (deploy_custom_facts.yml)
---
- name: Deploy custom facts
hosts: all
become: yes # Enable privilege escalation
vars:
my_env: "{{ my_env }}"
tasks:
- name: Ensure facts directory exists
file:
path: /etc/ansible/facts.d
state: directory
mode: '0755'
- name: Create custom fact from template
template:
src: templates/custom.fact.j2
dest: /etc/ansible/facts.d/custom.fact
mode: '0644'
Access the Custom Facts: Once the custom facts are deployed, you can access them in your playbooks using the ansible_local
variable. Here’s an example playbook that uses the custom facts:
Playbook (facts_playbook.yml)
---
- name: Use custom facts
hosts: all
tasks:
- name: Print custom facts
debug:
msg: "Environment: {{ ansible_local.custom.environment }}, Application Version: {{ ansible_local.custom.application_version }}, Datacenter: {{ ansible_local.custom.datacenter }}"
- name: Show Custom Fact in hostvars
debug:
msg: "{{ hostvars[ansible_hostname].ansible_local.custom.environment }}"
Example:
- Deploying custom facts:
Assuming that we are going to deploy the custom fact on the hosts in the ubuntu group and the environment is “development“:
$ ansible-playbook -i hosts -l ubuntu deploy_custom_facts.yml -e my_env=development
PLAY [Deploy custom facts] **********************************************************************************************************************************************************
TASK [Gathering Facts] **************************************************************************************************************************************************************
ok: [ubuntu1]
ok: [ubuntu3]
ok: [ubuntu2]
TASK [Ensure facts directory exists] ************************************************************************************************************************************************
changed: [ubuntu1]
changed: [ubuntu2]
changed: [ubuntu3]
TASK [Create custom fact from template] *********************************************************************************************************************************************
changed: [ubuntu1]
changed: [ubuntu2]
changed: [ubuntu3]
PLAY RECAP **************************************************************************************************************************************************************************
ubuntu1 : ok=3 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
ubuntu2 : ok=3 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
ubuntu3 : ok=3 changed=2 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
- Showing custom facts:
$ ansible-playbook -i hosts -l ubuntu facts_playbook.yml
PLAY [Use custom facts] *************************************************************************************************************************************************************
TASK [Gathering Facts] **************************************************************************************************************************************************************
ok: [ubuntu2]
ok: [ubuntu3]
ok: [ubuntu1]
TASK [Print custom facts] ***********************************************************************************************************************************************************
ok: [ubuntu1] => {
"msg": "Environment: development, Application Version: 1.2.3, Datacenter: us-west"
}
ok: [ubuntu2] => {
"msg": "Environment: development, Application Version: 1.2.3, Datacenter: us-west"
}
ok: [ubuntu3] => {
"msg": "Environment: development, Application Version: 1.2.3, Datacenter: us-west"
}
TASK [Show Custom Fact 1 in hostvars] ***********************************************************************************************************************************************
ok: [ubuntu1] => {
"msg": "development"
}
ok: [ubuntu2] => {
"msg": "development"
}
ok: [ubuntu3] => {
"msg": "development"
}
PLAY RECAP **************************************************************************************************************************************************************************
ubuntu1 : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
ubuntu2 : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
ubuntu3 : ok=3 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0