1. 为什么需要监控Linux连接数?
在运维工作中,服务器连接数是一个关键的性能指标。当我在某次值班时遇到线上服务响应缓慢的情况,排查后发现是因为某台Nginx服务器的TCP连接数突破了5万,导致新连接无法建立。这种问题如果能在早期发现并处理,完全可以避免业务中断。
连接数监控的典型场景包括:
- Web服务器(Nginx/Apache)的并发连接数监控
- 数据库(MySQL/Redis)的连接池使用情况
- 自定义TCP服务的客户端连接数统计
- 异常连接(如DDoS攻击)的早期发现
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 连接数统计的几种技术方案
2.1 使用netstat命令
最基础的统计方法是使用netstat命令:
bash复制netstat -ant | grep -E ':80|:443' | wc -l
这个命令会统计80和443端口的TCP连接数。但需要注意:
- netstat在高连接数时性能较差(超过1万连接时可能卡顿)
- 需要根据实际业务端口调整过滤条件
- 在较新Linux版本中建议改用ss命令
2.2 使用更高效的ss命令
ss(socket statistics)是netstat的现代替代品,性能更好:
bash复制ss -s | grep 'TCP:'
输出示例:
code复制TCP: 3271 (estab 42, closed 3219, orphaned 0, synrecv 0, timewait 3219/0), ports 0
其中estab表示当前活跃连接数。
2.3 通过/proc文件系统获取
Linux系统在/proc/net/tcp和/proc/net/tcp6文件中实时记录了所有TCP连接信息:
bash复制awk 'END{print NR}' /proc/net/tcp
这种方法性能最好,但需要处理十六进制转换(比如端口号是16进制的)。
3. 构建自动化监控脚本
3.1 基础监控脚本
创建一个shell脚本conn_monitor.sh:
bash复制#!/bin/bash
# 获取当前连接数
CONN_COUNT=$(ss -ant | grep -v 'State' | wc -l)
# 设置告警阈值
WARNING=1000
CRITICAL=5000
# 判断并记录日志
if [ $CONN_COUNT -gt $CRITICAL ]; then
echo "$(date '+%F %T') CRITICAL - Connections: $CONN_COUNT" >> /var/log/conn_monitor.log
exit 2
elif [ $CONN_COUNT -gt $WARNING ]; then
echo "$(date '+%F %T') WARNING - Connections: $CONN_COUNT" >> /var/log/conn_monitor.log
exit 1
else
echo "$(date '+%F %T') OK - Connections: $CONN_COUNT" >> /var/log/conn_monitor.log
exit 0
fi
3.2 增强版脚本(带端口分组统计)
更实用的版本可以按端口统计:
bash复制#!/bin/bash
# 定义要监控的端口列表
PORTS=(80 443 3306 6379)
for port in "${PORTS[@]}"; do
count=$(ss -ant "sport = :$port" | grep -v 'State' | wc -l)
echo "Port $port connections: $count"
# 这里可以添加针对不同端口的阈值判断
done
4. 钉钉机器人告警集成
4.1 创建钉钉机器人
- 在钉钉群设置中添加自定义机器人
- 选择"自定义"类型,设置机器人名称
- 记录下Webhook地址(包含access_token参数)
- 设置安全设置(建议使用"加签"方式)
4.2 发送告警到钉钉
修改监控脚本,添加钉钉通知功能:
bash复制send_dingding_alert() {
local message="$1"
local webhook="https://oapi.dingtalk.com/robot/send?access_token=YOUR_TOKEN"
local secret="YOUR_SECRET"
# 计算签名
timestamp=$(date +%s%3N)
sign=$(echo -ne "$timestamp\n$secret" | openssl dgst -sha256 -hmac "$secret" -binary | base64)
# 构造JSON数据
json_data=$(cat <<EOF
{
"msgtype": "text",
"text": {
"content": "Linux连接数告警\n$message"
},
"at": {
"isAtAll": false
}
}
EOF
)
# 发送请求
curl -s "$webhook" \
-H "Content-Type: application/json" \
-d "$json_data" \
--connect-timeout 3 \
--max-time 5
}
4.3 完整集成示例
将告警功能整合到监控脚本中:
bash复制#!/bin/bash
# 配置部分
DINGDING_TOKEN="YOUR_TOKEN"
DINGDING_SECRET="YOUR_SECRET"
WARNING=1000
CRITICAL=5000
# 获取连接数
CONN_COUNT=$(ss -ant | grep -v 'State' | wc -l)
# 告警判断
if [ $CONN_COUNT -gt $CRITICAL ]; then
send_dingding_alert "CRITICAL: 当前连接数 ${CONN_COUNT} 超过临界值 ${CRITICAL}"
exit 2
elif [ $CONN_COUNT -gt $WARNING ]; then
send_dingding_alert "WARNING: 当前连接数 ${CONN_COUNT} 超过警告值 ${WARNING}"
exit 1
else
echo "INFO: 当前连接数正常 (${CONN_COUNT})"
exit 0
fi
5. 生产环境优化建议
5.1 性能优化技巧
- 使用ss替代netstat:ss直接读取内核数据,性能更好
- 减少采样频率:一般5分钟一次足够,高频监控使用专门的监控系统
- 避免重复统计:缓存结果用于多次判断
- 使用并发处理:当监控多台服务器时,用parallel或xargs并行执行
5.2 安全注意事项
- 钉钉webhook token要妥善保管,不要写入脚本
- 建议将敏感信息存储在环境变量或配置文件中
- 设置合理的权限(如脚本只允许特定用户执行)
- 添加执行锁机制,防止脚本重复执行
5.3 日志与记录
完善的监控系统应该记录历史数据:
bash复制# 记录到CSV文件
echo "$(date '+%F %T'),$CONN_COUNT" >> /var/log/connections_history.csv
# 使用rrdtool存储时间序列数据
rrdtool update /var/lib/monitoring/connections.rrd N:$CONN_COUNT
6. 扩展方案:Prometheus+Grafana监控
对于大规模环境,建议使用专业监控系统:
- 安装node_exporter(自带tcp_connection统计)
- 配置Prometheus抓取指标
- 在Grafana中创建监控面板
- 设置Alertmanager告警规则
关键指标示例:
yaml复制# Prometheus告警规则
groups:
- name: tcp_connections
rules:
- alert: HighTCPConnections
expr: node_netstat_Tcp_CurrEstab > 5000
for: 5m
labels:
severity: warning
annotations:
summary: "High TCP connections ({{ $value }})"
7. 常见问题排查
7.1 连接数突然飙升
排查步骤:
- 使用ss -antp查看连接详情
- 检查是否有异常IP(netstat -ant | awk '{print $5}' | cut -d: -f1 | sort | uniq -c | sort -n)
- 分析nginx/apache日志(如果有)
- 检查是否有定时任务或爬虫
7.2 钉钉消息发送失败
检查点:
- 网络连通性(curl -v测试)
- 签名计算是否正确(时间戳同步问题)
- 机器人是否被禁用
- 消息内容是否包含特殊字符
7.3 脚本执行权限问题
确保:
- 脚本有执行权限(chmod +x)
- 定时任务的环境变量正确
- 日志目录可写入
- 依赖命令(ss、jq等)已安装
8. 实际案例分享
某电商公司在618大促期间使用这套方案成功避免了服务中断:
- 凌晨2点收到钉钉告警(连接数突破8000)
- 快速定位到是某个爬虫异常导致
- 临时封禁异常IP
- 自动扩容了2台nginx服务器
- 整个过程在15分钟内完成,用户无感知
关键改进点:
- 在脚本中添加了自动IP封禁功能
- 设置了多级告警(不同级别通知不同人员)
- 增加了连接数预测功能(基于历史数据)
