服务器带宽限速脚本防止爬虫恶意占用:服务器带宽限速脚本

服务器带宽限速脚本:用几行命令防止爬虫恶意占用

如果某天你发现服务器CPU和内存正常,但带宽跑满,网站响应变慢,大概率是有爬虫或恶意程序在疯狂下载。
手动封IP治标不治本,不如写一个自动限速脚本,超出流量阈值的IP自动降速。
本文以CentOS 7/Ubuntu 20.04为例,手把手教你实现。

你需要准备什么

  • 一台Linux服务器(已开通root权限)
  • 确认网卡名称:运行 ip link show 找到对外网卡(如 eth0、ens3)
  • 安装以下工具:
  • iftop:实时查看带宽占用者
  • iptablestc:流量控制和限速

安装命令(以CentOS为例):

yum install -y iftop iptables-services iproute-tc

Ubuntu下:

apt install -y iftop iptables iproute2

核心脚本:自动限速高带宽IP

以下脚本会每隔一段时间扫描当前带宽排行,对超过设定阈值的IP进行限速。
新建文件 /root/bandwidth_limit.sh,写入以下内容:

#!/bin/bash
# 带宽限速脚本 - 防止爬虫恶意占用
# 设置阈值 (单位:Kbps,这里设为 50Mbps = 50000Kbps)
LIMIT=50000
# 网卡名称
INTERFACE="eth0"
# 获取当前流量最大的IP(排除本地回环和广播)
IP_LIST=$(iftop -t -N -n -s 2 2>/dev/null | grep -E "^[0-9]{1,3}\.[0-9]{1,3}" | awk '{print $2}' | sort -u)
for IP in $IP_LIST; do
    # 获取该IP当前出站流量速率(单位:Kbps)
    RATE=$(iftop -t -N -n -s 1 -f "dst host $IP" 2>/dev/null | grep "Total" | awk '{print $3}' | head -1)
    # 如果速率数值是数字且大于阈值
    if [[ "$RATE" =~ ^[0-9]+(\.[0-9]+)?$ ]] && (( $(echo "$RATE > $LIMIT" | bc -l) )); then
        # 如果该IP尚未被限速,则添加tc规则
        if ! tc filter show dev $INTERFACE | grep -q "$IP"; then
            tc qdisc add dev $INTERFACE root handle 1: htb default 30
            tc class add dev $INTERFACE parent 1: classid 1:1 htb rate ${LIMIT}kbps
            tc filter add dev $INTERFACE parent 1: protocol ip prio 1 u32 match ip dst $IP flowid 1:1
            echo "$(date): 已限速IP $IP (当前速率 $RATE Kbps)" >> /var/log/bandwidth_limit.log
        fi
    fi
done

保存后赋予执行权限:chmod +x /root/bandwidth_limit.sh

关键解释

  • iftop -t -N -n -s 2 以文本模式显示2秒流量,过滤出IP列表。
  • tc 命令创建HTB队列,限制目标IP的出口带宽。
  • 日志记录到 /var/log/bandwidth_limit.log,方便排查。

设置自动运行:定时任务

脚本需要每1-2分钟执行一次才能及时反应。
编辑crontab:

crontab -e

添加以下行:

*/2 * * * * /root/bandwidth_limit.sh

保存后重启cron:systemctl restart crond(CentOS)或 systemctl restart cron(Ubuntu)。

如果你希望开机自启,也可以将脚本做成systemd服务,但使用cron更简单。

避坑指南与常见问题

1. 脚本未生效,查看日志无记录
检查iftop是否正常输出:手动运行 /root/bandwidth_limit.sh,观察报错。常见原因是缺少 bc 工具,安装即可:yum install -y bc

2. tc规则不断累加导致失效
上面脚本每次执行都会尝试添加新规则,但实际上规则已存在时会报错。改进办法:每次执行前先删除旧规则:tc qdisc del dev $INTERFACE root 2>/dev/null。但这样会清空所有规则,建议将删除操作放在脚本开头。

3. 限速后正常用户被误伤
脚本以IP为粒度,如果多个正常用户共享一个公网IP(如公司出口),可能会一起被限。可以改用连接数或HTTP请求频率等更精准的指标。

4. iptables限制带宽更方便?
iptables本身不具备带宽限制功能,一般结合tc使用。本脚本纯tc实现,无需额外iptables规则。

5. 服务器重启后规则丢失
tc规则重启即消失,所以必须依赖cron定时运行脚本,重启后cron自动拉起。或者将tc规则保存到启动脚本中,但cron方案更简单。

验证限速效果

运行以下命令查看当前tc队列规则:

tc qdisc show dev eth0
tc class show dev eth0
tc filter show dev eth0

如果看到针对某个IP的过滤器和class,说明限速已生效。

你还可以在另一台机器上测试:通过大文件下载从服务器拉取文件,观察服务器端iftop显示的速率是否被限制在你设定的阈值附近。

高频问题解答

Q:脚本如何调整限速阈值?
修改脚本开头的 LIMIT=50000(单位Kbps),比如想限制为10Mbps,改成 LIMIT=10000

Q:爬虫IP经常变,脚本能自动处理吗?
可以,脚本每2分钟扫描一次,新出现的IP只要超过阈值就会被限速。需要留意的是,如果爬虫更换IP速度极快,可能需要缩短扫描间隔到1分钟。

Q:我想永久解除某个IP的限速怎么办?
手动删除对应的tc规则即可:tc filter del dev eth0 protocol ip prio 1 u32 match ip dst X.X.X.X,然后删除对应class。更简单的方法是重启一次tc:tc qdisc del dev eth0 root,再让脚本重新创建。

总结

借助iftop和tc组合,你可以用十几行脚本实现自动带宽限速,有效抵御爬虫恶意占用。
按照本文步骤先执行一遍,再根据自身网络环境调整阈值和扫描间隔即可。
遇到异常时优先回看避坑部分,多数问题都能解决。
如果服务器上运行着重要业务,建议先在测试环境验证脚本可靠性。

如果你对tc高级配置或结合nginx限流感兴趣,可以继续阅读本站相关文章。

分享到:
上一篇
定时任务自动备份全站数据库与模型文件新手实操指南
下一篇
宝塔面板批量清理网站垃圾缓存与日志
1
系统公告

机房迁移升级通知

尊敬的用户: IP 段 103.23.148.x、156.224.29.x 原香港一区线路波动、攻击频繁,平台定于 7 月 5 日凌晨分批迁移至香港 GIA 机房,硬件升级 AMD 铂金机型。 迁移均在凌晨操作,最大程度降低业务影响,迁移期间服务器临时关机; 升级后配置不降低、费用不涨价,数据默认同步迁移; 迁移后 IP 全部更换,请及时修改域名解析、防火墙白名单; 建议提前备份重要数据,有问题可联系在线客服。 感谢理解与支持! 泽御云科技 2026.06.30
服务中心
客服
在线客服
24小时为您服务
咨询
联系我们
联系我们,为您的业务提供专属服务。
24/7 技术支持
如果您遇到寻求进一步的帮助,请过工单与我们进行联系。
24/7 即时支持
泽御云
售前客服
泽御云
泽御云
售后客服
泽御云
技术支持
评价
您对当前页面的整体感受是否满意?
😞
非常不满意
😕
不满意
😐
一般
🙂
满意
😊
非常满意