Trigger Actions with Handlers
Restarting a service every time a playbook runs is inefficient and causes unnecessary downtime. Handlers solve this: they are special tasks that only execute when another task reports a "changed" state.
Why Use Handlers?
If you update an Apache configuration file or replace an index.html, the Apache service needs to be restarted to apply the changes. But if the file hasn't changed, restarting the service is a waste of time and drops active connections.
How it Works
You add the notify directive to any standard task. If that task results in a changed state (e.g., a file was actually modified or a package was newly installed), it sends a signal to a corresponding handler by name.
The Apache Handler Playbook
---
- name: install apache using handler
hosts: localhost
become: yes
tasks:
- name: install apache
apt:
name: apache2
state: present
notify: Restart apache
- name: copy file
copy:
src: index.html
dest: /var/www/html
notify: Restart apache
- name: restart service
service:
name: apache2
state: started
enabled: true
handlers:
- name: Restart apache
service:
name: apache2
state: restartedThe Execution Flow
What happens when you run this?
- 1. Install Ansible ensures
apache2is installed. If it has to download it, it registers a "changed" state and queues the Restart apache handler. - 2. Copy Ansible copies
index.html. If the file is different from what's on the server, it queues the handler again. - 3. Start Ansible simply ensures the service is currently running and enabled on boot.
- 4. Handlers Flush At the very end of the play, Ansible looks at the queue. It sees the Restart apache handler was notified, and executes it exactly once.
terminal output
$ ansible-playbook deploy_apache.yml
TASK [install apache] *************************************
ok: [localhost]
TASK [copy file] ******************************************
changed: [localhost]
TASK [restart service] ************************************
ok: [localhost]
RUNNING HANDLER [Restart apache] **************************
changed: [localhost]