华为防火墙上传异常流量报警


华为防火墙上传异常流量报警

代码功能概述

该代码主要用于从一个特定的防火墙设备获取网络流量报告,并根据流量数据进行警报通知。它涉及到对设备的两个主要操作:

  1. 获取流量报告(POST 请求):根据设定的时间范围和应用程序代码,从防火墙设备中请求流量报告。
  2. 发送警报通知:如果检测到某个用户的总流量超过 5000MB,则通过钉钉 Webhook 发送警报。

个人博客

个人博客直达地址
网站不断完善中里面拥有大量的脚本,并且源码完全开放 欢迎纯白嫖。关注公众私信可免费写脚本。

效果展示

在这里插入图片描述

使用方法

  1. 初始化 Redis 连接

    • 代码使用 redis.Redis 连接到 Redis 数据库,用于缓存处理过的数据。
  2. 定义应用程序名称

    • app_names 字典定义了一些应用程序代码与其名称的映射关系。
  3. 获取时间范围

    • 计算当前日期的开始和结束时间戳,以确定数据查询的时间范围。
  4. 发送 GET 请求获取基础数据

    • 发送 GET 请求到防火墙设备,获取基础的流量数据。
  5. 循环处理每个应用程序

    • 对每个应用程序代码,发送 POST 请求请求详细的流量数据。
  6. 处理和检查数据

    • 解析返回的流量数据,检查每个 IP 地址的流量。
    • 如果某个 IP 地址的流量超过 5000MB,则通过钉钉 Webhook 发送警报通知。
  7. 缓存和控制警报发送

    • 使用 Redis 缓存已处理的数据,避免重复警报。
    • 通过设置缓存过期时间来控制警报发送的频率。

注意事项

  1. 安全性

    • 代码中 verify=False 表示忽略 SSL 证书验证,这可能存在安全隐患。应确保使用正确的 SSL 证书或适当处理 SSL 验证。
  2. 防火墙 IP 地址

    • urlparams 中的 自己防火墙ip 应替换为实际的防火墙设备 IP 地址。
  3. Web 应用服务

    • 确保钉钉 Webhook 的 access_token 是正确的,并且配置了 Webhook 地址。
  4. Redis 配置

    • r = redis.Redis(host='10.1.6.175', port=6379, db=0) 中的 Redis 地址和端口应根据实际环境进行配置。
  5. 错误处理

    • 代码对请求失败做了基本处理,但可能需要根据实际情况添加更多的错误处理和重试机制。
  6. 性能优化

    • 代码中对每个应用程序循环发送请求,可能会对性能产生影响。考虑优化请求发送和数据处理的逻辑。
  7. 时间范围设置

    • time_rangetime_to 应正确设置,以确保获取的流量数据是准确的。

代码使用示例

  • 运行代码:直接运行脚本以获取流量报告并发送警报。
  • 配置:根据实际环境配置防火墙 IP 地址、Redis 地址以及钉钉 Webhook 相关参数。
  • 监控:检查控制台输出和钉钉消息,确保警报通知的准确性和及时性。
import requests
import json
import time
import html
import warnings
import redis
from urllib3.exceptions import InsecureRequestWarning
from datetime import datetime

# 忽略 urllib3 的 InsecureRequestWarning 警告
warnings.filterwarnings("ignore", category=InsecureRequestWarning)

