Deploying the Zabbix Monitoring Agent
Establish the required directory hierarchy within the Salt base environment to separate system initialization tasks from application-specific configurations.
mkdir -p /srv/salt/base/{init/zabbix_epel,zabbix_agent/templates}
Configure the EPEL repository to ensure dependency resolution works correctly. Download the repository definition, place it in the designated files directory, and reference it in a state file.
cat > /srv/salt/base/init/zabbix_epel/repo_setup.sls << 'EOF'
epel_repository:
file.managed:
- name: /etc/yum.repos.d/epel.repo
- source: salt://init/zabbix_epel/files/epel-7.repo
- user: root
- group: root
- mode: '0644'
EOF
Prepare the Zabbix agent configuration template. Utilize Jinja variables to dynamically inject the monitoring server address and client hostname during deployment, replacing static entries.
sed -i 's/^Server=.*/Server={{ MONITOR_HOST }}/' /srv/salt/base/zabbix_agent/templates/zabbix_agentd.conf.j2
sed -i 's/^Hostname=.*/Hostname={{ CLIENT_FQDN }}/' /srv/salt/base/zabbix_agent/templates/zabbix_agentd.conf.j2
The deployment state handles RPM installation, package resolution, configuration templating, and service management in a sequential execution chain.
cat > /srv/salt/base/zabbix_agent/deploy.sls << 'EOF'
install_zabbix_release:
file.managed:
- name: /tmp/zabbix-release-4.0-2.el7.noarch.rpm
- source: salt://zabbix_agent/files/zabbix-release-4.0-2.el7.noarch.rpm
- makedirs: True
cmd.run:
- name: rpm -ivh /tmp/zabbix-release-4.0-2.el7.noarch.rpm --force
- require:
- file: install_zabbix_release
setup_zabbix_agent:
pkg.installed:
- name: zabbix-agent
- require:
- cmd: install_zabbix_release
configure_zabbix_agent:
file.managed:
- name: /etc/zabbix/zabbix_agentd.conf
- source: salt://zabbix_agent/templates/zabbix_agentd.conf.j2
- user: zabbix
- group: zabbix
- mode: '0644'
- template: jinja
- defaults:
MONITOR_HOST: 192.168.5.18
CLIENT_FQDN: {{ grains['fqdn'] }}
- require:
- pkg: setup_zabbix_agent
start_zabbix_agent:
service.running:
- name: zabbix-agent
- enable: True
- watch:
- file: configure_zabbix_agent
- pkg: setup_zabbix_agent
EOF
Validate the configuration syntax before applying changes to a target minion:
salt 'node-1' state.sls zabbix_agent.deploy test=True
salt 'node-1' state.sls zabbix_agent.deploy
Provisioning Redis Instances
For production workloads, switch to the prod Salt environment. Organize the module structure to support scalable service orchestration.
mkdir -p /srv/salt/prod/{modules/redis,redis_cluster/templates}
Create a foundatoinal state to ensure the Redis package is available across all target hosts.
cat > /srv/salt/prod/modules/redis/base_install.sls << 'EOF'
redis_package:
pkg.installed:
- name: redis
EOF
Define the master node orchestration state. This file extends the base installation, applies a customized configuration template, and ensures the service is active and persistent across reboots.
cat > /srv/salt/prod/redis_cluster/master_node.sls << 'EOF'
include:
- modules.redis.base_install
apply_redis_config:
file.managed:
- name: /etc/redis.conf
- source: salt://redis_cluster/templates/redis_master.conf.j2
- user: redis
- group: redis
- mode: '0644'
- template: jinja
- defaults:
MAX_RAM_LIMIT: 100M
LISTEN_PORT: 6001
NODE_IPV4: {{ grains['fqdn_ip4'][0] }}
- require:
- pkg: redis_package
enable_redis_service:
service.running:
- name: redis
- enable: True
- watch:
- file: apply_redis_config
EOF
The accompanying configuration template strips unnecessary comments and maps critical parameters to the Jinja variables defined in the state file.
cat > /srv/salt/prod/redis_cluster/templates/redis_master.conf.j2 << 'EOF'
bind {{ NODE_IPV4 }}
protected-mode yes
port {{ LISTEN_PORT }}
tcp-backlog 511
timeout 0
tcp-keepalive 300
daemonize yes
supervised no
pidfile /var/run/redis_6001.pid
loglevel notice
logfile /var/log/redis/redis.log
databases 16
save 900 1
save 300 10
save 60 10000
stop-writes-on-bgsave-error yes
rdbcompression yes
rdbchecksum yes
dbfilename dump.rdb
dir /var/lib/redis
slave-serve-stale-data yes
slave-read-only yes
repl-diskless-sync no
repl-diskless-sync-delay 5
repl-disable-tcp-nodelay no
slave-priority 100
maxmemory {{ MAX_RAM_LIMIT }}
appendonly no
appendfilename "appendonly.aof"
appendfsync everysec
no-appendfsync-on-rewrite no
auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb
aof-load-truncated yes
lua-time-limit 5000
slowlog-log-slower-than 10000
slowlog-max-len 128
latency-monitor-threshold 0
notify-keyspace-events ""
hash-max-ziplist-entries 512
hash-max-ziplist-value 64
list-max-ziplist-size -2
list-compress-depth 0
set-max-intset-entries 512
zset-max-ziplist-entries 128
zset-max-ziplist-value 64
hll-sparse-max-bytes 3000
activerehashing yes
client-output-buffer-limit normal 0 0 0
client-output-buffer-limit slave 256mb 64mb 60
client-output-buffer-limit pubsub 32mb 8mb 60
hz 10
aof-rewrite-incremental-fsync yes
EOF
Because the state resides in the production environment rather than the default base directory, explicitly declare the saltenv parameter during execution.
salt 'node-1' state.sls redis_cluster.master_node saltenv=prod test=True
salt 'node-1' state.sls redis_cluster.master_node saltenv=prod