Ansible – Structuring your playbooks


In this series of blog posts, I will be talking about Ansible. Ansible is a powerful automation tool that you can learn quickly.

Ansible is very flexible. When starting you will most likely do everything in a single .yaml file. As things get more complex, it becomes very useful to start separating things out into files and folders. There are several ways to do this and some recommendations from Ansible about the recommended ways of going about this.

The simplest way is to just include another file, for example:

tasks:

  - include: tasks/foo.yml

There are much better ways to structure your files though. If you head over to the Ansible website there is some best practices which are very good. It can be a bit confusing at first digesting all of the recommendations at once, so I will attempt to explain what I have found the most useful.

http://docs.ansible.com/ansible/playbooks_best_practices.html

For starters if you name folders in a particular way in your playbook directory, Ansible will automatically discover them and allow you to use them in your playbook. The most useful usage of this is if you have a common set of instructions that would would run on all of your machines. If you create a folder called roles in and then inside create a folder called common,

roles
└── common
    ├── handlers
    │   └── main.yml
    └── tasks
        └── main.yml

Then inside your main playbook you can just list the role that you just created and it will run for that particular host:

---
- hosts:
    - web
  roles:
    - common

For a recent playbook I built, I my directory structure looks like the one below. For all of my hosts I ran the common script and then on the other hosts I picked and chose the roles I needed for them. This also makes it easy to write a common setup role that you could share across playbooks.

roles
├── admin
│   └── tasks
│       └── main.yml
├── common
│   ├── handlers
│   │   └── main.yml
│   └── tasks
│       └── main.yml
├── edit
│   └── tasks
│       └── main.yml
└── mongodb
    └── tasks
        └── main.yml

As you can see, this offers you many benefits. It makes your playbooks easier to read and maintain. Splitting up your playbook also allows you to pick and choose roles that you would like to run on a particular server.