DEV Community

Pau Santana
Pau Santana

Posted on

Zabbix configuration as code with zbxctl

If you've used Terraform, Ansible, or ArgoCD, you already know the mental model:

plan → review → apply
Enter fullscreen mode Exit fullscreen mode

Your infrastructure lives in Git.
Changes are reviewed like code.
Drift is visible.
Rollback is a git revert.

So the obvious question becomes:

Why can't Zabbix monitoring work the same way?

It can now, with zbxctl.

The problem with the Zabbix UI

If you manage more than a handful of hosts, you've probably felt the pain:

  • Templates modified directly in the web UI with no audit trail

  • “Who changed that trigger expression?” answered with a shrug

  • Copying templates between environments: export XML, import XML and pray.

  • Onboarding a new engineer means giving them UI access and hoping for the best

The configuration lives in the database, not in your codebase.

It can’t be:

  • reviewed
  • versioned
  • tested

What zbxctl does

zbxctl brings the Terraform mental model to Zabbix.

# See what would change — no writes
zbx plan configs/templates/

# Apply the changes
zbx apply configs/templates/

# See drift between YAML and live Zabbix
zbx diff configs/templates/

# Export an existing template to YAML (migration path)
zbx export template "Linux by Zabbix agent"
Enter fullscreen mode Exit fullscreen mode

Your Zabbix configuration now lives in YAML files in Git.

Engineers review changes as pull requests.
CI validates before deploy.

The Zabbix UI becomes essentially read-only.

Quick start

Install from PyPI:

pip install zbxctl

Set connection details:

export ZABBIX_URL=https://zabbix.example.com
export ZABBIX_USER=Admin
export ZABBIX_PASSWORD=yourpassword
Enter fullscreen mode Exit fullscreen mode

Or use a .env file:

cat > .env << EOF
ZABBIX_URL=https://zabbix.example.com
ZABBIX_USER=Admin
ZABBIX_PASSWORD=yourpassword
EOF
Enter fullscreen mode Exit fullscreen mode

Validate and preview changes:

# Validate config
zbx validate configs/checks/postgresql/

# Plan before applying
zbx plan configs/checks/postgresql/
Enter fullscreen mode Exit fullscreen mode

YAML template format

Example template:

template: postgresql-monitoring
description: "PostgreSQL performance and availability"

items:
  - name: "PostgreSQL: connections used"
    key: pg.connections.used
    interval: 60s
    type: external

  - name: "PostgreSQL: transactions per second"
    key: pg.tps
    interval: 30s

triggers:
  - name: "PostgreSQL: too many connections"
    expression: "last(/postgresql-monitoring/pg.connections.used) > 80"
    severity: warning

  - name: "PostgreSQL: service unavailable"
    expression: "max(/postgresql-monitoring/pg.connections.used,5m) = 0"
    severity: disaster
Enter fullscreen mode Exit fullscreen mode

14 bundled checks

zbxctl ships with production-ready monitoring checks.

Check What it monitors
postgresql Connections, TPS, cache hit ratio, replication lag
redis Memory usage, hit ratio, connected clients
nginx Active connections, request rate
mysql Connections, queries, InnoDB metrics
elasticsearch Cluster health, JVM heap
rabbitmq Queue depth, message rates
haproxy Frontend/backend status
mongodb Connections, operations, replication lag
apache-httpd Active workers, request rate
jvm-jolokia Heap usage, GC time
windows-agent CPU, memory, disk
linux-observability CPU, memory, disk, network

Install a check in seconds:


zbx check install postgresql
zbx apply configs/checks/postgresql/
Enter fullscreen mode Exit fullscreen mode

CI/CD integration

Saved plans allow deployment gating.


# .github/workflows/deploy.yml

- name: Plan
  run: zbx plan configs/ --output zbx.plan.json

- name: Apply
  if: github.ref == 'refs/heads/main'
  run: zbx apply --from-plan zbx.plan.json
Enter fullscreen mode Exit fullscreen mode

The plan file becomes an artifact.

You can:

  • review it in PRs
  • store it in S3
  • require manual approval before apply

Try it locally

The repo includes a Docker environment for testing.

git clone https://github.com/psantana5/zbx.git
cd zbx
docker compose up -d
Enter fullscreen mode Exit fullscreen mode

Wait ~60 seconds, then:


export ZABBIX_URL=http://localhost:8080/zabbix
export ZABBIX_USER=Admin
export ZABBIX_PASSWORD=zabbix
zbx status
zbx plan configs/checks/postgresql/

Enter fullscreen mode Exit fullscreen mode

The bigger picture

zbxctl is intentionally opinionated:

Zabbix configuration belongs in Git.

Once you adopt this workflow:

  • Onboarding becomes git clone + zbx apply
  • Change review becomes a pull request
  • Rollback becomes git revert + zbx apply
  • Environment parity becomes copying a folder

The Zabbix API has always supported this.

zbxctl simply makes it ergonomic.

Links

GitHub

GitHub logo psantana5 / zbx

Zabbix configuration as code — plan, apply, diff your monitoring like Terraform

zbxctl — Zabbix Configuration as Code

PyPI Python Tests License: MIT Zabbix

Manage Zabbix templates, items, triggers and discovery rules through YAML files and Git — the same mental model as Terraform, Ansible or ArgoCD.

pip install zbxctl
Enter fullscreen mode Exit fullscreen mode

zbxctl demo


zbx plan      configs/          See what would change
zbx plan      configs/ --output plan.json   Save plan to file
zbx apply     configs/          Apply changes to Zabbix
zbx apply     --from-plan plan.json         Apply a saved plan (CI/CD gating)
zbx diff      configs/          Compare local config against Zabbix
zbx validate  configs/          Validate YAML schema (no Zabbix connection)
zbx export    linux             Export an existing template to YAML
zbx export    --all             Export every template to configs/templates/
zbx schema                      Print YAML field reference (Markdown or JSON Schema)
zbx scaffold  my-check          Bootstrap a new monitoring check folder
zbx status                      Show connection status and server summary
zbx host list                   List all hosts in Zabbix
zbx host create <host> --ip ... Create a host from the CLI
zbx host delete <host>

PyPI
pip install zbxctl

Supported Zabbix Versions

6.x
7.x
Enter fullscreen mode Exit fullscreen mode

Stars, issues and PRs are very welcome.

Top comments (0)