Linux系统监控:Shell脚本实现CPU、内存、磁盘、IO与网络流量告警

发布于:2025-09-08 ⋅ 阅读:(23) ⋅ 点赞:(0)

📋 ​​详细大纲​

  1. 1.

    ​明确监控目标与指标​

    • ​核心指标​​:CPU使用率与负载、内存使用率、磁盘空间使用率、磁盘I/O等待时间、网络带宽流量、关键进程状态。

    • ​辅助指标​​:系统运行时间、登录用户数、网络连接数、系统日志中的错误信息。

  2. 2.

    ​设计监控脚本结构​

    • ​参数配置区​​:定义各项监控指标的阈值、报警邮箱、日志文件路径等。

    • ​数据采集函数​​:为每个监控指标编写独立的数据采集函数。

    • ​阈值判断与报警逻辑​​:将采集到的数据与预设阈值比较,超出阈值则触发报警。

    • ​日志记录功能​​:所有监控操作和报警信息都应记录到日志文件中,便于追溯。

  3. 3.

    ​实现报警机制​

    • ​邮件报警 (最常用)​​:使用 mail命令或 msmtp等工具发送报警邮件。需预先配置SMTP服务(如QQ邮箱的SMTP服务及其授权码)。

    • ​其他报警方式​​:企业微信、钉钉机器人等,通常通过调用Webhook API实现。

  4. 4.

    ​部署与定时执行​

    • 为脚本添加可执行权限 (chmod +x)。

    • 利用 ​​cron计划任务​​ 定时执行脚本,例如:

      • 0 * * * * /path/to/script.sh(每小时)

      • */30 * * * * /path/to/script.sh(每30分钟)

  5. 5.

    ​考虑进阶功能与优化​

    • ​日志轮转 (Log Rotation)​​:防止日志文件过大,可配合 logrotate工具或脚本自行清理旧日志。

    • ​安全考虑​​:脚本中涉及密码、授权码等敏感信息,应注意权限控制(如设置配置文件为600权限)。

    • ​性能影响​​:监控脚本本身应轻量,避免频繁执行或复杂操作消耗过多系统资源。

    • ​集中监控​​:对于多台服务器,考虑使用 ​​Zabbix​​、​​Prometheus​​ 等专业监控系统,功能更强大、全面。

一份通过Shell脚本实现Linux系统资源监控与邮件告警的实用指南

本文将详细介绍如何使用Shell脚本监控Linux系统的CPU使用率、内存使用率、磁盘使用率、IO等待时间以及网络流量,并在资源使用超过设定阈值时自动发送邮件告警。这套方案轻量、灵活,非常适合中小型项目或个人服务器使用。

一、监控脚本核心命令概述

在开始编写监控脚本前,我们先了解一些Linux系统监控的基础命令:

​命令​ ​主要功能​ ​常用示例​
top/htop 实时查看CPU、内存、进程负载 top -bn1(批处理模式)
vmstat 报告进程、内存、分页、块IO、陷阱和CPU活动 vmstat 1 5(每秒刷新,共5次)
iostat 监控系统输入输出设备和CPU使用情况 iostat -dx 2(每2秒刷新)
free 显示内存使用情况 free -m(以MB为单位显示)
df 报告文件系统磁盘空间使用情况 df -h(人类可读格式)
iftop/nload 实时网络流量监控 iftop -i eth0(监控指定网卡)

这些命令为我们编写监控脚本提供了基础数据来源。

二、完整监控脚本实现

下面是一个综合性的监控脚本,它涵盖了CPU、内存、磁盘、IO等待和网络流量的监控,并支持邮件告警功能。

#!/bin/bash

#############################################################################
# 系统资源监控脚本
# 功能:监控CPU、内存、磁盘、IO等待和网络流量,支持邮件告警
# 配置说明:使用前请修改以下配置项以适应您的环境
#############################################################################

# ======================
# 核心配置区(必须修改)
# ======================

# 告警阈值配置
CPU_THRESHOLD=80        # CPU使用率阈值(%)
MEM_THRESHOLD=80        # 内存使用率阈值(%)
DISK_THRESHOLD=80       # 根分区磁盘使用率阈值(%)
IO_THRESHOLD=50         # IO await阈值(毫秒)
NET_THRESHOLD=10        # 网络流量阈值(MB/s)

# 网络监控配置
INTERFACE="eth0"        # 监控的网卡名称(通过ifconfig或ip addr查看)

# 邮件配置(以QQ邮箱为例)
MAIL_TO="your_email@qq.com"                 # 接收告警的邮箱
SMTP_USER="your_qq@qq.com"                  # 发件邮箱(需开启SMTP服务)
SMTP_PASSWORD="your_authorization_code"     # 邮箱授权码(不是登录密码)
SMTP_SERVER="smtp.qq.com"                   # SMTP服务器地址
SMTP_PORT="465"                             # SMTP端口

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

# ======================
# 函数定义区
# ======================

