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

使用 Shell 脚本监控服务器 IOWait 并发送邮件告警

前言

1. IO Wait 简介

2. 获取 IOWait 的方法

3. Shell 脚本实现

脚本说明

4. 常见问题与解决

4.1 iowait 取到空值

4.2 awk 比较浮点数报错

4.3 多收件人邮件只收到了部分邮箱

4.4 测试告警

5. 总结

前言

在生产环境中,磁盘 IO 瓶颈是影响服务器性能的重要因素之一。本文介绍如何用 Shell 脚本监控 IO Wait,并在超过阈值时通过邮箱告警,同时讨论多收件人和邮件发送中常见的问题及解决方法。


1. IO Wait 简介

  • IOWait 是 CPU 等待磁盘或网络 IO 完成的时间百分比。

  • 当 IOWait 高于阈值时,意味着系统可能出现 IO 瓶颈,需要关注磁盘性能。


2. 获取 IOWait 的方法

我们使用 iostat 命令获取 CPU IO Wait 值:

iostat -cy 1 1 | awk '/^ /{print $4}'

说明:

  • -c:显示 CPU 使用情况

  • -y:跳过平均值(可选)

  • 1 1:每隔 1 秒采样一次,只输出一次

  • awk '/^ /{print $4}':匹配数据行,取第 4 列(%iowait)

注意:不能直接用 awk 'END{print $4}',因为最后一行可能是空行或表头,导致取到空值。


3. Shell 脚本实现

下面是一个完整示例,带告警邮件功能:

#!/bin/bash#设置阈值(设置负数用于测试)
IOWAIT_WARNING=-1#设置邮件收件人
MAIL_TO="3426848201@qq.com,2270993679@qq.com"#邮件标题
TITLE="服务器IO等待告警"#iowait获取
iowait=$(iostat -cy 1 1 | awk '/^ /{print $4}')#获取当前系统时间
TIME=$(date +"%F %T")#判断iowait是否为空,防止误报
if [ -z "$iowait" ]; thenecho "iowait值为空"exit 0
else#判断是否大于阈值,大于则发送邮件告警if awk "BEGIN {exit !($iowait > $IOWAIT_WARNING)}"; thenwarning_info="${TIME}主机: $(hostname)iowait当前值为: ${iowait}%已超过阈值: ${IOWAIT_WARNING}%"(echo "Subject: $TITLE"echo "To: $MAIL_TO"echoecho -e "$warning_info") | msmtp -telseecho "iowait值正常" fi
fi

脚本说明

  1. 变量说明

    • IOWAIT_WARNING:告警阈值,可在测试时设置负数强制触发

    • MAIL_TO:收件人,多收件人空格分隔

    • TITLE:邮件标题

  2. 邮件发送

    • msmtp -t 从邮件头读取收件人 To: 和标题 Subject:

    • 如果在 /etc/msmtprc 已配置 from,脚本中无需再写 From:

    • 多收件人时最好用空格或逗号分隔,但不同 SMTP 对空格/逗号解析可能不同,必要时分开发送。


4. 常见问题与解决

4.1 iowait 取到空值

  • 原因:awk 'END{print $4}' 可能取到空行或表头

  • 解决:使用 /^ /{v=$4} END{print v} 或直接 iostat -cy 1 1 | awk '/^ /{print $4}'


4.2 awk 比较浮点数报错

  • 原因:小数点在 Shell 展开时可能导致语法错误

  • 解决:使用 awk -v io="$iowait" -v th="$IOWAIT_WARNING" 传入变量

     补充:

  • -v io="$iowait"
    把 shell 变量 $iowait 传给 awk 内部变量 io

  • -v th="$IOWAIT_WARNING"
    把阈值 $IOWAIT_WARNING 传给 awk 内部变量 th

  • 'BEGIN {exit !(io > th)}'

    • BEGIN 块在 awk 开始处理任何输入之前执行

    • io > th 为真时,!(io > th) 为假,exit 0 → awk 返回成功

    • io > th 为假时,!(io > th) 为真,exit 1 → awk 返回失败


4.3 多收件人邮件只收到了部分邮箱

  • 原因:

    1. SMTP 服务器限制,只允许发给同域邮箱

    2. 收件人不存在或拼写错误

    3. 邮件头 To: 与 SMTP 命令行不匹配

  • 解决:

    • 确保邮箱有效

    • 使用 msmtp -t 并在 To: 中列出所有收件人

    • 测试时可先用同域邮箱确保收全


4.4 测试告警

  • 可以将阈值设为负数,或临时把 $iowait 赋值为大于阈值的值,强制触发邮件发送逻辑:

iowait=99.99

4.5 补充知识

