以下是一个用于检测网卡流量并按指定格式记录日志的Shell脚本,支持自定义监控间隔、网卡选择和日志轮转功能:
#!/bin/bash
# 网卡流量监控脚本
# 日志格式:时间戳,网卡名称,接收流量(KB),发送流量(KB),总流量(KB)
# 配置参数
INTERFACE="eth0" # 监控的网卡名称
LOG_DIR="/var/log/network" # 日志存放目录
LOG_NAME="traffic.log" # 日志文件名
MAX_LOG_DAYS=30 # 日志保留天数
INTERVAL=10 # 监控间隔(秒)
# 创建日志目录
mkdir -p "$LOG_DIR"
# 初始化流量计数器
declare -A prev_bytes
init_counters() {
while read dev rbytes tbytes; do
prev_bytes["$dev"]="$rbytes:$tbytes"
done < <(grep "$INTERFACE" /proc/net/dev | awk '{print $1,$2,$10}')
}
# 获取当前流量
get_traffic() {
local curr_rbytes curr_tbytes
read curr_rbytes curr_tbytes < <(grep "$INTERFACE" /proc/net/dev | awk '{print $2,$10}')
echo "$curr_rbytes $curr_tbytes"
}
# 计算流量差值(KB)
calculate() {
local prev=$1 curr=$2
local diff=$(( (curr - prev) / 1024 ))
echo $diff
}
# 生成时间戳
timestamp() {
date '+%Y-%m-%d %H:%M:%S'
}
# 日志轮转管理
manage_logs() {
find "$LOG_DIR" -name "*.log" -mtime +$MAX_LOG_DAYS -delete
}
# 主监控循环
main() {
echo "时间戳,网卡名称,接收流量(KB),发送流量(KB),总流量(KB)" >> "$LOG_DIR/$LOG_NAME"
init_counters
while true; do
sleep $INTERVAL
# 获取当前流量
read curr_rbytes curr_tbytes < <(get_traffic)
# 解析上一次值
IFS=':' read prev_rbytes prev_tbytes <<< "${prev_bytes[$INTERFACE]}"
# 计算增量
rdiff=$(calculate $prev_rbytes $curr_rbytes)
tdiff=$(calculate $prev_tbytes $curr_tbytes)
total=$(( rdiff + tdiff ))
# 记录日志
echo "$(timestamp),$INTERFACE,$rdiff,$tdiff,$total" >> "$LOG_DIR/$LOG_NAME"
# 更新计数器
prev_bytes["$INTERFACE"]="$curr_rbytes:$curr_tbytes"
# 每日0点执行日志管理
if [ $(date +%H%M) == "0000" ]; then
manage_logs
fi
done
}
# 异常处理
trap "echo '监控被用户中断'; exit 0" SIGINT
trap "echo '发生未捕获错误'; exit 1" ERR
# 执行主函数
main
使用说明
1、配置参数调整
修改 INTERFACE 为目标网卡(通过 ip link 查看可用网卡)
调整 INTERVAL 监控频率(建议≥5秒)
2、首次运行授权
chmod +x net_monitor.sh
sudo ./net_monitor.sh # 需要root权限读取/proc文件
3、查看实时日志
tail -f /var/log/network/traffic.log
日志格式示例
时间戳,网卡名称,接收流量(KB),发送流量(KB),总流量(KB)
2023-10-05 14:30:00,eth0,1024,2048,3072
2023-10-05 14:30:10,eth0,512,4096,4608
扩展功能
1. 多网卡监控
修改主函数支持多个网卡:
INTERFACES=("eth0" "wlan0")
main() {
for intf in "${INTERFACES[@]}"; do
# 采集每个网卡数据
done
}
2. 动态单位转换
增加智能单位显示:
format_bytes() {
local bytes=$1
if [ $bytes -gt 1048576 ]; then
echo "$(( bytes/1048576 )) GB"
elif [ $bytes -gt 1024 ]; then
echo "$(( bytes/1024 )) MB"
else
echo "$bytes KB"
fi
}
3. 告警阈值
添加流量超限通知:
ALERT_THRESHOLD=100000 # 100MB
if [ $total -gt $ALERT_THRESHOLD ]; then
echo "流量超标警告:$total KB" | mail -s "网络告警" admin@example.com
fi
部署建议
1、后台运行
nohup sudo ./net_monitor.sh > /dev/null 2>&1 &
2、系统服务化
创建systemd服务文件 /etc/systemd/system/netmon.service:
[Unit]
Description=Network Traffic Monitor
[Service]
ExecStart=/usr/local/bin/net_monitor.sh
Restart=always
[Install]
WantedBy=multi-user.target
注意事项
1、精度误差
采样间隔越短精度越高,但会增加系统负载
1024进制转换会产生小数误差
2、虚拟化环境
KVM/Xen等虚拟网卡需特殊处理(过滤virbr、vnet前缀)
3、容器网络
Docker创建的veth设备需要额外监控逻辑
通过此脚本可实现企业级网络流量监控,数据可直接导入Excel/PowerBI生成流量趋势图,或对接Zabbix等监控平台实现可视化告警。