当前位置: 首页 > news >正文

Linux 系统监控 + 邮件告警实战:CPU、内存、IO、流量全覆盖

在服务器运维中,“被动救火” 往往会导致业务中断、数据丢失等严重问题。如果能实时监控系统核心资源(CPU、内存、硬盘、IO、网络),并在指标超限时自动发送告警邮件,就能将运维从 “事后处理” 转变为 “事前预警”。本文将手把手教你用 Bash 脚本实现这套监控告警系统,配置简单、轻量化,适用于各类 Linux 服务器。

一、为什么需要这套监控系统?

日常运维中,我们常遇到这些痛点:

  • 服务器突然卡顿,才发现 CPU 使用率飙升到 100%;
  • 硬盘满了导致服务崩溃,事前毫无察觉;
  • 网络带宽被占满,用户反馈访问慢才去排查;
  • 磁盘 IO 等待过高,数据库响应延迟却没及时发现。

这套监控系统能解决这些问题:

  • 覆盖核心指标:CPU、内存、硬盘使用率(超 80% 告警)、IO await(超 50ms 告警)、网络流量(超 10MB/s 可自定义告警);
  • 自动邮件告警:用 QQ/163/139 邮箱发送告警,包含服务器 IP、异常指标、告警时间;
  • 轻量化部署:基于 Bash 脚本,无需安装复杂监控平台,适合中小服务器集群;
  • 灵活可配置:所有阈值可自定义,适配不同业务场景。

二、前置准备:3 分钟搞定邮箱 SMTP 配置

要实现邮件告警,首先需要开启邮箱的 SMTP 服务(用于发送邮件),并获取授权码(替代登录密码,更安全)。以 QQ 邮箱为例,其他邮箱(163、139)步骤类似。

1. 开启 QQ 邮箱 SMTP 服务

  1. 登录 QQ 邮箱,点击顶部「设置」→「账户」;
  1. 下拉找到「POP3/IMAP/SMTP/Exchange/CardDAV/CalDAV 服务」,开启「POP3/SMTP 服务」;
  1. 按提示用手机 QQ 扫码验证,生成 16 位「授权码」,务必保存好(后续脚本要用)。

2. 核心邮箱参数整理

无论用哪种邮箱,最终需要这 5 个参数,整理成表格备用:

参数名称

说明

QQ 邮箱示例

163 邮箱示例

SENDER_EMAIL

发件人邮箱(告警邮箱)

2578628978@qq.com

yourname@163.com

SENDER_PWD

邮箱授权码(非登录密码)

vjcjarmmmuleecce(示例)

xxxxxxxx(自行获取)

RECEIVER_EMAIL

收件人邮箱(运维邮箱)

2578628978@qq.com(可同发件人)

admin@xxx.com

SMTP_SERVER

邮箱 SMTP 服务器地址

smtp.qq.com

smtp.163.com

SMTP_PORT

SMTP 端口(SSL 加密)

465

465

三、实战步骤:编写 Bash 监控告警脚本

1. 安装依赖工具

脚本需要用到msmtp(发送邮件)、sysstat(获取 IO/CPU 数据)、ifstat(获取网络流量),执行以下命令安装(适用于 CentOS/RHEL,Ubuntu/Debian 将yum替换为apt-get):

 

# 安装依赖

yum install -y msmtp sysstat ifstat bc curl

2. 编写完整监控脚本

创建脚本文件system_monitor.sh,直接复制以下代码,注意将「邮箱配置区」替换为你自己的参数:

 

#!/bin/bash

#########################################################################

# 脚本名称:system_monitor.sh

# 功能描述:监控CPU、内存、硬盘、IO、网络,超阈值发送邮件告警

# 适用系统:CentOS/RHEL/Ubuntu/Debian

# 作者:运维笔记

# 日期:2025-09-07

#########################################################################

# ======================== 1. 邮箱配置区(必须修改!)=======================

SENDER_EMAIL="2578628978@qq.com" # 发件人邮箱(你的QQ邮箱)

SENDER_PWD="vjcjarmmmuleecce" # 邮箱授权码(前文获取的16位码)

RECEIVER_EMAIL="2578628978@qq.com" # 收件人邮箱(可填多个,用逗号分隔)

SMTP_SERVER="smtp.qq.com" # SMTP服务器(QQ邮箱固定为smtp.qq.com)

SMTP_PORT="465" # SMTP端口(SSL加密固定465)

# ======================== 2. 监控阈值配置区(可自定义)=======================

CPU_THRESHOLD=80 # CPU使用率阈值(超80%告警)

MEM_THRESHOLD=80 # 内存使用率阈值(超80%告警)