# 初始化邮件配置
setup_mail_config() {
    # 检查是否已安装msmtp
    if ! command -v msmtp &> /dev/null; then
        echo "[错误] msmtp未安装,请先执行安装: sudo apt install msmtp -y 或 sudo yum install msmtp -y"
        exit 1
    fi
    
    # 创建msmtp配置文件
    local MAIL_CONFIG="$HOME/.msmtprc"
    cat > "$MAIL_CONFIG" << EOF
# 默认账户
account default
host ${SMTP_SERVER}
port ${SMTP_PORT}
from ${SMTP_USER}
auth on
user ${SMTP_USER}
password ${SMTP_PASSWORD}
tls on
tls_starttls off
tls_certcheck off
logfile ${LOG_FILE}
EOF

    # 设置配置文件权限
    chmod 600 "$MAIL_CONFIG"
    echo "[信息] 邮件配置完成" >> "$LOG_FILE"
}

# 发送邮件函数
send_alert_mail() {
    local subject="$1"
    local content="$2"
    
    {
        echo "Subject: $subject"
        echo "From: $SMTP_USER"
        echo "To: $MAIL_TO"
        echo
        echo -e "$content"
        echo
        echo "监控时间: $(date '+%Y-%m-%d %H:%M:%S')"
        echo "主机名: $(hostname)"
    } | msmtp --from="$SMTP_USER" "$MAIL_TO" 2>> "$LOG_FILE"
}

# 记录日志函数
log_message() {
    echo "[$(date '+%Y-%m-%d %H:%M:%S')] $1" >> "$LOG_FILE"
}

# 检查CPU使用率
check_cpu() {
    local cpu_usage=$(top -bn1 | grep "Cpu(s)" | awk '{print $2 + $4}' | cut -d'%' -f1)
    local cpu_rounded=$(printf "%.0f" "$cpu_usage")
    
    if [ "$cpu_rounded" -ge "$CPU_THRESHOLD" ]; then
        send_alert_mail "CPU告警" "CPU使用率过高:${cpu_rounded}% (阈值:${CPU_THRESHOLD}%)"
        log_message "CPU使用率过高:${cpu_rounded}%"
    fi
}

# 检查内存使用率
check_memory() {
    local mem_usage=$(free | awk '/Mem/{printf "%.0f", $3/$2 * 100}')
    
    if [ "$mem_usage" -ge "$MEM_THRESHOLD" ]; then
        send_alert_mail "内存告警" "内存使用率过高:${mem_usage}% (阈值:${MEM_THRESHOLD}%)"
        log_message "内存使用率过高:${mem_usage}%"
    fi
}

# 检查磁盘使用率
check_disk() {
    local disk_usage=$(df -h / | awk 'NR==2{print $5}' | tr -d '%')
    
    if [ "$disk_usage" -ge "$DISK_THRESHOLD" ]; then
        send_alert_mail "磁盘告警" "根分区磁盘使用率过高:${disk_usage}% (阈值:${DISK_THRESHOLD}%)"
        log_message "磁盘使用率过高:${disk_usage}%"
    fi
}

# 检查IO等待时间
check_io() {
    if ! command -v iostat &> /dev/null; then
        log_message "警告:iostat未安装,无法监控IO状态"
        return
    fi
    
    local io_wait=$(iostat -x 1 2 | awk '/^avg-cpu/{getline; print $NF}' | tail -n1)
    local io_rounded=$(printf "%.0f" "$io_wait")
    
    if [ "$io_rounded" -ge "$IO_THRESHOLD" ]; then
        send_alert_mail "IO等待告警" "磁盘IO等待时间过高:${io_rounded}ms (阈值:${IO_THRESHOLD}ms)"
        log_message "IO等待时间过高:${io_rounded}ms"
    fi
}

# 检查网络流量
check_network() {
    if [ ! -d "/sys/class/net/$INTERFACE" ]; then
        log_message "错误:网络接口 $INTERFACE 不存在"
        return
    fi
    
    # 获取初始流量数据
    local rx_bytes_start=$(cat /sys/class/net/$INTERFACE/statistics/rx_bytes)
    local tx_bytes_start=$(cat /sys/class/net/$INTERFACE/statistics/tx_bytes)
    
    # 等待1秒再次测量
    sleep 1
    
    local rx_bytes_end=$(cat /sys/class/net/$INTERFACE/statistics/rx_bytes)
    local tx_bytes_end=$(cat /sys/class/net/$INTERFACE/statistics/tx_bytes)
    
    # 计算流量速率(MB/s)
    local rx_rate=$(( (rx_bytes_end - rx_bytes_start) / 1024 / 1024 ))
    local tx_rate=$(( (tx_bytes_end - tx_bytes_start) / 1024 / 1024 ))
    
    if [ "$rx_rate" -ge "$NET_THRESHOLD" ]; then
        send_alert_mail "网络下载流量告警" "下载流量过高:${rx_rate}MB/s (阈值:${NET_THRESHOLD}MB/s)"
        log_message "下载流量过高:${rx_rate}MB/s"
    fi
    
    if [ "$tx_rate" -ge "$NET_THRESHOLD" ]; then
        send_alert_mail "网络上载流量告警" "上传流量过高:${tx_rate}MB/s (阈值:${NET_THRESHOLD}MB/s)"
        log_message "上传流量过高:${tx_rate}MB/s"
    fi
}

