ansiblecode-duplicationansible-role

What is the best way to deal with Ansible's import_tasks/import_role and "notify"?


Here is a very simple code fragment taken from my "kafka" role:

- import_role:
    name: java
  notify:
    - restart kafka
    - restart zookeeper

Basically I want to install Java running "java" role and when there are changes performed by that role (e.g. Java has been updated), then restart "kafka" and "zookeeper" services. It turns out, Ansible doesn't throw any error as well as not running these handlers specified in "notify" field.

What would be my options to workaround this?

P.S. Java is being installed manually, not from repositories.


Solution

  • I am answering my own question.


    Problem

    I have 3 roles in total:

    Then intention was to run only kafka role and include other ssl and java roles inside kafka role. Like this:

    - import_role:
        name: java
      notify:
        - restart kafka
        - restart zookeeper
    
    - import_role:
        name: ssl
      notify:
        - restart kafka
    

    I've been expecting above code to work, because why not? Ansible did not throw any error regarding this, but silently did not run any handlers...

    Note: both ssl and java are being re-usable roles, used by few other roles/playbooks.


    Workaround

    I've changed my handlers in kafka role into like this:

    - name: restart kafka
      service:
        name: kafka
        state: restarted
      when: "'kafka_all' in group_names"
      listen:
        - restart SSL dependent services
        - restart java dependent services
        - restart kafka & zookeeper services
    
    - name: restart zookeeper
      service:
        name: zookeeper
        state: restarted
      when: "'kafka_all' in group_names"
      listen:
        - restart java dependent services
        - restart kafka & zookeeper services
    
    

    Then changed code in kafka role tasks like this:

    - import_role:
        name: java
    
    - import_role:
        name: ssl
    

    And in both java and ssl role tasks I've added handlers accordingly. Like this for ssl role:

    - name: upload SSL files
      copy:
        src: <hidden>
        dest: <hidden>
      notify: restart SSL dependent services
    

    All above code might not make any sense yet, but familiarize yourself with below key points:

    1. In kafka role I import and not include other roles. It means that imported roles (kafka and ssl) are able to "see" handlers of kafka role. Upstream note.
    2. I am using Ansible's 2.8 new feature called listen. It means tasks can call a specified "listener" and it will automatically calls all listening handlers. If there are no handlers bound to the listener, it will not run anything (and that's expected behavior).
    3. Not so important, but I am using when: "'kafka_all' in group_names" just because I am storing kafka installation tasks in task file install.yml and I specified there notify: restart kafka & zookeeper services and the thing is - I want to install Kafka on server where I want Kafka as a service as well as on server where I want to have Kafka CLI tools only (so no services are started). Such server won't be part of kafka_all and eventually these handlers won't be executed.