微信报警
微信报警原理流程
注册微信企业号,通过企业号提供的信息ID、以及获取微信的API接口,就可以将服务器的报警数据,发给API,发给微信,发给关注这个公众号的所有用户。
url 访问,拿人家这个url数据,是什么http method? ------get
bilibili.com/login
给这个url发请求,切提交你的账户密码http method---post
如何把你的zabbix数据,提交到微信这里
API(应用程序的接口)
(微信会提供一个URL给你,往这个URL发送http请求,post类型的请求,提交你的zabbix采集到的数据)
微信的服务器收到了你的请求,且,你这个请求,包含了如下内容
- 发给谁,具体的企业微信ID号3
- 发送的标题,正文等数据
待会来看,如何发请求,且构造这些数据,
微信这里再把这些数据,发送你们的微信工作组(企业ID号)
3.以及获取微信的API接口,就可以将服务器的报警数据,发给API
4.发给微信,发给关注这个公众号的所有用户、这个组内的成员都收到消息了
微信中创建的zabbix应用的secret密钥
你注册的企业微信的id
注册企业微信
https://work.weixin.qq.com/wework_admin/frame
修改通讯录组名
创建自定义zabbix应用
.查看企业ID
微信报警架构图逻辑图
添加通信群组成员
想让其他人也加入到这个组,便于接收消息,因此需要邀请加入组。
扫码加入企业
加入监控小分队即可。
分组的组ID
关注监控公众号(无须下载企业微信了)
至此,微信的设置就结束了
刚才已经完成了,创建企业微信的账号,获取了企业号的id,以及创建了企业微信的一个zabbix小程序,获取了程序的id,和密钥
接下来就是zabbix客户端的事了
下一步就来看,python,和bash两个风格的脚本,发请求。
推送报警信息(python)
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]# vim weixin_zabbix.py
#!/usr/bin/env python3
# Author: www.haloyang.top
import requests
import sys
import os
import json
import logging
# 日志格式构造
logging.basicConfig(level = logging.DEBUG, format = '%(asctime)s, %(filename)s, %(levelname)s, %(message)s',
datefmt = '%a, %d %b %Y %H:%M:%S',
filename = os.path.join('/tmp','weixin_python.log'),
filemode = 'a')
# 企业ID
corpid='ww76b67c7e3bea'
# 应用秘钥
appsecret='Z2LpWY2H15svWZXuXAzyxqCuGUWrDPKhhHvvnY'
# 应用id
agentid=1000002
# 获取身份令牌,用于和微信通信的认证
# 参考企业微信API文档https://developer.work.weixin.qq.com/document/path/90487
token_url='https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=' + corpid +'&corpsecret=' + appsecret
req=requests.get(token_url)
accesstoken=req.json()['access_token']
msgsend_url='https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=' + accesstoken
# 构造消息体
#touser=sys.argv[1]
toparty=sys.argv[1]
subject=sys.argv[2]
# 发送微信消息的数据格式
message=sys.argv[2] + "\n\n" +sys.argv[3]
params={
#"touser": touser,
"toparty": toparty,
"msgtype": "text",
"agentid": agentid,
"text": {
"content": message
},
"safe":0
}
# 最终发请求
req=requests.post(msgsend_url, data=json.dumps(params))
# 调试请求发送结果
print(req.content)
# 记录日志
logging.info('sendto:' + toparty + ';;subject:' + subject + ';;message:' + message)
测试发微信(python)
# 参数1是发给哪个部门
# 参数2是主题
# 参数3是消息正文
# 装好所需模块
[root@zabbix-server-71 ~]##yum install python3 python3-devel python3-pip
[root@zabbix-server-71 ~]##pip3 install requests
# 发给部门消息
[root@zabbix-server-71 ~]##python3 weixin_zabbix.py 2 "zabbix微信报警测试" "当前使用python脚本发送,发送人www.haloyang.top"
坑记录,添加ip白名单
# 踩坑了,tmd,需要加入自建应用的ip白名单
# https://open.work.weixin.qq.com/devtool/query?e=60020
python3版本的坑
#!/usr/bin/env python3
别忘记,修改脚本的python解释器!!
推送报警信息(bash)
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]# vim weixin_zabbix.sh
#!/bin/bash
# Authror: www.haloyang.top
#需要将下列信息修改为自己注册的企业微信信息 #应用ID
agentid='1000002'
#secretID
corpsecret='Z2LpWYv2tswSWZXuXAzyxqCuGUWrDPKhhHvvnY'
#企业ID
corpid='ww76b673e3bea'
#接受者的账户,由zabbix传入
#user=$1
#报警邮件标题,由zabbix传入
title=$2
#报警邮件内容,由zabbix传入
message=$3
#接收信息的组
# 消息发给哪个组
# linux0224小分队,组id是1
group=$1
#获取token信息,需要在链接里带入ID
# 如下2段代码,需要结合着跑
# -s 安静执行
# -X GET 制定GET请求访问
# "https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=${corpid}&corpsecret=${corpsecret}"
# 这就是一个url,但是url是变量替换的一个字符串
# 你发送你的企业id号,和应用id号,发给微信的服务器,微信服务器会返回给你一个身份令牌字符串
# 下一步,你就可以用这个字符串代表你的身份,是有权限和微信的公众号通信了
#这段代码是获取身份校验值,代表这个客户端是有权限和微信API通信的
token=$(curl -s -X GET "https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=${corpid}&corpsecret=${corpsecret}"|awk -F \" '{print $10}')
#构造语句执行发送动作,发送http请求
# 这个curl的作用详解
# 1.发送json类型的一堆数据
# 2.传入 部门id得值,脚本的第一个参数
# 3. 传入微信创建的应用的id
# 4. 传入text,消息数据体,分别是 title 和俩换行 和 message数据体
# 5.最终你运行这个脚本的方式是
# bash zabbix.sh 1 "牛逼" "今天正式玩一玩,生产级别的消息发送脚本"
curl -s -H "Content-Type: application/json" -X POST "https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=${token}" -d' {
"toparty" : "'"${group}"'",
"msgtype" : "text",
"agentid" : "'"${agentid}"'",
"text" : {
"content" : "'"${title}\n\n${message}"'"
},
"safe":0
}' >> /tmp/weixin_bash.log
#将报警信息写入日志文件
echo -e "\n报警时间:$(date +%F-%H:%M)\n报警标题:${title}\n报警内容:${message}" >> /tmp/weixin_bash.log
详细解bash脚本
手工拆解代码执行
[root@zabbix-server-71 ~]#corpid='ww76b67c7a9e3e3bea'
[root@zabbix-server-71 ~]#agentid='1000003'
[root@zabbix-server-71 ~]#corpsecret='mrZiPnSDsod_DPVcF-TTyCtz6BCwKGSPX8ksb4nw-KY'
客户端发出了请求,获取token值
微信的服务器,返回了一串json数据给你
[root@zabbix-server-71 ~]#curl -s -X GET "https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=${corpid}&corpsecret=${corpsecret}"
{"errcode":0,"errmsg":"ok","access_token":"E9DzfQc-QTREb33YGcJVvm6e9PKFZo-75PF_UW5fNcCdP9_XNbpczHgtT9Cqjlt4FGIXCCgsXRegMeNpYhk3Z4Vj6-njUMR-FCm2XEess3_pH9VYq557cj6cG4yL0vByyoQ9NY56s-LJzP7bZViZigPT8HN1pDK3WU69ALMwpiCJ3y8DgK2fW2SNi3f4h1vPKS87Xo_iT6iUZYuF7Zry1Q","expires_in":7200}
awk提取token字符串值
[root@zabbix-server-71 ~]#curl -s -X GET "https://qyapi.weixin.qq.com/cgi-bin/gettoken?corpid=${corpid}&corpsecret=${corpsecret}" | awk -F \" '{print $10}'
E9DzfQc-QTREb33YGcJVvm6e9PKFZo-75PF_UW5fNcCdP9_XNbpczHgtT9Cqjlt4FGIXCCgsXRegMeNpYhk3Z4Vj6-njUMR-FCm2XEess3_pH9VYq557cj6cG4yL0vByyoQ9NY56s-LJzP7bZViZigPT8HN1pDK3WU69ALMwpiCJ3y8DgK2fW2SNi3f4h1vPKS87Xo_iT6iUZYuF7Zry1Q
bash发报警测试
[root@zabbix-server-71 ~]##bash weixin.sh 2 "bash还是不如python美丽啊" "bash发送报警了!!"
注意:记得添加企业微信ip白名单
最终微信效果
zabbix页面配置微信报警
脚本发送报警信息,调试通过后,最终还是希望zabbix实现报警触发。
添加报警媒介类型
管理 > 报警媒介类型 > 创建媒体类型
添加报警参数,参考zabbix官网文档
https://www.zabbix.com/documentation/3.4/zh/manual/config/notifications/media/script
宏参数查询
https://www.zabbix.com/documentation/3.4/zh/manual/appendix/macros/supported_by_location
zabbix配置文件设置目录
需要告诉zabbix,你自定义的脚本在什么目录
1. 需要设置zabbix-server的配置文件,在/etc/zabbix/zabbix_server.conf文件追加一条定义脚本存储的文件夹AlertScriptsPath=/usr/lib/zabbix/alertscripts,这样zabbix才能去这里去找到脚本且执行。
[root@zabbix-server-71 ~]#grep '^AlertScriptsPath' /etc/zabbix/zabbix_server.conf
AlertScriptsPath=/usr/lib/zabbix/alertscripts
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#ls
weixin_zabbix.sh weixin_zabbix.py
2. bash py的脚本放入该目录即可,还得注意权限。。。太坑了。
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chown zabbix.zabbix weixin_zabbix.py
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chown zabbix.zabbix weixin_zabbix.sh
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chmod +x weixin_zabbix.py
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chmod +x weixin_zabbix.sh
#提醒,少一步都是坑,哈哈哈,辛酸;特别是设置文件的权限
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#ll
total 8
-rwxr-xr-x 1 zabbix zabbix 1510 Oct 2 18:50 weixin_zabbix.py
-rwxr-xr-x 1 zabbix zabbix 2147 Oct 2 18:49 weixin_zabbix.sh
3. 去zabbix-UI界面添加即可。
用户设置报警媒介
请注意,这里的收件人,是指微信的组,或者微信的联系人!
传入的参数,我这里是传入的1,是zabbix监控小组的ID。
脚本参数:
{ALERT.SENDTO}
{ALERT.SUBJECT}
{ALERT.MESSAGE}
完结收工(测测微信有报警吗)
[root@zabbix-server-71 ~]#ab -c 100 -n 100000 http://10.0.0.7/
可以检测日志
tail -f /tmp/weixin.log
Sat, 02 Oct 2024 22:16:45, connectionpool.py, DEBUG, Starting new HTTPS connection (1): qyapi.weixin.qq.com:443
Sat, 02 Oct 2024 22:16:45, connectionpool.py, DEBUG, https://qyapi.weixin.qq.com:443 "GET /cgi-bin/gettoken?corpid=ww76b67c7a9e3e3bea&corpsecret=Z2LpWY2H15sv2tswSWZXuXAzyxqCuGUWrDPKhhHvvnY HTTP/1.1" 200 277
Sat, 02 Oct 2024 22:16:45, connectionpool.py, DEBUG, Starting new HTTPS connection (1): qyapi.weixin.qq.com:443
Sat, 02 Oct 2024 22:16:46, connectionpool.py, DEBUG, https://qyapi.weixin.qq.com:443 "POST /cgi-bin/message/send?access_token=_tIBkDweSW5UD0RoNnkuNQp0hmBe8ILlEUb6l3gdZuLVOArculwDJRiXy02chWt7VgQNHi6KFhU7Vu16lwwMqnEvRYL0n-ttIy33PmUt0ohiV5tUXc6rBOWCT1ZKH6TDHZAlospAUzVtVCdmcGxahiNLherauix-wX4K8gLYnsWdu50QxMA-ksViff-qDI4nc0ISrSxBgOa_338Pf_Ss_A HTTP/1.1" 200 124
Sat, 02 Oct 2024 22:16:46, weixin_zabbix.py, INFO, sendto:2;;subject:恢复OK, 服务器:web7: TIME_WAIT连接数太多已恢复!;;message:恢复OK, 服务器:web7: TIME_WAIT连接数太多已恢复!
Author: www.haloyang.top
告警主机:web7
告警时间:2024.10.02 22:15:42
告警等级:Warning
告警信息: TIME_WAIT连接数太多
告警项目:tcp_status[TIME_WAIT]
问题详情:TIME_WAIT监控:64
当前状态:OK:64
事件ID:94
钉钉报警
钉钉报警原理流程
和微信报警类似,发送指定的数据到钉钉官方提供的API接口,钉钉会将报警信息,发送到指定的钉钉群聊,提醒所有的群成员查看,实现告警通知。
具体操作流程
创建钉钉群聊
创建自定义机器人
创建报警关键词
生成webhook认证信息
开发报警脚本
填写zabbix-UI界面的配置
测试钉钉报警通知
什么是API,以及什么叫给API发请求
API会返回给你什么
API 会返回什么给你,请看
可能返回一个html给你,zabbix是返回的字符串,
html
可能返回一个json数据(字符串)给你,
微信,钉钉API就是这么玩的。
先看微信API,返回的json数据
# 吧报警数据,发到微信,发到你的微信小组
#就是这一段代码
curl -s -H "Content-Type: application/json" -X POST "https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=${token}" -d' {
"toparty" : "'"${group}"'",
"msgtype" : "text",
"agentid" : "'"${agentid}"'",
"text" : {
"content" : "'"${title}\n\n${message}"'"
},
"safe":0
}'
发出get类型的请求,看看是什么结果
2个方式
给这个API,发出get类型的请求
curl 访问 ,方式1
用浏览器直接访问,方式,get类型
https://qyapi.weixin.qq.com/cgi-bin/message/send?access_token=${token}
再看zabbix的API,返回的结果
纠正,form-data和json数据提交,是两种数据构造类型
1. zabbix的登录页面,登录请求,发出http请求,看响应结果
携带着数据提交的get请求,form-data类型
2. 微信的API,发出http请求,看响应结果
携带着数据提交的get请求
(微信这个,的确是,请求传入的数据,就是json类型的字符串,响应的数据,也是json类型的数据)
json是一个网络中传输数据的,数据结构类型
form-data zabbix用的是这个类型,表单数据提交,账户密码,也依然是key:value类型
form-data类型的数据提交,如图
zabbix的登录页面
纯json的数据构造提交
你去理解,如何通过浏览器的抓包工具,分析请求的具体协议类型。
创建群聊机器人
创建群聊自定义机器人
保存好你的webhook地址后面脚本中会用到
机器人文档 https://open.dingtalk.com/document/org/application-types 用户可以向这个webhook地址发起post请求,提交数据,也就是等于给钉钉发消息了,注意字符集编码
测试webhook地址
# 提交json类的数据,发给钉钉的API
[root@zabbix-server-71 ~]#curl -H 'Content-Type: application/json' \
-d '{"msgtype": "text", "text": {"content": "zabbix 报警测试,来自于www.haloyang.top"}}' \
'机器人的webhook地址'
# 拿到了结果
{"errcode":0,"errmsg":"ok"}
支持更多功能参数,如圈某人看消息
# 参考钉钉机器人API的文档,支持哪些参数,参考用法如下
https://open.dingtalk.com/document/robots/custom-robot-access
# shell发请求 ,注意json数据格式,以及zabbix触发关键字
# 圈人语法,基于手机号
curl '机器人的webhook地址' \
-H 'Content-Type: application/json' \
-d '{"at":{"atMobiles":["要@人的手机号"],"isAtAll":false},"text":{"content":"正在测试zabbix钉钉报警机器人!!"},"msgtype":"text"}'
# 圈人语法2,基于UserIds,员工ID,但是需要管理员查看,用户自己不好尝试了
钉钉发消息脚本
python版
注意,该脚本是python3,你的目标机器,是否支持python3
yum install python3 python3-devel python3-pip -y
pip3 install requests
#!/usr/bin/python3
# coding: utf-8
# about zabbix python script
# Author: www.haloyang.top
import requests,json,sys,os,datetime
# 钉钉机器人API
webhook_url="机器人的webhook地址"
# 给脚本参数手机号参数1
user_phone=sys.argv[1]
# 参数2,消息正文
text=sys.argv[2] + "\n\n" + sys.argv[3]
# 构造json数据体
data={
"msgtype":"text",
"text":{
"content":text
},
"at":{
"atMobiles":[user_phone],
"isAtAll":False
}
}
# 请求头,表明请求类型是json
headers={"Content-Type":"application/json"}
# 发HTTP请求,POST方式,传入数据与请求头
response=requests.post(url=webhook_url,data=json.dumps(data),headers=headers)
print(response.content.decode())
# 日志目录生成
if os.path.exists("/tmp/dingding.log"):
with open("/tmp/dingding.log","a+") as f:
print("该文件以存在,追加写入中")
if response.json().get("errcode")==0:
f.write("\n" + str(datetime.datetime.now()) + " " + str(user_phone) + " " + "发送成功" + "\n" + str(text) )
else:
f.write("\n" + str(datetime.datetime.now()) + " " + str(user_phone) + " " + "发送失败" + "\n" + str(text) )
else:
with open("/tmp/dingding.log","w+") as f:
print("该日志文件不存在,创建且写入中")
if response.json().get("errcode")==0:
f.write("\n" + str(datetime.datetime.now()) + " " + str(user_phone) + " " + "发送成功" + "\n" + str(text) )
else:
f.write("\n" + str(datetime.datetime.now()) + " " + str(user_phone) + " " + "发送失败" + "\n" + str(text) )
执行测试结果
[root@m-61 /tmp]#python3 ding.py 15210858004 "python测试钉钉机器人" "zabbix故障了!!抓紧起来修复啊!!火星撞地球了!!"
#拿到结果了
b'{"errcode":0,"errmsg":"ok"}'
该文件以存在,追加写入中
#错误结果
{"errcode":310000,"errmsg":"错误描述:关键词不匹配;解决方案:请联系群管理员查看此机器人的关键词,并在发送的信息中包含此关键词;"}
钉钉结果
bash版
#!/bin/bash
# about zabbix bash script
# Author: www.haloyang.top
#webhook 地址 webhook=''
#接受者的手机号,由 zabbix 传入
user=$1
#报警邮件标题,由 zabbix 传入
title=$2
#报警邮件内容,由 zabbix 传入
message=$3
# 构造语句执行发送动作
# bash就是用curl 构造json数据发出去而已,注意引号的细节就好
# 通过API返回的数据,来确认是否发送正确
curl -s -H "Content-Type: application/json" -X POST "机器人的webhook地址" -d '{"msgtype":"text","text":{"content":"'"${title}\n\n${message}\n\nzabbix报警啦"'"},"at":{"atMobiles":["'"${user}"'"],"isAtAll":false}}'
#将报警信息写入日志文件
echo -e "\n 报警时间:$(date +%F-%H:%M)\n 报警标题:${title}\n 报警内容:${message}" >> /tmp/ding_bash.log
测试运行
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#bash ding_zabbix.sh 15210858004 'web-7 报警了!' 'nginx挂了!'
#拿到结果
{"errcode":0,"errmsg":"ok"}
钉钉结果
zabbix-UI页面配置钉钉报警
脚本调通后,就可以去zabbix的UI页面配置参数,提供报警
思路依然是
创建报警媒介类型
↓
创建媒体类型
↓
钉钉报警创建
↓
用户选择报警媒介方式
创建媒体类型
脚本参数:
{ALERT.SENDTO}
{ALERT.SUBJECT}
{ALERT.MESSAGE}
注意坑
1.脚本放入zabbix目录,采用python脚本,闲的更nb
2.脚本权限
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chown zabbix.zabbix ding_zabbix.py
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chown zabbix.zabbix ding_zabbix.sh
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chmod +x ding_zabbix.py
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#chmod +x ding_zabbix.sh
[root@zabbix-server-71 /usr/lib/zabbix/alertscripts]#ll
total 16
-rwxr-xr-x 1 zabbix zabbix 1747 Oct 2 21:07 ding_zabbix.py
-rwxr-xr-x 1 zabbix zabbix 887 Oct 2 21:19 ding_zabbix.sh
3.日志文件权限
[root@zabbix-server-71 /tmp]#rm -rf /tmp/*.log
用户选择报警媒介(钉钉)
坑记录,最后一步zabbix调用python发报警,别忘记关键字
给zabbix中的动作,添加关键字即可,否则无法触发钉钉机器人
最后测试
报警通知
问题修复通知