EDA examples
As most sites, I will show you a simple eda project and a more complex one.
Lets start simple
The project is built using ansible (obviously), but created in a way that is can be loaded and adpated by configurationa s code.
The goal of the project is to check my webservers in the development environment and my production webservers with the same rulebook project.
the project structure:
.
├── collections
│ └── requirements.yml
├── rulebooks
│ └── check_website_yml
├── restart_server.yml
└── README.md
As You can see, I placed the rulebook and the playbook to call in the same repository, this means that this 'project' must be defined in controller_projects as in eda_projects.
Additionally, the playbook restart_server.yml must be configured as a 'job_template' to call from the rulebook.
So it would make sense, keeping this together in one repository and one organization.
collections/requirements.yml
This file contains the required collections for the playbook to run:
---
collections:
- infra.aap_configuration
- community.proxmox
As I am using proxmox as my virtualization platform, obviously the community.proxmox is in there.
rulebooks/check_website.yml
This is the rulebook checking my webservers:
---
- name: Monitor the websites
hosts: localhost
sources:
- ansible.eda.url_check:
urls: "{{ check_urls }}"
delay: 30
rules:
- name: Start Nginx server if the status is down
condition: event.url_check.status == "down"
action:
run_job_template:
name: "{{ template_to_run }}"
organization: "{{ template_org }}"
As you can see, this rulebook cannot run without the variables:
check_urls: a list of webserver urls to check every 30 seconds, the urls have the following format:
- http://webserver1.dev.lab:8080
- http://webserver2.dev.lab:8080
So basicly hostname and port number.
template_to_run: The name of the job_template to run when a server is down.
template_org: The name of the organization the template is in.
The use of these variables is shown in the documentation of eda in configuration as code rhaap 2.6.
In this rulebook we caal upon the restart_server job_template, the playbook is found in this same project:
restart_server.yml
Needless to say that you must have execute rights on this template to run it.
This example is rather simple you define a check and the take action when the check fails, but what if you have to define 150- or more checks? This is where monitoring comes in..
A more complex example
For this next example, we wil use alertmanager and we will feed the alertmanager from grafana.
Monitoring and generating events with grafana is rather easy and well documented.
So we willl pickup the story after the defenition of the events, and for most the struggle begins...
For this we will need a alertmanager instance, you can run this on docker or in a very small alpine container in proxmox.
We chose for a small linux container on proxmox, this consumes less resources than a VM with docker.
Install alertmanager
For alertmanager to run on a linux server:
login as root on the container machine
wget https://github.com/prometheus/alertmanager/releases/download/v0.24.0/alertmanager-0.24.0.linux-amd64.tar.gz
tar xvzf alertmanager-0.24.0.linux-amd64.tar.gz
This installs alertmanager on your system, now we need to configure an run it when the machine boots.
edit the file alertmanager.yml in the folder /root/alertmanager-0.24.0.linux-amd64
route:
group_by: [ alertname ]
receiver: 'EDA' # default receiver
repeat_interval: 24h
routes:
receivers:
- name: 'EDA'
webhook_configs:
- url: 'http://<your-rhaap-fqdn>:9000/alerts'
This configuration will send all alerts to the same EDA port and you'll need to filter in EDA which playbook to run on which event.
The webhook_configs url here, is the listener you create in your rulebook for alertmanager.
This will enable alertmanager to send the incoming alerts to the EDA instance.
A somewhat more advanced configurtation is this:
route:
group_by: [ alertname ]
receiver: 'EDA' # default receiver
repeat_interval: 24h
group_wait: 5s
routes:
- matchers:
- alertname="nginx-server-up-down"
receiver: 'webserver-status'
continue: true
group_wait: 10s
- matchers:
- alertname="proxmox-guest-mem-usage"
receiver: 'guest-overload'
continue: true
group_wait: 30s
- matchers:
- alertname="proxmox-guest-cpu-usage"
receiver: 'guest-overload'
continue: true
group_wait: 30s
- matchers:
- alertname="proxmox-guest-disk-usage"
receiver: 'guest-disk'
continue: true
group_wait: 30s
- receiver: 'telegram'
group_wait: 5s
receivers:
- name: 'webserver-status'
webhook_configs:
- url: 'http://rhaap26.homelab:9000/alerts'
- name: 'guest-overload'
webhook_configs:
- url: 'http://rhaap26.homelab:9001/alerts'
- name: 'guest-disk'
webhook_configs:
- url: 'http://rhaap26.homelab:9002/alerts'
- name: 'telegram'
telegram_configs:
- bot_token: <token>
api_url: https://api.telegram.org
chat_id: <chat_id>
parse_mode: ''
This configuration will send different alerts to separate ports on the automation platform EDA thus having much more
control over what is handled where. Lastly all event notifications are sent to a telegram chat, so we know what is
happening and we can check that events are beeing handled.
The timing is that the event is first sent to telegram, this can be changed later, to only send an alert if it is not handled.
The link to configure telegram Telegram notifications.
Now we need to start alertmanager on every reboot. Creating a service file and ad the service to the startup of the system and it will be started after every boot. .
The poormans way to do this, is to create a startscript and add this to crontab:
The script:
#!/bin/sh
cd /root/alertmanager-0.24.0.linux-amd64
nohup ./alertmanager > /dev/null 2>&1 &
A simple script that will start the alertmanager without any logging.
Add this line to crontab to start the script after every boot:
@reboot /bin/sleep 10 ; /root/start_alert.sh
We wait for 10 seconds before starting alertmanager, as we would have no network yet.
With a service, we wouldn't have this problem.
As an example, the following event from alertmanager is routed to EDA.
alert:
annotations:
__orgId__: '1'
__value_string__: >-
[ var='A' labels={id=lxc/1002, name=web01.dev.lab} value=0.86285400390625
], [ var='C' labels={id=lxc/1002, name=web01.dev.lab} value=1 ]
__values__: '{"A":0.86285400390625,"C":1}'
endsAt: '0001-01-01T00:00:00Z'
fingerprint: bf94732181d7c640
generatorURL: http://localhost:3000/alerting/grafana/beot9sm6tqhhcf/view
labels:
__alert_rule_uid__: beot9sm6tqhhcf
__grafana_autogenerated__: 'true'
__grafana_receiver__: grafana-alertmanager
alertname: proxmox-guest-mem-usage
grafana_folder: proxmox
id: lxc/1002
name: web01.dev.lab
startsAt: '2026-03-10T12:04:10Z'
status: firing
Configure EDA
When we have alertmanager and grafana configured to send events to EDA, we can start the rulebook
First we add the rulebook project to EDA.
When the project is added, we can create a rulebook activation.
- name: Test Ruleset for Alerts from Grafana
hosts: localhost
sources:
# Set the receiver in alert manager to the ip of the EDA host with port 9000
# This will install a listener on this port and is the target for the route in
# alertmanager.yml
- name: listen for alertmanager alerts
ansible.eda.alertmanager:
host: 0.0.0.0
port: 9000
rules:
- name: Alert default action
condition: event.alert.status == 'firing'
action:
run_job_template:
name: EDA_grafana_handle_alerts
organization: ORG_EDA
This starts a playbook on the automation platform instance and passes the full alert info to the playbook in the variable ansible_eda_event. Using the event information, you can take the correct action for this event.
The condition in this example is very simple, just fire up the playbook..
If you use the more advanced alertmanager configuration, you'll need more rulebooks in EDA.