宝塔面板的网站设置里有一个“并发数”选项,不少用户以为把它调低就能限制访问,但在Nginx环境下这个选项并不总是生效,它更多是为Apache环境准备的。要想在Nginx上精准控制并发,必须通过Nginx原生的limit_conn和limit_req两个模块实现。前者限制同时建立的连接数量,后者限制请求速率,二者配合才能防止资源被瞬间耗尽。下面先梳理这两者的区别,再给出宝塔面板中的具体配置步骤。

一、为什么宝塔面板自带并发限制经常失效
打开宝塔面板的网站设置,能看到“并发数”参数,这个参数对于使用Apache的站点会转换为MaxClients之类的指令,但如果你用的是Nginx,它并不会自动生成limit_conn或limit_req配置。Nginx默认没有开启这两个限流模块,因此仅靠面板里的并发数字,攻击者依然可以快速建立大量TCP连接或发送高频请求,把后端PHP进程和数据库连接池拖垮。
从资源消耗的角度看,并发连接数过高会直接占满Nginx的worker进程可用的文件描述符,同时每个连接都会占用内存缓冲区;请求速率过高则会让后端应用频繁创建销毁进程或线程,CPU和内存使用率飙升。这两种攻击方式对应的防护指令不同:limit_conn针对连接本身,limit_req针对请求速率。只配置其中一个,另一个维度仍然可能被打穿。
还有一个容易混淆的点:一个TCP连接上可以串行发送多个HTTP请求,所以“连接数不大”不代表“请求量不大”。反过来,大量空闲连接也会占用资源。理解这一点后,就能明白为什么需要同时配置两个模块,并在不同层级施加限制。
# 在 http 块中声明共享内存区域 limit_conn_zone $binary_remote_addr zone=conn_perip:10m; limit_req_zone $binary_remote_addr zone=req_perip:10m rate=10r/s;
二、在宝塔面板中写入Nginx限流配置
登录宝塔面板,进入网站管理,找到对应站点,点击“设置”后切换到“配置文件”标签页。这里会展示当前站点完整的Nginx配置内容。你需要先找到http块的位置,一般位于文件较上方,包含include和server等指令。把上面的两条limit_conn_zone和limit_req_zone声明放到http块内、任意server块之前。
这一步不能省略,因为limit_conn和limit_req必须引用已经定义好的共享内存区域,否则执行nginx -t检测时会报错zone "conn_perip" is not found。共享内存区域名称可以自定义,大小根据站点流量调整,10m大约能存储16万个IP地址的状态信息。配置完成后,再在server或具体的location块内添加限制指令。
下面是一个完整的站点配置示例,演示如何对根路径应用连接数和请求速率限制。其中limit_conn conn_perip 20表示每个IP最多同时保持20个连接,limit_req zone=req_perip burst=20 nodelay表示平均每秒允许10个请求,突发最多20个请求,超过突发值立即返回错误。
server {
listen 80;
server_name yourdomain.com;
location / {
limit_conn conn_perip 20;
limit_req zone=req_perip burst=20 nodelay;
proxy_pass http://127.0.0.1:8080;
}
}
保存后宝塔面板会自动执行配置重载。如果担心配置出错,可以先在面板自带的终端里运行nginx -t进行语法检测,确认无误后再手动执行nginx -s reload。很多用户配置完不生效,原因就是只改了站点的伪静态区域,而没有把limit_conn_zone加到http块,或者指令写在了错误的层级。
三、压测验证与参数优化
配置完成后需要实际压测,确认限流确实生效。可以在另一台机器上使用ab或wrk工具发起高并发请求。例如用ab -n 1000 -c 100 http://yourdomain.com/模拟100个并发连接、总共1000次请求,观察返回结果中是否出现503状态码。503是Nginx默认的限流响应状态,如果看到大量503,说明限制已经触发。
ab -n 1000 -c 100 http://yourdomain.com/
同时可以查看Nginx错误日志,宝塔面板默认日志路径在/www/wwwlogs/目录下。如果限流生效,日志里会出现类似limiting requests或limiting connections的记录。如果日志没有相关条目,但压测结果正常,就要检查配置是否真正加载。常见的坑是limit_req_zone的rate参数单位理解错误:rate=10r/s表示每秒10个请求,不是每分钟;如果写成rate=10r/m才是每分钟10个,瞬时请求很容易把后端打挂。
参数优化主要围绕burst和nodelay展开。如果不加nodelay,突发请求会排队等待,用户体验会表现为页面一直转圈;加上之后,超过平均速率但在burst范围内的请求立即处理,超出burst的才直接拒绝。对于普通企业站,rate=10r/s配合burst=20通常足够;如果是API接口,可以适当提高速率,但必须根据后端压测数据调整,避免误伤正常前后端分离调用。
另外还可以设置limit_req_status 429或limit_conn_status 429,让客户端明确知道被限流,而不是笼统的503。如果需要临时放行某个IP,可以在location块内使用limit_req zone=req_perip burst=100 nodelay;配合allow和deny规则,实现白名单豁免。限流不是越低越好,稳定运行一段时间后根据日志和实际访问情况动态调整,才能既防住资源耗尽,又保持正常业务流畅。