一、方案概述
1.1 监控原理
- 通过防火墙策略,让不同域名走不同的出口线路
- zabbix 定期访问这些域名,获取访问时的出口ip
- 将获取的ip与预设值比较,不一致时通过飞书发送告警
1.2 线路与域名对应关系示例
| 线路编号 | 域名 | 预设ip | 出口接口 |
|---|---|---|---|
| 线路1 | ifconfig.me | 203.0.113.10 | port2 |
| 线路2 | api.ipify.org | 203.0.113.20 | port3 |
| 线路3 | icanhazip.com | 203.0.113.30 | port4 |
| … | … | … | … |
二、环境准备
2.1 前提条件
- zabbix server 7.4 已部署(docker或物理机)
- 已获取飞书机器人 webhook 地址
- zabbix server 能访问外网(ip查询服务)
2.2 确认zabbix容器名称
docker ps | grep zabbix
记录zabbix server容器名称(如 zabbix-server)
三、部署外部检查脚本
3.1 进入zabbix server容器
docker exec -it zabbix-server sh
3.2 创建脚本目录并编写脚本
# 创建目录
mkdir -p /usr/lib/zabbix/externalscripts
# 创建脚本文件
cat > /usr/lib/zabbix/externalscripts/get_ip_by_domain.sh << 'eof'
#!/bin/bash
# 通过指定的域名获取公网出口ip
# 用法:get_ip_by_domain.sh <域名>
domain="$1"
timeout=5
if [ -z "$domain" ]; then
echo "error: no domain provided"
exit 1
fi
# 使用curl访问域名,提取ipv4地址
ip=$(curl -s -l -m $timeout "http://$domain" 2>/dev/null | grep -eo '([0-9]{1,3}\.){3}[0-9]{1,3}' | head -1)
if [ -n "$ip" ]; then
echo "$ip"
exit 0
else
echo "error: failed to get ip from $domain"
exit 1
fi
eof
# 赋予执行权限
chmod +x /usr/lib/zabbix/externalscripts/get_ip_by_domain.sh
# 修改属主
chown zabbix:zabbix /usr/lib/zabbix/externalscripts/get_ip_by_domain.sh
# 安装curl(alpine系统)
apk add curl3.3 测试脚本
su -s /bin/sh -c "/usr/lib/zabbix/externalscripts/get_ip_by_domain.sh api.ipify.org" zabbix
应返回一个公网ip地址。
3.4 退出容器
exit
四、创建监控项
4.1 登录zabbix web
访问 http://你的zabbix服务器ip:8080,使用 admin/zabbix 登录。
4.2 创建监控项
- 进入 配置 → 主机,选择目标主机(如
hwipmonitor) - 点击 监控项 → 创建监控项
4.3 填写监控项信息
| 字段 | 填写内容 |
|---|---|
| 名称 | wan01 exit ip (via api.ipify.org) |
| 类型 | 外部检查 |
| 键值 | get_ip_by_domain.sh["api.ipify.org"] |
| 信息类型 | 文本 |
| 更新间隔 | 60m |
| 历史记录保留期 | 3d |
4.4 保存
点击 添加 完成创建。
4.5 验证监控项
- 进入 监控 → 最新数据
- 筛选主机,查看监控项是否有数据
- 状态应为 已启用,且有ip值
五、创建触发器
5.1 进入触发器创建
- 配置 → 主机 → 选择主机 → 触发器 → 创建触发器
5.2 填写触发器信息
| 字段 | 填写内容 |
|---|---|
| 名称 | wan01 出口ip异常 (api.ipify.org) |
| 严重性 | 警告 |
| 描述 | 期望ip:103.248.229.101(填写实际预设ip) |
| 表达式 | {hwipmonitor:get_ip_by_domain.sh["api.ipify.org"].last()}<>"103.248.229.101" |
5.3 表达式说明
{主机名:监控项键值.last()}:获取监控项最新值<>"预设ip":不等于预设ip- 如需排除脚本错误,可添加
and {监控项.str(error)}=0
5.4 保存
点击 添加 完成创建。
六、配置飞书媒介
6.1 进入媒介类型配置
管理 → 报警媒介类型 → 创建媒介类型
6.2 填写基本信息
| 字段 | 填写内容 |
|---|---|
| 名称 | feishu |
| 类型 | webhook |
6.3 添加参数
点击 参数 标签页,添加以下参数:
| 名称 | 值 |
|---|---|
subject | {alert.subject} |
message | {alert.message} |
6.4 编写脚本
在 脚本 框中输入以下内容(将webhook地址替换为实际地址):
try {
var params = json.parse(value),
req = new httprequest(),
webhook_url = 'https://open.feishu.cn/open-apis/bot/v2/hook/你的完整webhook地址',
msg = {
msg_type: "text",
content: {
text: params.subject + "\n" + params.message
}
},
resp;
req.addheader("content-type: application/json");
resp = req.post(webhook_url, json.stringify(msg));
if (req.getstatus() != 200) {
throw "response code: " + req.getstatus();
}
resp = json.parse(resp);
return json.stringify(resp);
} catch (error) {
throw "failed with error: " + error;
}6.5 测试媒介
- 点击 测试 按钮
- 填写测试内容:
- subject:
测试告警 - message:
这是一条测试消息
- subject:
- 点击 测试
- 确认飞书群收到测试消息
6.6 保存
点击 添加 完成创建。
七、配置用户媒介
7.1 进入用户配置
管理 → 用户 → 点击 admin (zabbix administrator)
7.2 添加报警媒介
- 点击 报警媒介 标签页
- 点击 添加
- 填写:
- 类型:选择
feishu - 收件人:填写
飞书群(任意标识) - 当活动时:默认
- 严重性:全选
- 启用:勾选
- 类型:选择
- 点击 添加
7.3 保存
点击 更新 保存用户配置。
八、创建动作
8.1 进入动作配置
配置 → 动作 → 触发器动作 → 创建动作
8.2 填写基本信息
| 字段 | 填写内容 |
|---|---|
| 名称 | 出口ip异常飞书告警 |
8.3 配置条件
点击 条件 标签页,添加:
- 类型:触发器名称
- 运算符:包含
- 值:
出口ip异常
这样所有名称包含“出口ip异常”的触发器都会触发此动作。
8.4 配置操作
点击 操作 标签页 → 新增:
| 字段 | 填写内容 |
|---|---|
| 操作类型 | 发送消息 |
| 默认接收人 | 选择 admin (zabbix administrator) |
| 仅送到 | 选择 feishu |
| 主题 | 告警:{trigger.name} |
| 消息 | 主机:{host.name}\n当前ip:{item.lastvalue}\n期望ip:{trigger.description}\n时间:{event.date} {event.time} |
| 自定义持续时间 | 0 |
| 仅当问题出现时发送 | ✅ 勾选 |
8.5 配置恢复操作(可选)
点击 新增 添加恢复操作:
| 字段 | 填写内容 |
|---|---|
| 操作类型 | 发送消息 |
| 默认接收人 | 选择 admin |
| 仅送到 | feishu |
| 主题 | 恢复:{trigger.name} |
| 消息 | 主机:{host.name}\n当前ip:{item.lastvalue}\n时间:{event.date} {event.time} |
| 自定义持续时间 | 0 |
| 仅当问题恢复时发送 | ✅ 勾选 |
8.6 保存
点击 添加 完成动作创建。
九、测试验证
9.1 强制触发测试
临时修改触发器表达式,强制触发告警:
- 配置 → 主机 → 选择主机 → 触发器
- 找到目标触发器,点击编辑
- 将表达式改为:
{hwipmonitor:get_ip_by_domain.sh["api.ipify.org"].last()}<>"1.2.3.4" - 保存
- 等待几秒,进入 监控 → 问题,应看到触发器变为问题状态
- 进入 报表 → 动作日志,查看发送记录
- 检查飞书是否收到告警
9.2 恢复表达式
测试完成后,将表达式改回正确的预设ip。
9.3 验证飞书消息
飞书应收到类似以下内容的消息:
告警:wan01 出口ip异常 (api.ipify.org) 主机:hwipmonitor 当前ip:103.248.229.101 期望ip:期望ip:103.248.229.101 时间:2026.03.30 17:04:23
十、批量配置其他线路
10.1 方法一:手动创建
为每个域名重复以下操作:
- 创建监控项(修改键值中的域名)
- 创建触发器(修改预设ip和域名)
- 触发器名称格式:
wan01 出口ip异常 (域名)
10.2 方法二:使用模板
- 创建一个模板,添加所有监控项和触发器
- 将模板链接到主机
10.3 方法三:使用zabbix api(python脚本)
#!/usr/bin/env python3
import csv
from zabbix_api import zabbixapi
# 配置
zabbix_url = "http://localhost/zabbix"
user = "admin"
password = "zabbix"
host_name = "hwipmonitor"
# 线路配置列表
configs = [
{"domain": "ifconfig.me", "ip": "203.0.113.10"},
{"domain": "api.ipify.org", "ip": "103.248.229.101"},
{"domain": "icanhazip.com", "ip": "203.0.113.30"},
# ... 添加更多
]
zapi = zabbixapi(zabbix_url)
zapi.login(user, password)
# 获取主机id
hosts = zapi.host.get({"filter": {"host": host_name}})
host_id = hosts[0]["hostid"]
for config in configs:
domain = config["domain"]
preset_ip = config["ip"]
# 创建监控项
item = zapi.item.create({
"name": f"wan01 exit ip (via {domain})",
"key_": f'get_ip_by_domain.sh["{domain}"]',
"hostid": host_id,
"type": 0, # 外部检查
"value_type": 1, # 文本
"delay": "60m",
"history": "3d"
})
# 创建触发器
trigger = zapi.trigger.create({
"description": f"wan01 出口ip异常 ({domain})",
"expression": f'{{{host_name}:get_ip_by_domain.sh["{domain}"].last()}}<>"{preset_ip}"',
"priority": 2, # 警告
"comments": f"期望ip:{preset_ip}",
"status": 0
})
print(f"已创建: {domain} -> {preset_ip}")十一、常见问题排查
11.1 监控项显示“不支持”
可能原因:
- 脚本不存在或路径错误
- 脚本没有执行权限
- 缺少curl命令
解决方法:
# 检查脚本是否存在 ls -l /usr/lib/zabbix/externalscripts/get_ip_by_domain.sh # 检查curl是否安装 which curl # 测试脚本 su -s /bin/sh -c "/usr/lib/zabbix/externalscripts/get_ip_by_domain.sh api.ipify.org" zabbix
11.2 飞书收不到消息
可能原因:
- webhook地址错误
- 飞书机器人安全设置(关键词/ip白名单)
- 脚本中url为空
解决方法:
- 在媒介类型中点击测试,确认能收到
- 检查飞书机器人安全设置,添加关键词“告警”
- 确认脚本中webhook地址正确
11.3 动作日志显示“no media defined for user”
解决方法:
- 进入 管理 → 用户,为admin用户添加feishu媒介
- 确认媒介类型已启用
11.4 触发器表达式语法错误
正确格式:
{主机名:监控项键值.last()}<>"预设ip"
常见错误:
- 缺少花括号
{} - ip未加双引号
- 使用中文括号
11.5 查看zabbix server日志
# docker环境 docker logs zabbix-server --tail 100 | grep -i error # 物理机 tail -f /var/log/zabbix/zabbix_server.log
十二、总结
12.1 配置文件清单
| 文件/配置 | 位置 |
|---|---|
| 外部脚本 | /usr/lib/zabbix/externalscripts/get_ip_by_domain.sh |
| 监控项 | zabbix web → 配置 → 主机 → 监控项 |
| 触发器 | zabbix web → 配置 → 主机 → 触发器 |
| 媒介类型 | zabbix web → 管理 → 报警媒介类型 |
| 用户媒介 | zabbix web → 管理 → 用户 |
| 动作 | zabbix web → 配置 → 动作 |
12.2 关键宏说明
| 宏 | 说明 |
|---|---|
{host.name} | 主机名 |
{trigger.name} | 触发器名称 |
{item.lastvalue} | 监控项最新值 |
{trigger.description} | 触发器描述 |
{event.date} | 事件日期 |
{event.time} | 事件时间 |
{alert.subject} | 告警主题 |
{alert.message} | 告警内容 |
12.3 后续优化建议
- 调整检查频率:根据线路重要性,可设置为15-30分钟
- 添加期望ip显示:在触发器描述中填写期望ip
- 配置告警重复间隔:如需重复告警,修改自定义持续时间
- 使用模板:将监控项和触发器放入模板,方便批量管理
- 监控脚本健康:添加监控项监控脚本执行状态
至此,您已完成 zabbix 多线路出口ip监控与飞书告警的全部配置。如有任何问题,欢迎随时交流!
到此这篇关于zabbix 监控多线路出口ip并通过飞书告警完整教程的文章就介绍到这了,更多相关zabbix 监控多线路出口ip内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!
发表评论