# 连接 Redis
r = redis.Redis(host='10.1.6.175', port=6379, db=0)
# 定义变量组
app_names = {
    "%u5951%u6587%u4EF6%u4E2D%u8F6C%u534F%u8BAE": "QQ文件中转协议",
    "%u96C5%u864E%u901A%u6587%u4EF6%u4F20%u8F93": "雅虎通文件传输",
    "MSN%u6587%u4EF6%u4F20%u8F93": "MSN文件传输",
    "%u98DE%u4FE1%u6587%u4EF6%u4F20%u8F93": "飞信文件传输",
    "ICQ%u6587%u4EF6%u4F20%u8F93": "ICQ文件传输",
    "QQ%u6587%u4EF6%u4F20%u8F93": "QQ文件传输",
    "Instan%5C_T%u6587%u4EF6%u4F20%u8F93": "Instan_T文件传输",
    "Rediffbol%u6587%u4EF6%u4F20%u8F93": "Rediffbol文件传输",
    "Mail.ru%5C_Agent%u6587%u4EF6%u4F20%u8F93": "Mail.ru_Agent文件传输",
    "%u767E%u5EA6Hi%u6587%u4EF6%u4F20%u8F93": "百度Hi文件传输",
    "Softros%5C_Messenger%u6587%u4EF6%u4F20%u8F93": "Softros_Messenger文件传输",
    "%u98DE%u9E26%u4F20%u4E66%u6587%u4EF6%u4F20%u8F93": "飞鸽传书文件传输",
    "Trillian%u6587%u4EF6%u4F20%u8F93": "Trillian文件传输",
    "ICUII%u6587%u4EF6%u4F20%u8F93": "ICUII文件传输",
    "AIM%5C_Express%u6587%u4EF6%u4F20%u8F93": "AIM_Express文件传输",
    "123%5C_Web%5C_Messenger%u6587%u4EF6%u4F20%u8F93": "123_Web_Messenger文件传输",
    "EyeballChat%u6587%u4EF6%u4F20%u8F93": "EyeballChat文件传输",
    "GeVeZeLAN%u6587%u4EF6%u4F20%u8F93": "GeVeZeLAN文件传输",
    "EasyMessenger%u6587%u4EF6%u4F20%u8F93": "EasyMessenger文件传输",
    "CoolMessenger%u6587%u4EF6%u4F20%u8F93": "CoolMessenger文件传输",
    "Indline%5C_Messenger%u6587%u4EF6%u4F20%u8F93": "Indline_Messenger文件传输",
    "Outlook%5C_LAN%u6587%u4EF6%u4F20%u8F93": "Outlook_LAN文件传输",
    "LanTalk%5C_Messenger%u6587%u4EF6%u4F20%u8F93": "LanTalk_Messenger文件传输",
    "SonorkEIM%u6587%u4EF6%u4F20%u8F93": "SonorkEIM文件传输",
    "Transporter%5C_P2P%u6587%u4EF6%u4F20%u8F93": "Transporter_P2P文件传输",
    "%u98DE%u79CB%u6587%u4EF6%u4F20%u8F93": "飞秋文件传输",
    "%u5FAE%u535A%u684C%u9762%u6587%u4EF6%u4F20%u8F93": "微博桌面文件传输",
    "35EQ%u6587%u4EF6%u4F20%u8F93": "35EQ文件传输",
    "GooberMessenger%u6587%u4EF6%u4F20%u8F93": "GooberMessenger文件传输",
    "Commfort%u6587%u4EF6%u4F20%u8F93": "Commfort文件传输",
    "Garena%u6587%u4EF6%u4F20%u8F93": "Garena文件传输",
    "AvChat%u6587%u4EF6%u4F20%u8F93": "AvChat文件传输",
    "%u6709%u670B%u901A%u8BAF%u6587%u4EF6%u4F20%u8F93": "有朋通讯文件传输",
    "%u5E03%u8C37%u9E1F%u6587%u4EF6%u4F20%u8F93": "布谷鸟文件传输",
    "VypressChat%u6587%u4EF6%u4F20%u8F93": "VypressChat文件传输",
    "%u4F18%u4F60%u5BA2%u6587%u4EF6%u4F20%u8F93": "优你客文件传输",
    "UU%u6587%u4EF6%u4F20%u8F93": "UU文件传输",
    "UCEIM%u6587%u4EF6%u4F20%u8F93": "UCEIM文件传输",
    "Espace%u6587%u4EF6%u4F20%u8F93": "Espace文件传输",
    "%u6C47%u8BAF%u6587%u4EF6%u4F20%u8F93": "汇讯文件传输",
    "ImOffice%u6587%u4EF6%u4F20%u8F93": "ImOffice文件传输",
    "%u5642%u5642%u6587%u4EF6%u4F20%u8F93": "嘟嘟文件传输",
    "Qcn%u6587%u4EF6%u4F20%u8F93": "Qcn文件传输",
    "%u5FAE%u4FE1%u6587%u4EF6%u4F20%u8F93": "微信文件传输",
    "Box%u6587%u4EF6%u4E0A%u4F20": "Box文件上传",
    "Box%u6587%u4EF6%u4E0B%u8F7D": "Box文件下载",
    "%u9489%u9489%u6587%u4EF6%u4F20%u8F93": "钉钉文件传输",
    "Studiopass%u6587%u4EF6%u4E0A%u4F20": "Studiopass文件上传",
    "WeTransfer%u6587%u4EF6%u4E0A%u4F20": "WeTransfer文件上传",
    "WeTransfer%u6587%u4EF6%u4E0B%u8F7D": "WeTransfer文件下载",
    "AdobeCreativeCloud%u6587%u4EF6%u4E0A%u4F20": "AdobeCreativeCloud文件上传",
    "Insync%u6587%u4EF6%u4E0B%u8F7D": "Insync文件下载",
    "Insync%u6587%u4EF6%u4E0A%u4F20": "Insync文件上传",
    "%u4F18%u4E91%u7F51%u76D8%u6587%u4EF6%u4E0B%u8F7D": "优云网盘文件下载",
    "%u4F18%u4E91%u7F51%u76D8%u6587%u4EF6%u4E0A%u4F20": "优云网盘文件上传",
    "%u4F01%u4E1A%u5FAE%u4FE1%u6587%u4EF6%u4F20%u8F93": "企业微信文件传输",
    "WhatsAPP%u6587%u4EF6%u4F20%u8F93": "WhatsAPP文件传输",
    "Dropbox%u6587%u4EF6%u4E0B%u8F7D": "Dropbox文件下载",
    "Dropbox%u6587%u4EF6%u4E0A%u4F20": "Dropbox文件上传",
    "%u5FAE%u4FE1%u53D1%u9001%u6587%u4EF6": "微信发送文件",
    "%u5FAE%u4FE1%u63A5%u6536%u6587%u4EF6": "微信接收文件",
    "%u7C73%u804A%u6587%u4EF6%u4F20%u8F93": "米聊文件传输",
    "%u963F%u91CC%u65FA%u65FA%u6587%u4EF6%u4F20%u8F93": "阿里旺旺文件传输",
    "PingChat%u6587%u4EF6%u4F20%u8F93": "PingChat文件传输",
    "%u817E%u8BAF%u901A%u6587%u4EF6%u4F20%u8F93": "腾讯通文件传输",
    "Worktile%u6587%u4EF6%u4F20%u8F93": "Worktile文件传输",
    "QQ%u53D1%u9001%u6587%u4EF6": "QQ发送文件",
    "QQ%u63A5%u6536%u6587%u4EF6": "QQ接收文件",
    "%u767E%u5EA6%u7F51%u76D8": "百度网盘",
    "%u767E%u5EA6%u4E91%u76D8%u4E0A%u4F20": "百度云盘上传",
    "%u767E%u5EA6%u4E91%u76D8%u4E0B%u8F7D": "百度云盘下载",
    "%u963F%u91CC%u4E91%u76D8": "阿里云盘"
}
# 获取当天的时间戳
current_time = int(time.time())
time_range = current_time - (current_time % 86400)  # 昨天的时间戳
time_to = current_time + 86400  # 今天的时间戳
date_time = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
url = "https://自己防火墙ip:8443/common.html"
payload = {
    "getTrafficReportTOPN": {
        "language": 1,
        "vsys": "public",
        "pageIndex": 1,
        "pageSize": 100,
        "exported": 0,
        "reportType": "flowReport",
        "funcName": "getTrafficReportTOPN",
        "time_range": str(time_range),
        "time_to": str(time_to),
        "topNType": "app",
        "desc": "upflow"
    }
}
headers = {
    'Accept': '*/*',
    'Accept-Encoding': 'gzip, deflate, br',
    'Accept-Language': 'zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2',
    'Connection': 'keep-alive',
    'Content-Length': '239',
    'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8',
    'Cookie': 'SESSIONID=bQEAAApssLsyQHBKbFp1IsmHHFB8+n/3C6O/R5rbx5g=&bQEAADaGLftkNINKVr87HQ==&HUAWEI &langfrombrows=zh-CN,&copyright=2014-2019',
    'Host': '自己防火墙ip:8443',
    'Origin': 'https://自己防火墙ip:8443',
    'Referer': 'https://自己防火墙ip:8443/default.html',
    'Sec-Fetch-Dest': 'empty',
    'Sec-Fetch-Mode': 'cors',
    'Sec-Fetch-Site': 'same-origin',
    'Token': 'kVlUZjudU5EtircTfNj4enORi9mpsF6E8Tolb8zdn3M=',
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:124.0) Gecko/20100101 Firefox/124.0',
    'X-Requested-With': 'XMLHttpRequest'
}

