监控硬盘利用率
硬盘利用率监控脚本:分区级别的磁盘空间预警
使用fdisk来分析硬盘使用信息
!/bin/bash
配置参数
THRESHOLD=80 # 磁盘使用率报警阈值(%)
COOLDOWN=3600 # 重复报警冷却时间(秒)
MAIL="example@mail.com"
LOG_FILE="/var/log/disk_monitor.log"
ALERT_HISTORY="/var/log/disk_alert_history.log" # 记录报警历史,用于冷却控制
初始化文件
touch $LOG_FILE $ALERT_HISTORY
chmod 644 $LOG_FILE $ALERT_HISTORY
日志函数
log() {
echo "[$(date +%F" "%H:%M:%S)] $1" >> $LOG_FILE
}
获取系统信息
get_system_info() {
DATE=$(date +%F" "%H:%M)
IP=$(hostname -I | awk '{print $1}') # 兼容更多系统的IP获取方式
if [ -z "$IP" ]; then
IP=$(ifconfig | grep 'inet ' | grep -v '127.0.0.1' | head -1 | awk '{print $2}')
fi
}
获取总磁盘信息(兼容sd、vd、nvme等类型)
get_total_disk() {
TOTAL=$(fdisk -l 2>/dev/null | awk -F'[: ]+' '
BEGIN{OFS="="}
/^Disk \/dev\/(sd|vd|nvme)/{ # 支持多种磁盘命名
size=$3
if ($4 == "GB") size=$3
else if ($4 == "TB") size=$3*1024 # 转换TB为GB
printf "%s=%.0fG,", $2, size
}
')
# 移除末尾多余的逗号
TOTAL=${TOTAL%,}
}
检查是否在冷却期内
is_in_cooldown() {
local part=$1
local current_time=$(date +%s)
# 查找该分区最后一次报警时间
local last_alert=$(grep "$part" $ALERT_HISTORY | tail -1 | awk '{print $1}')
if [ -n "$last_alert" ]; then
local time_diff=$((current_time - last_alert))
if [ $time_diff -lt $COOLDOWN ]; then
return 0 # 在冷却期内
fi
fi
return 1 # 不在冷却期内
}
记录报警历史
record_alert() {
local part=$1
echo "$(date +%s) $part" >> $ALERT_HISTORY
}
发送报警邮件
send_alert() {
local part=$1
local use=$2
local mount=$3
# 检查冷却期
if is_in_cooldown "$part"; then
log "分区 $part 仍在冷却期内,暂不重复报警"
return
fi
SUBJECT="磁盘报警: $IP 分区 $part 使用率过高"
BODY="
服务器磁盘分区使用率超过阈值,请及时处理!
日期时间: $DATE
服务器IP: $IP
总磁盘容量: $TOTAL
问题分区: $part
使用率: $use%
挂载点: $mount
报警阈值: $THRESHOLD%
"
echo "$BODY" | mail -s "$SUBJECT" $MAIL
record_alert "$part"
log "已发送 $part 报警邮件至 $MAIL"
}
主监控逻辑
main() {
get_system_info
get_total_disk
log "开始磁盘监控检查 - 总磁盘: $TOTAL"
# 遍历所有挂载的磁盘分区(排除tmpfs等虚拟文件系统)
df -h | awk 'BEGIN{OFS="="}/^\/dev\/(sd|vd|nvme)/{print $1, $5+0, $6}' | while read -r line; do
PART=$(echo $line | cut -d"=" -f1)
USE=$(echo $line | cut -d"=" -f2)
MOUNT=$(echo $line | cut -d"=" -f3)
log "检查分区 $PART - 使用率: $USE% 挂载点: $MOUNT"
if [ $USE -gt $THRESHOLD ]; then
log "分区 $PART 使用率 $USE% 超过阈值 $THRESHOLD%"
send_alert "$PART" "$USE" "$MOUNT"
fi
done
}
执行主函数
main