DISK_THRESHOLD=80 # 硬盘使用率阈值(超80%告警,监控/根分区)

IO_AWAIT_THRESHOLD=50 # IO等待时间阈值(超50ms告警,值越大IO越卡)

NET_THRESHOLD=10 # 网络流量阈值(超10MB/s告警,上下行均监控)

# ======================== 3. 初始化变量与系统信息 ========================

ALARM_CONTENT="" # 告警内容,初始为空

SERVER_NAME=$(hostname) # 服务器主机名

SERVER_IP=$(curl -s ifconfig.me 2>/dev/null || hostname -I | awk '{print $1}') # 服务器IP

CURRENT_TIME=$(date '+%Y-%m-%d %H:%M:%S') # 当前时间

LOG_FILE="/var/log/system_monitor.log" # 监控日志文件路径

# ======================== 4. 监控函数:逐个检查系统指标 ========================

# 4.1 监控CPU使用率

monitor_cpu() {

# 取1分钟内CPU平均使用率(排除空闲进程)

CPU_USAGE=$(vmstat 1 2 | awk 'NR==4{print 100-$15}' | awk '{print int($1)}')

if [ $CPU_USAGE -gt $CPU_THRESHOLD ]; then

ALARM_CONTENT+="⚠️ CPU使用率异常:${CPU_USAGE}%(阈值${CPU_THRESHOLD}%)\n"

fi

}

# 4.2 监控内存使用率

monitor_memory() {

# 总内存-空闲内存(含缓存)=已用内存,计算使用率

MEM_TOTAL=$(free | awk '/Mem/{print $2}')

MEM_FREE=$(free | awk '/Mem/{print $4 + $6 + $7}') # 空闲+缓存+缓冲,更准确

MEM_USAGE=$(( (MEM_TOTAL - MEM_FREE) * 100 / MEM_TOTAL ))

if [ $MEM_USAGE -gt $MEM_THRESHOLD ]; then

ALARM_CONTENT+="⚠️ 内存使用率异常:${MEM_USAGE}%(阈值${MEM_THRESHOLD}%)\n"

fi

}

# 4.3 监控硬盘使用率(默认监控/根分区,可修改为其他分区如/data)

monitor_disk() {

DISK_USAGE=$(df -h / | awk '/\/$/{print substr($5, 1, length($5)-1)}')

if [ $DISK_USAGE -gt $DISK_THRESHOLD ]; then

ALARM_CONTENT+="⚠️ 硬盘使用率异常(/分区):${DISK_USAGE}%(阈值${DISK_THRESHOLD}%)\n"

fi

}

# 4.4 监控磁盘IO等待时间(await)

monitor_io() {

# 采集2次IO数据,取平均await(排除虚拟loop设备)

IO_AWAIT=$(iostat -x 1 2 | grep -vE '^$|Device|loop' | awk '{sum += $10} END {print sum/NR}')

IO_AWAIT=$(printf "%.1f" "$IO_AWAIT") # 保留1位小数

# 浮点数比较,用bc工具

if (( $(echo "$IO_AWAIT > $IO_AWAIT_THRESHOLD" | bc -l) )); then

ALARM_CONTENT+="⚠️ 磁盘IO等待时间过高:${IO_AWAIT}ms(阈值${IO_AWAIT_THRESHOLD}ms)\n"

fi

}

# 4.5 监控网络流量(上下行速率,单位MB/s)

monitor_network() {

# 采集2次网络数据,计算每秒速率(排除lo回环接口)

NET_STATS=$(ifstat -i eth0,ens*,wlan* -T 1 2 | awk 'NR==3 {print $1, $2}')

RX_RATE=$(echo "$NET_STATS" | awk '{print $1}') # 下载速率(MB/s)

TX_RATE=$(echo "$NET_STATS" | awk '{print $2}') # 上传速率(MB/s)

# 保留1位小数

RX_RATE=$(printf "%.1f" "$RX_RATE")

TX_RATE=$(printf "%.1f" "$TX_RATE")

# 分别判断上下行是否超阈值

if (( $(echo "$RX_RATE > $NET_THRESHOLD" | bc -l) )); then

ALARM_CONTENT+="⚠️ 网络下载流量过高:${RX_RATE}MB/s(阈值${NET_THRESHOLD}MB/s)\n"

fi

if (( $(echo "$TX_RATE > $NET_THRESHOLD" | bc -l) )); then

ALARM_CONTENT+="⚠️ 网络上传流量过高:${TX_RATE}MB/s(阈值${NET_THRESHOLD}MB/s)\n"

fi

}