# ======================
# 主程序
# ======================

# 初始化日志文件
if [ ! -f "$LOG_FILE" ]; then
    touch "$LOG_FILE"
    chmod 644 "$LOG_FILE"
fi

# 初始化邮件配置
setup_mail_config

log_message "开始系统监控检查..."

# 执行所有监控检查
check_cpu
check_memory
check_disk
check_io
check_network

log_message "系统监控检查完成"

三、脚本使用说明

1. 前置准备工作

在使用此脚本前,需要完成以下准备工作:

  1. ​安装必要工具​​:

    # Ubuntu/Debian系统
    sudo apt update
    sudo apt install sysstat msmtp mailutils -y
    
    # CentOS/RHEL系统
    sudo yum install sysstat msmtp mailx -y
  2. ​配置邮箱SMTP服务​​:

    • 登录您的QQ邮箱(或其他支持SMTP的邮箱)
    • 进入「设置」→「账户」
    • 开启「POP3/SMTP服务」
    • 获取「授权码」(不是邮箱密码)

2. 脚本配置

使用前,请修改脚本「核心配置区」中的以下参数:

  • ​告警阈值​​:根据您的需求调整各指标阈值
  • ​网络接口​​:通过ifconfigip addr命令查看并设置正确的网卡名称
  • ​邮箱配置​​:填写您的发件邮箱、授权码和收件邮箱

3. 运行方式

  1. 将脚本保存为system_monitor.sh
  2. 添加执行权限:
    chmod +x system_monitor.sh
  3. 手动测试运行:
    ./system_monitor.sh

4. 设置定时任务

要实现自动监控,需要设置cron定时任务:

  1. 编辑cron任务:
    crontab -e
  2. 添加以下行(每30分钟检查一次):
    */30 * * * * /path/to/system_monitor.sh > /dev/null 2>&1
  3. 保存并退出

四、故障排除与常见问题

  1. ​邮件发送失败​​:

    • 检查邮箱授权码是否正确(注意不是邮箱密码)
    • 确认SMTP服务器地址和端口是否正确
    • 检查系统防火墙是否允许SMTP通信
  2. ​命令不存在错误​​:

    • 确保已安装所有必要工具(sysstat、msmtp)
    • 对于IO监控,需要安装sysstat包
  3. ​网络接口不存在错误​​:

    • 使用ifconfigip addr命令确认正确的网卡名称
  4. ​脚本执行权限错误​​:

    • 使用chmod +x script.sh为脚本添加执行权限

五、进阶改进建议

当基本监控满足需求后,可以考虑以下进阶改进:

  1. ​添加进程监控​​:监控关键进程的存活状态

    check_process() {
        if ! pgrep -x "$1" > /dev/null; then
            echo "[错误] 进程 $1 未运行!"
        fi
    }
  2. ​数据可视化​​:将监控数据保存到数据库中,并使用Grafana等工具进行可视化展示

  3. ​集成专业监控工具​​:随着需求增长,可以考虑集成Zabbix、Prometheus等专业监控工具

  4. ​生成HTML报告​​:使用awk生成HTML格式的报告,更直观展示系统状态

六、总结

💎 ​​核心总结​

编写 Linux 系统监控脚本是一项非常实用的运维技能。其核心思路是:​​“采集 - 判断 - 报警”​​。

  1. 1.

    ​采集是关键​​:熟练使用 topfreedfiostat/sys/class/net/等命令和接口是基础。

  2. 2.

    ​判断要准确​​:在脚本中合理设置阈值(如CPU使用率80%),并进行数值比较。

  3. 3.

    ​报警须可靠​​:邮件报警是常见方式,务必正确配置SMTP。记得处理报警风暴,避免频繁发送。

  4. 4.

    ​自动化运行​​:通过 ​​cron​​ 让脚本在后台定时执行,实现真正自动化的监控。

  5. 5.

    ​记录很重要​​:详细的日志有助于问题排查和历史回顾。

对于初学者,可以从监控一两个关键指标(如CPU和磁盘)开始,逐步增加功能。对于复杂环境或更高要求,建议直接采用成熟的监控平台如 ​​Zabbix​​ 或 ​​Prometheus​​,它们提供了更完善的数据采集、存储、可视化、报警和扩展能力。

​注意事项​​:

  • 所有脚本应在测试环境验证后再投入生产环境使用
  • 定期检查日志文件(/var/log/system_monitor.log)以确保监控正常运行
  • 根据实际硬件性能和服务负载调整监控阈值

希望本文能帮助您构建有效的系统监控方案。如有任何问题或建议,欢迎交流讨论!


网站公告

今日签到

点亮在社区的每一天
去签到