# how to have general playlist call specific playlist and/or roles?

**URL:** <https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188>\
**Category:** Ansible Project\
**Created:** [May 7, 2014, 5:27pm UTC](https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188 "2014-05-07T17:27:41Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![chris\_snyder](https://avatars.discourse-cdn.com/v4/letter/c/7c8e57/32.png) [@chris\_snyder](https://forum.ansible.com/u/chris_snyder)\
**Post date:** [May 7, 2014, 5:27pm UTC](https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188/1 "2014-05-07T17:27:41Z")

</div>

I’m having a really hard time wrapping my head around how to organize my plays and roles with Ansible.

What I have:

I have multiple Linux distros I need to support with Ansible. Each distro has different requirements which manifest themselves as different playbooks/roles/tasks/host groups.

What I want (i.e. this is what my brain is telling me _ **SHOULD** _ be the correct solution for this type of situation. And yes, I _ **DO** _ have a programmer back ground):

Call a single, general Ansible playbook that determines the specific distro/host on client host and then executes a more specific playbook and/or set of roles for my target host or host group.

What I don’t want to do:

- I don’t want to have to programmatically determine the distro of my target host BEFORE calling Ansible so I can pass some OS-specific playbook name to Ansible on the command line for specific host or groups of hosts.

- I don’t want a SINGLE playbook which contains plays for all the OS’s I support – that’s just too large and unwieldy.

Obviously, Ansible doesn’t parse variables as part of include statements, but IDEALLY, the following example is how I feel I should be solving my problem:

- hosts: all

Tasks:

- name: Determine distrbution name and release

set\_fact: myos=“{{ansible\_distribution|lower}}{{ansible\_lsb.major\_release}}”

- name: Group hosts by distro and release

action: group\_by key={{myos}}

- hosts: {{myos}}

Roles:

- {{myos}}

So, how do other people solve/organize their solutions to problems similar to this?

Thx

Chris.

---

<div class="post-metadata">

**Author:** ![James\_Cammarata](https://avatars.discourse-cdn.com/v4/letter/j/7c8e57/32.png) [@James\_Cammarata](https://forum.ansible.com/u/James_Cammarata)\
**Post date:** [May 7, 2014, 6:48pm UTC](https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188/2 "2014-05-07T18:48:53Z")

</div>

This will not work, since the hosts and roles must be known at the time the playbook is read, so you can’t do variable substitutions on those.

An alternative to this method is to have just the one role that includes different task files based on the values of the system facts. See [https://github.com/ansible/ansible/blob/devel/test/integration/roles/test\_apt/tasks/main.yml](https://github.com/ansible/ansible/blob/devel/test/integration/roles/test_apt/tasks/main.yml) for example of how we limit the apt test to running on certain distributions. This way, you can keep common tasks together while only splitting out the distro-specific pieces.

This way, you could do the following:

- hosts: all  
roles:
- { role: do\_distro\_stuff, target\_os: “{{ansible\_distribution|lower}}{{ansible\_lsb.major\_release}}” }

and then in roles/do\_distro\_stuff/main.yml:

# includes for distro-version specific tasks

- include: ‘ubuntu12.yml’  
when: target\_os == ‘ubuntu12’
- include: ‘ubtunu14.yml’  
when: target\_os == ‘ubuntu14’

# …

# and then do common tasks here

So you’d have to add new lines there when new distros come out, but that’s not something that occurs frequently so it’s not a major concern.

---

<div class="post-metadata">

**Author:** ![chris\_snyder](https://avatars.discourse-cdn.com/v4/letter/c/7c8e57/32.png) [@chris\_snyder](https://forum.ansible.com/u/chris_snyder)\
**Post date:** [May 8, 2014, 2:36pm UTC](https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188/3 "2014-05-08T14:36:08Z")

</div>

Thanks for this example. I’m still pondering over this and it’s possibilities but I’m thinking that I’m probably going to have to rip out a lot of the roles I’ve already defined and make them into task files called from more general roles unless I do a lot of explicit ‘when’ statements for calling roles in my playbooks.

Or maybe not. I’m still trying to get my head around of it.

---

<div class="post-metadata">

**Author:** ![Adam\_Morris](https://avatars.discourse-cdn.com/v4/letter/a/ecae2f/32.png) [@Adam\_Morris](https://forum.ansible.com/u/Adam_Morris)\
**Post date:** [May 8, 2014, 8:58pm UTC](https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188/4 "2014-05-08T20:58:26Z")

</div>

Here’s the top of my site.yml

# file: site.yml

# Set up groups automatically for OS

- include: group.yml

# Perform a basic server configuration

- include: checklist.yml

The group.yml looks like this…

---

<div class="post-metadata">

**Author:** ![Michael\_DeHaan1](https://avatars.discourse-cdn.com/v4/letter/m/5e9695/32.png) [@Michael\_DeHaan1](https://forum.ansible.com/u/Michael_DeHaan1)\
**Post date:** [May 9, 2014, 11:53pm UTC](https://forum.ansible.com/t/how-to-have-general-playlist-call-specific-playlist-and-or-roles/15188/5 "2014-05-09T23:53:53Z")

</div>

set\_fact shouldn’t be needed for basic variable concation. You can actually just define a variable that references the other two variable names and it will work

vars:  
“myos” : “{{ ansible\_os\_family }}-{{ other }}”

etc.

Another handy trick to include distro specific variables is:

tasks:

- include\_vars: “{{ ansible\_os\_family }}.yml”