response = requests.request("POST", url, headers=headers, json=payload, verify=False)
shuaxin_decoded_data = html.unescape(response.text)
# print(shuaxin_decoded_data)

# 构建 GET 请求 URL
url = "https://自己防火墙ip:8443/filename/heartbeat/"
params = {
    "time_range": str(time_range),
    "time_to": str(time_to)
}
headers = {
    "Accept": "*/*",
    "Accept-Encoding": "gzip, deflate, br",
    "Accept-Language": "zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2",
    "Connection": "keep-alive",
    "Cookie": "SESSIONID=bQEAAApssLsyQHBKbFp1IsmHHFB8+n/3C6O/R5rbx5g=&bQEAADaGLftkNINKVr87HQ==&HUAWEI &langfrombrows=zh-CN,&copyright=2014-2019",
    "Host": "自己防火墙ip:8443",
    "Referer": "https://自己防火墙ip:8443/default.html",
    "Sec-Fetch-Dest": "empty",
    "Sec-Fetch-Mode": "cors",
    "Sec-Fetch-Site": "same-origin",
    "Token": "kVlUZjudU5EtircTfNj4enORi9mpsF6E8Tolb8zdn3M=",
    "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:124.0) Gecko/20100101 Firefox/124.0",
    "X-Requested-With": "XMLHttpRequest"
}