awk 的退出码与 shell 的 if

  • shell 在执行一条命令后,可以通过 $? 取到退出状态

  • if 判断的是真假:退出状态为 0 表示“真”(success),非 0 表示“假”(failure)。

  • awk 程序里执行 exit N,退出码就是 N,shell 能接收到。


 awk 里布尔运算

  • 在 awk 中,布尔表达式 ($iowait > $THRESHOLD) 的值是真或假:
    1
    0

  • ! 是逻辑非运算符:
    !1 = 0
    !0 = 1


为什么写 exit !($iowait > $THRESHOLD)

逐步展开:

  • 假设 $iowait > $THRESHOLD → 表达式值 1!1 = 0exit 0
    shell if 看到退出码 0,认为真,进入 then。

  • 假设 $iowait$THRESHOLD → 表达式值 0!0 = 1exit 1
    shell if 看到退出码 1,认为假,跳过 then。

所以这句相当于:

“如果 $iowait 大于 $THRESHOLD,awk 以状态码 0 退出(shell if 真);
否则 awk 以状态码 1 退出(shell if 假)。”


5. 总结

  • 使用 Shell 脚本 + iostat 可以轻松监控服务器 IO Wait

  • 告警邮件可用 msmtpmailx 发送,多收件人需注意 SMTP 限制

  • 浮点比较、空值检查和邮件头书写是脚本稳定性的关键点


文章转载自:

http://dBbMyVPf.gwdnL.cn
http://729rk4IK.gwdnL.cn
http://2u5CcjGL.gwdnL.cn
http://CnDkZSki.gwdnL.cn
http://OUwynblY.gwdnL.cn
http://yHDzGzOj.gwdnL.cn
http://SHsGY77k.gwdnL.cn
http://hIaeGNqY.gwdnL.cn
http://PS61enC0.gwdnL.cn
http://xdn0bDBF.gwdnL.cn
http://P3WkYrM3.gwdnL.cn
http://ezdzvidL.gwdnL.cn
http://LKMIRHaF.gwdnL.cn
http://7hrdMc0q.gwdnL.cn
http://C0bQCNKX.gwdnL.cn
http://MNMFIDQs.gwdnL.cn
http://ddz26YJu.gwdnL.cn
http://saVDzLI9.gwdnL.cn
http://jTiVwk6x.gwdnL.cn
http://n4YYiuYR.gwdnL.cn
http://vkPkQgCH.gwdnL.cn
http://4d4kpK6z.gwdnL.cn
http://NZBXLNNG.gwdnL.cn
http://yKT8rpnk.gwdnL.cn
http://MhJDSn6r.gwdnL.cn
http://c9HHZWuh.gwdnL.cn
http://aIxN2urL.gwdnL.cn
http://Wxgh8sW0.gwdnL.cn
http://O48IJ0Ar.gwdnL.cn
http://GCYusBys.gwdnL.cn
http://www.dtcms.com/a/370631.html

相关文章:

  • Python数据可视化科技图表绘制系列教程(六)
  • [Upscayl图像增强] docs | 前端 | Electron工具(web->app)
  • 同态加密库(Google FHE)
  • Qt自定义列表项与QListWidget学习
  • MySQL 高可用方案之 MHA 架构搭建与实践
  • 天津大学2024-2025 预推免 第一批机试题目纯暴力题解
  • 金属也有“记忆力”?—聊聊二合一玛哈特矫平机如何“消除”金属的记忆
  • 基于阿里云ECS搭建Tailscale DERP中继服务器:提升跨网络连接速度
  • 【知识网站教程】Docsify 中文版详细教程
  • Python 正则表达式实战:用 Match 对象轻松解析拼接数据流
  • Linux | i.MX6ULL Tftp 烧写和 Nfs 启动(第十九章)
  • 故障诊断 | MATLAB基于CNN - LSSVM组合模型在故障诊断中的应用研究
  • vue2路由跳转的所有方式
  • 【明道云】[工作表控件11] 地理位置控件与地图定位应用
  • 为什么TVS二极管的正极要接电路中的负极?-ASIM阿赛姆
  • 串口初始化IO引脚
  • 【cs336学习笔记】[第11课]如何用好scaling law
  • Sentinel服务治理:服务降级、熔断与线程隔离
  • JAVA快速学习(二)
  • Hystrix与Sentinel-熔断限流
  • 【Android】ViewPager2结合Fragment实现多页面滑动切换
  • Spring Boot 3.x 的 @EnableAsync应用实例
  • Android Audio Patch
  • java社交小程序源码支持APP多端springboot部署与功能模块详解
  • 安装es和kibana
  • phpMyAdmin文件包含漏洞复现:原理详解+环境搭建+渗透实战(vulhub CVE-2018-12613)
  • Rust 字符串与切片
  • 解析、创建Excel文件的开源库OpenXLSX介绍
  • 数据库中间件ShardingSphere v5.2.1
  • 大模型推理时的加速思路?