How to split an ansible role's `defaults/main.yml` file into multiple files?
The feature I'm describing below has been available since Ansible 2.6, but got a bugfix in v2.6.2 and another (minor) one in v2.7.
To see a solution for older versions, see Paul's answer.
defaults/main/
Instead of creating defaults/main.yml
, create a directory — defaults/main/
— and place all YAML files in there.
defaults/main.yml
→defaults/main/*.yml
Ansible will load any *.yml
file inside that directory, so you can name your files like roles/my-role/defaults/main/{1,2}.yml
.
Note, the old file — defaults/main.yml
— must not exist. See this Github comment.
vars/main/
By the way, the above solution also works for vars/
:
vars/main.yml
→vars/main/*.yml
further details
The feature has been introduced in v2.6 — git commit, Pull Request, main Github issue.
There have been two bugfixes:
- v2.7 fix: git commit, Pull Request — backported to v2.6.2: commit, Pull Request
- v2.7 fix: git commit, Pull Request, bug discussion
If you aren't using 2.6 (which you probably should, but I understand that isn't always an option), then you might find include_vars useful.
- name: Include vars of stuff.yaml into the 'stuff' variable (2.2).
include_vars:
file: stuff.yaml
name: stuff
- name: Conditionally decide to load in variables into 'plans' when x is 0, otherwise do not. (2.2)
include_vars:
file: contingency_plan.yaml
name: plans
when: x == 0
- name: Load a variable file based on the OS type, or a default if not found. Using free-form to specify the file.
include_vars: "{{ item }}"
with_first_found:
- "{{ ansible_distribution }}.yaml"
- "{{ ansible_os_family }}.yaml"
- default.yaml
- name: Bare include (free-form)
include_vars: myvars.yaml
- name: Include all .json and .jsn files in vars/all and all nested directories (2.3)
include_vars:
dir: vars/all
extensions:
- json
- jsn
- name: Include all default extension files in vars/all and all nested directories and save the output in test. (2.2)
include_vars:
dir: vars/all
name: test
- name: Include default extension files in vars/services (2.2)
include_vars:
dir: vars/services
depth: 1
- name: Include only files matching bastion.yaml (2.2)
include_vars:
dir: vars
files_matching: bastion.yaml
Note that this is a task directive, though. It isn't as neat as just being able to include it into the defaults file itself.