# 发送 GET 请求
response = requests.get(url, params=params, headers=headers, verify=False)

if response.status_code == 200:
    # 循环处理每个应用程序
    for app_code, app_name in app_names.items():
        # 构建 POST 请求参数
        post_params = {
            "getTrafficReportTOPN": {
                "language": 1,
                "vsys": "public",
                "pageIndex": 1,
                "pageSize": 10,
                "exported": 0,
                "reportType": "flowReport",
                "funcName": "getTrafficReportTOPN",
                "time_range": str(time_range),
                "time_to": str(time_to),
                "topNType": "app-srcIp",
                "application": app_code,
                "singleItem": app_code,
                "desc": "flow"
            }
        }
        post_url = "https://自己防火墙ip:8443/common.html"
        post_headers = {
            "Accept": "*/*",
            "Accept-Encoding": "gzip, deflate, br",
            "Accept-Language": "zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2",
            "Connection": "keep-alive",
            "Content-Type": "application/x-www-form-urlencoded; charset=UTF-8",
            "Cookie": "SESSIONID=bQEAAApssLsyQHBKbFp1IsmHHFB8+n/3C6O/R5rbx5g=&bQEAADaGLftkNINKVr87HQ==&HUAWEI &langfrombrows=zh-CN,&copyright=2014-2019",
            "Host": "自己防火墙ip:8443",
            "Origin": "https://自己防火墙ip:8443",
            "Referer": "https://自己防火墙ip:8443/default.html",
            "Sec-Fetch-Dest": "empty",
            "Sec-Fetch-Mode": "cors",
            "Sec-Fetch-Site": "same-origin",
            "Token": "kVlUZjudU5EtircTfNj4enORi9mpsF6E8Tolb8zdn3M=",
            "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:124.0) Gecko/20100101 Firefox/124.0",
            "X-Requested-With": "XMLHttpRequest"
        }
        # 发送 POST 请求
        post_response = requests.post(post_url, json=post_params, headers=post_headers, verify=False)
        decoded_data = html.unescape(post_response.text)
        if post_response.status_code == 200:
            # 解析 JSON 数据
            data = json.loads(decoded_data)
            traffic_report = data["getTrafficReportTOPN"]
            for item in traffic_report["data"]:
                upflow_mb = int(item["upflow"]) / (1024 * 1024)  # 将上行流量转换为MB
                downflow_mb = int(item["downflow"]) / (1024 * 1024)  # 将下行流量转换为MB
                flow_mb = int(item["flow"]) / (1024 * 1024)  # 将总流量转换为MB
                total_flow_mb = int(item["totalFlow"]) / (1024 * 1024)  # 将总流量转换为MB
                total_upflow_mb = int(item["totalUpflow"]) / (1024 * 1024)  # 将总上行流量转换为MB
                total_downflow_mb = int(item["totalDownflow"]) / (1024 * 1024)  # 将总下行流量转换为MB

                # 构建缓存键值
                cache_key = f"{app_name}:{item['singleItem']}"

                # 检查缓存中是否存在该键值
                if not r.exists(cache_key):
                    # 如果该用户总流量大于 5000MB,发送报警 Webhook 并将键值存入缓存,缓存过期时间设置为 1 小时
                    if flow_mb > 5000:
                        payload = {
                            "msgtype": "text",
                            "text": {
                                "content": f"TEST网络流量预警当前用户总流量大于5000MB通知\n"
                                           f"应用程序名称: {app_name}\n"
                                           f"IP地址: {item['singleItem']}\n"
                                           f"上传流量: {upflow_mb:.2f} MB\n"
                                           f"下载流量: {downflow_mb:.2f} MB\n"
                                           f"该用户总流量: {flow_mb:.2f} MB\n"
                                           f"该用户会话数: {item['sessionNum']}\n"
                                           f"该应用整体总流量: {total_flow_mb:.2f} MB\n"
                                           f"该应用总上传流量: {total_upflow_mb:.2f} MB\n"
                                           f"该应用总下载流量: {total_downflow_mb:.2f} MB\n"
                                           f"总会话数: {item['totalSessionNum']}\n"
                            }
                        }
                        headers = {
                            "Content-Type": "application/json"
                        }
                        response = requests.post(
                            "https://oapi.dingtalk.com/robot/send?access_token=3d3c3a0e7f45bd760b6d0dde83fe5b193783a50a9db5a5f92db1b27c54XXXXX",
                            json=payload,
                            headers=headers
                        )
                        if response.status_code == 200:
                            print("报警 Webhook 发送成功")
                        else:
                            print(f"报警 Webhook 发送失败,状态码: {response.status_code}")

                        # 将键值存入缓存,过期时间设置为 3 小时
                        r.set(cache_key, 1, ex=10800)

                print({
                    "应用程序名称": app_name,
                    "IP地址": item["singleItem"],
                    "上传流量": f"{upflow_mb:.2f} MB",
                    "下载流量": f"{downflow_mb:.2f} MB",
                    "该用户总流量": f"{flow_mb:.2f} MB",
                    "该用户会话数": item["sessionNum"],
                    "该应用整体总流量": f"{total_flow_mb:.2f} MB",
                    "该应用总上传流量": f"{total_upflow_mb:.2f} MB",
                    "该应用总下载流量": f"{total_downflow_mb:.2f} MB",
                    "总会话数": item["totalSessionNum"]
                })
            # 每次循环请求之间延迟 0.3 秒
            time.sleep(0.3)
        else:
            print(f"POST 请求失败,状态码: {post_response.status_code}")
else:
    print(f"GET 请求失败,状态码: {response.status_code}")
  • 6
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

脚本小能手

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值