# ======================== 5. 发送告警邮件函数 ========================

send_alert_email() {

# 只有当有告警内容时,才发送邮件

if [ -n "$ALARM_CONTENT" ]; then

# 构建完整邮件内容(含服务器信息)

FULL_CONTENT="⚠️ 服务器资源告警 ⚠️\n\n"

FULL_CONTENT+="📌 服务器信息:\n"

FULL_CONTENT+="主机名:${SERVER_NAME}\n"

FULL_CONTENT+="IP地址:${SERVER_IP}\n"

FULL_CONTENT+="告警时间:${CURRENT_TIME}\n\n"

FULL_CONTENT+="🔴 异常指标:\n"

FULL_CONTENT+="${ALARM_CONTENT}\n"

FULL_CONTENT+="💡 建议:\n"

FULL_CONTENT+="1. CPU/内存异常:检查是否有高占用进程(top命令)\n"

FULL_CONTENT+="2. 硬盘异常:清理无用文件(du -sh * 查找大文件)\n"

FULL_CONTENT+="3. IO异常:检查磁盘是否故障(smartctl工具)\n"

FULL_CONTENT+="4. 网络异常:查看流量来源(iftop命令)"

# 用msmtp发送邮件(SSL加密)

echo -e "From: ${SENDER_EMAIL}\nTo: ${RECEIVER_EMAIL}\nSubject: 【系统告警】${SERVER_NAME}资源异常\n\n${FULL_CONTENT}" | \

msmtp --server ${SMTP_SERVER} \

--port ${SMTP_PORT} \

--from ${SENDER_EMAIL} \

--auth on \

--user ${SENDER_EMAIL} \

--password ${SENDER_PWD} \

${RECEIVER_EMAIL}

# 记录告警日志(便于后续排查)

echo "[$CURRENT_TIME] 告警发送成功:${ALARM_CONTENT}" >> ${LOG_FILE}

echo "✅ 告警已发送至 ${RECEIVER_EMAIL},日志见 ${LOG_FILE}"

else

# 无异常时,也记录正常日志(可选)

echo "[$CURRENT_TIME] 所有指标正常:CPU=${CPU_USAGE}% 内存=${MEM_USAGE}% 硬盘=${DISK_USAGE}% IO=${IO_AWAIT}ms 下载=${RX_RATE}MB/s 上传=${TX_RATE}MB/s" >> ${LOG_FILE}

echo "✅ 所有指标正常,日志见 ${LOG_FILE}"

fi

}

# ======================== 6. 主程序:执行监控与告警 ========================

main() {

echo "[$CURRENT_TIME] 开始系统监控..."

# 执行所有监控函数

monitor_cpu

monitor_memory

monitor_disk

monitor_io

monitor_network

# 发送告警(如有)

send_alert_email

}

# 启动主程序

main

3. 脚本权限配置

给脚本添加可执行权限,否则无法运行:

 

chmod +x system_monitor.sh

四、测试与部署:确保监控正常运行

1. 手动测试脚本

先手动运行脚本,验证是否能正常采集指标、发送邮件:

 

# 运行脚本

./system_monitor.sh

测试结果判断:
  • 若输出 “✅ 所有指标正常”:说明脚本逻辑没问题,可继续部署定时任务;
  • 若输出 “✅ 告警已发送至 xxx@qq.com”:打开收件邮箱,应能收到告警邮件(示例如下);
  • 若报错:根据错误信息排查(常见错误见下文 “问题解决”)。
告警邮件示例:
 

⚠️ 服务器资源告警 ⚠️

📌 服务器信息:

主机名:localhost.localdomain

IP地址:192.168.1.100

告警时间:2025-09-07 15:30:00

🔴 异常指标:

⚠️ CPU使用率异常:85%(阈值80%)

⚠️ 网络下载流量过高:12.3MB/s(阈值10MB/s)

💡 建议:

1. CPU/内存异常:检查是否有高占用进程(top命令)

2. 硬盘异常:清理无用文件(du -sh * 查找大文件)

3. IO异常:检查磁盘是否故障(smartctl工具)

4. 网络异常:查看流量来源(iftop命令)

2. 部署定时任务:实现持续监控

手动运行只能测试一次,要实现 “每 5 分钟监控一次”,需用crontab设置定时任务:

 

# 编辑定时任务

crontab -e

# 在文件末尾添加以下内容(每5分钟执行一次,日志输出到/var/log/system_monitor.log)

*/5 * * * * /path/to/system_monitor.sh >> /var/log/system_monitor.log 2>&1

  • 注意:将/path/to/system_monitor.sh替换为脚本的实际路径(如/root/shengge/system_monitor.sh);
  • */5 * * * * 表示 “每 5 分钟执行一次”,可根据需求修改(如*/1 * * * *为每分钟一次)。

