Avoid conflicting roles on same machine

Hi

I have 4 roles, nginx, apache, kibana and grafana.

The kibana role has a requirement to the nginx role and grafana role has a requirement of the apache role.
Since both nginx and apache uses the same port numbers 80 and 443, they are in conflict with each other and can't run on the same host.
This also means the kibana and grafana roles can't be on the same host.

Is there a way in Ansible to make sure it fails, ideally before any changes has been made, if they are included in the same playbook on the same host?

You could probably do something clever with setting vars and when: clauses,
but I'm not sure how that will help you; you still won't have a
working play right?

At the end of the day Ansible is a force multiplier for you to compose
systems with.
I've run kibana and grafana (the html5 versions, anyway) perfectly well on
both apache and nginx, why not just change the roles?

You could probably do something clever with setting vars and when: clauses,
but I'm not sure how that will help you; you still won't have a
working play right?

I would like the play to fail, so the user get a message that the roles is in conflict with each other.
So I could set a fact in a apache role and check if it exist in nginx and vice versa, and fail if it's defined.
It will at least give the user a message, but not before some changes has been done on the host.

At the end of the day Ansible is a force multiplier for you to compose
systems with.
I've run kibana and grafana (the html5 versions, anyway) perfectly well on
both apache and nginx, why not just change the roles?

I need some auditing for searches made with Kibana and Kibana uses POST.
Reliable and good POST logging with Apache is not easy but very easy to do in Nginx.

All other roles uses Apache, reason for this is that Kerberos, Singel Sign On and LDAP is very easy to implement in Apache, not so easy in Nginx.

Fair enough - I'll be honest, I thought you might have been
overthinking your problem
but I can see how a safety net might help you. especially if you're
writing roles for others
to use.

In that case I'd do something lightweight, like setting
a 'no_nginx' var/fact in the apache role, which your nginx role checks for
and causes it to skip/fail with an error. It's not _too_ ugly and it's
isolated to
the role.

I've done ugly conditionals in our main playbook before now using conditional
roles/includes

( see http://docs.ansible.com/ansible/playbooks_conditionals.html#applying-when-to-roles-and-includes
)

- we usually used this in cases where we were replacing some components across
  several environments over a course of weeks, but still wanted to use
a single site.yml
  to manage the environments. Rather than adding conditional logic to
all our old roles we wrote new
  ones and set vars in each environments inventory to selectively
enable roles in the play.
  Once it was on live, we just replaced the old role with the new one
and took out all the conditional logic.

Like I said, not my proudest coding achievement but it was gone in the
next commit :slight_smile: