Dynamic 'include:' lines?

1,679 views
Skip to first unread message

candlerb

unread,
Oct 17, 2013, 1:25:25 PM10/17/13
to ansible...@googlegroups.com
Using ansible 1.3.3, I am trying to structure my tasks like this:

==> roles/ntp_client/tasks/main.yml <==
- include: "{{ ansible_os_family }}.yml"

==> roles/ntp_client/tasks/Debian.yml <==
- action: apt pkg=ntp state=installed
- service: name=ntp state=started enabled=yes

==> roles/ntp_client/tasks/RedHat.yml <==
- yum: name=ntp state=installed
- service: name=ntpd state=started enabled=yes

It fails with:

ERROR: file not found: /root/ansible/roles/ntp_client/tasks/{{ansible_os_family}}.yml

I also tried:

- include: $ansible_os_family
- include: ${ansible_os_family}.yml

which give:

ERROR: file not found: /root/ansible/roles/ntp_client/tasks/$ansible_os_family
ERROR: file not found: /root/ansible/roles/ntp_client/tasks/${ansible_os_family}.yml

respectively.

What I am trying to avoid is this:

- include: Debian.yml
  when: ansible_os_family == 'Debian'
- include: RedHat.yml
  when: ansible_os_family == 'RedHat'

which works, but is tedious if I have to write it for every role, and it also gives lots of 'skipping' tasks when run.

There is a tiny note at http://www.ansibleworks.com/docs/playbooks_roles.html which says:
"Note that you cannot do variable substitution when including one playbook inside another."
which maybe applies to tasks/roles too - this isn't clear to me.

I could of course define distinct roles called, say:

roles/ntp_client_Debian
roles/ntp_client_RedHat

but to avoid conditionally including them, I would have to make different playbooks for Debian-based hosts and RedHat-based hosts.

Any other suggestions for how to achieve what I want here?

Thanks,

Brian.

Michael DeHaan

unread,
Oct 17, 2013, 1:39:45 PM10/17/13
to ansible...@googlegroups.com
Dynamic includes are not a thing.

Why?  Task objects must be applied to each host in a group set.

This:

- include: Debian.yml
  when: ansible_os_family == 'Debian'
- include: RedHat.yml
  when: ansible_os_family == 'RedHat'



--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.



--
Michael DeHaan <mic...@ansibleworks.com>
CTO, AnsibleWorks, Inc.
http://www.ansibleworks.com/

candlerb

unread,
Oct 17, 2013, 1:53:03 PM10/17/13
to ansible...@googlegroups.com
OK, I found
"You will note a lot of ‘skipped’ output by default in Ansible when using this approach on systems that don’t match the criteria. Read up on the ‘group_by’ module in the modules docs for a more streamlined way to accomplish the same thing."

So I guess this means I can write a playbook like

- hosts: all
  group_by: key=family_{{ansible_os_family}}
- hosts: family_RedHat
  roles: ntp_client_redhat
- hosts: family_Debian
  roles: ntp_client_debian


I also found this:

So, I can abstract the name of the package into a variable (i.e. "ntp" or "ntpd" depending on the os_family); but I don't think I can abstract out whether to call the "apt" or "yum" module. Or can I?

Thanks,

Brian.

Michael DeHaan

unread,
Oct 17, 2013, 2:00:43 PM10/17/13
to ansible...@googlegroups.com
You don't want to abstract out the name of the apt or yum module.

Not only are the package names are always different, they have different capabilities, as we chose to not do the minimal implementation for each.

In fact, many things are also different from OS to OS -- think about how apache is managed so very differently between Ubuntu and Red Hat Enterprise Linux, for instance.

But you really should use group_by, it is your friend :)




--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

candlerb

unread,
Oct 17, 2013, 3:37:51 PM10/17/13
to ansible...@googlegroups.com
> But you really should use group_by, it is your friend :)

Thank you. So here's what my new friend looks like, in a playbook:

---
- hosts: all
  tasks:
    - group_by: key=os_family_{{ ansible_os_family}}
- hosts: os_family_Debian
  roles:
    - role: ntp_client_debian
- hosts: os_family_RedHat
  roles:
    - role: ntp_client_redhat
 
Now the only strange thing is that the "group_by" task is reported as "changed" in yellow. That is, the playbook run looks like this:

PLAY [all] ********************************************************************

GATHERING FACTS ***************************************************************

TASK: [group_by key=os_family_{{ansible_os_family}}] **************************
changed: [dar1.example.com]

PLAY [os_family_Debian] *******************************************************

TASK: [apt pkg=ntp state=installed] *******************************************

TASK: [service name=ntp state=started enabled=yes] ****************************

PLAY [os_family_RedHat] *******************************************************
skipping: no hosts matched

PLAY RECAP ********************************************************************
dar1.example.com    : ok=4    changed=1    unreachable=0    failed=0

I think this might be a bit confusing to the user, as they may think something has actually changed.

Michael DeHaan

unread,
Oct 17, 2013, 4:39:43 PM10/17/13
to ansible...@googlegroups.com
Group by did in fact change the definition of the host temporarily as it ran, but I understand what you are saying.

Can anyone think of a reason why someone would attach a handler to a group_by ?




--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

Brice Burgess

unread,
Oct 17, 2013, 6:35:16 PM10/17/13
to ansible...@googlegroups.com

On Thursday, October 17, 2013 12:39:45 PM UTC-5, Michael DeHaan wrote:
Dynamic includes are not a thing.


Is variable substitution being removed from include lines?

E.g.

- { include: "{{ common_tasks_path}}/deploy_tasks.yml" }

This behavior used to work && will break a lot of our existing playbooks.

Thanks,

~ Brice


Michael DeHaan

unread,
Oct 17, 2013, 6:38:46 PM10/17/13
to ansible...@googlegroups.com
if you pass stuff in with "-e" here it will work fine.

You never could use inventory variables here.




--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

Brice Burgess

unread,
Oct 17, 2013, 7:13:22 PM10/17/13
to ansible...@googlegroups.com
OK. It also worked with vars_files from the base playbook well enough for us in the past && the convenience of defining paths / and re-using common task files is very nice.

It makes sense to force a consistent set of tasks per host group. Will keep this in mind as we refactor.

Michael DeHaan

unread,
Oct 17, 2013, 7:32:11 PM10/17/13
to ansible...@googlegroups.com
vars_files that do not depend on facts are essentially global and fine there, yes.


candlerb

unread,
Oct 18, 2013, 4:39:58 AM10/18/13
to ansible...@googlegroups.com
> Can anyone think of a reason why someone would attach a handler to a group_by ?

To side-step this question, couldn't you just check for the presence of a "notify" clause?

group_by without notify => ok
group_by with notify => changed


Michael DeHaan

unread,
Oct 18, 2013, 8:46:44 AM10/18/13
to ansible...@googlegroups.com
I generally don't like to special case code in the main program like that.

Plus, I'm more interested in the original question :)




--
You received this message because you are subscribed to the Google Groups "Ansible Project" group.
To unsubscribe from this group and stop receiving emails from it, send an email to ansible-proje...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

David Karban

unread,
Oct 18, 2013, 9:32:58 AM10/18/13
to ansible...@googlegroups.com
I personally add changed_when: false.

Personally I haven`t thougth about notyfiing it yet.


2013/10/18 Michael DeHaan <mic...@ansibleworks.com>



--
David Karban
Specialista na správu linuxových serverů
www.karban.eu

Mailo Svetel

unread,
Feb 17, 2016, 9:05:13 PM2/17/16
to Ansible Project
On Ansible 2.0.0.2 I am able to do this:

- include: "{{ansible_os_family | lower}}.yml"




Dne čtvrtek 17. října 2013 19:25:25 UTC+2 candlerb napsal(a):
Reply all
Reply to author
Forward
0 new messages