3. 验证定时任务

设置后,等待 5 分钟,查看日志文件是否有新记录:

 

tail -f /var/log/system_monitor.log

若能看到类似以下日志,说明定时任务正常运行:

 

[2025-09-07 15:35:00] 开始系统监控...

[2025-09-07 15:35:02] 所有指标正常:CPU=25% 内存=60% 硬盘=75% IO=8.2ms 下载=1.5MB/s 上传=0.8MB/s

五、常见问题解决:避坑指南

在部署过程中,可能会遇到以下问题,这里提供针对性解决方案:

1. 脚本运行报错:bash: ./system_monitor.sh: 权限不够

  • 原因:脚本没有可执行权限;
  • 解决:执行chmod +x system_monitor.sh赋予权限。

2. 邮件发送失败:msmtp: authentication failed

  • 原因:邮箱授权码错误,或 SMTP 服务未开启;
  • 解决:
    1. 重新登录 QQ 邮箱,检查「POP3/SMTP 服务」是否开启;
    1. 重新生成授权码,替换脚本中的SENDER_PWD;
    1. 确保SENDER_EMAIL与SMTP_SERVER匹配(如 QQ 邮箱必须用smtp.qq.com)。


文章转载自:

http://I9iiuIjw.ggrzk.cn
http://l1qTZiEB.ggrzk.cn
http://S58xnGkd.ggrzk.cn
http://ckgYltfj.ggrzk.cn
http://dHJ9aqOe.ggrzk.cn
http://nMdLBYrj.ggrzk.cn
http://SuDhp4Dv.ggrzk.cn
http://LliQK0BE.ggrzk.cn
http://M4w9dy3s.ggrzk.cn
http://kg3Tyurb.ggrzk.cn
http://cNLBny3X.ggrzk.cn
http://5jbRPOEc.ggrzk.cn
http://uohEHmVv.ggrzk.cn
http://NAKvkp6N.ggrzk.cn
http://cAsWer9T.ggrzk.cn
http://3jQqnmgE.ggrzk.cn
http://zpgmgFMf.ggrzk.cn
http://30a8I9Sz.ggrzk.cn
http://cb38iNbx.ggrzk.cn
http://t2e7mPF0.ggrzk.cn
http://VUbjTkeq.ggrzk.cn
http://lJb2GhjN.ggrzk.cn
http://ASauKeLI.ggrzk.cn
http://7QQRi1Ry.ggrzk.cn
http://POWAG9sG.ggrzk.cn
http://fw4zSFxJ.ggrzk.cn
http://NtuZWgt7.ggrzk.cn
http://oiuLrwgK.ggrzk.cn
http://IrFPzJS8.ggrzk.cn
http://vyRtK9Eb.ggrzk.cn
http://www.dtcms.com/a/371539.html

相关文章:

  • HarmonyOS 应用开发新范式:深入剖析 Stage 模型与 ArkTS 状态管理
  • Elasticsearch面试精讲 Day 11:索引模板与动态映射
  • 5G NR PDCCH之信号调制
  • Android --- AOSP下载及编译
  • C#中的托管资源与非托管资源介绍
  • 初识Vue
  • JSP到Tomcat特详细教程
  • 滑动窗口与双指针(1)——定长
  • Lua > OpenResty Lua Module
  • [LeetCode 热题 100] 32. 最长有效括号
  • Python IO编程——文件读写
  • fps:游戏玩法
  • S 4.1深度学习--自然语言处理NLP--理论
  • [NCTF2019]Fake XML cookbook
  • ARM体系结构学习②
  • 多环境配置切换机制能否让开发与生产无缝衔接?
  • SC3336 rgb sensor linux
  • 人工智能学习:Transformer架构
  • Android --- AOSP源码导入Android Studio
  • 华为HCIP-Datacom-Core Technology H12-831 书籍目录
  • (RDFS)随机深度特征选择方法解释:简而言之,RDFS主要针对的是恶意的服务器,它建立在客户端是诚实的前提下。
  • 《从使用到源码:OkHttp3责任链模式剖析》
  • 华为IP(9)
  • 【秋招笔试】2025.09.03华为研发岗
  • 动态维护有效区间:单调栈
  • Ubuntu 22 安装 postgresql-17.4
  • Linux环境下配置visual code
  • 考研复习-计算机网络-第三章-数据链路层
  • OpenHarmony之SELinux安全组件底层原理设计架构精讲
  • 【机器学习】综合实训(二)