worker_processes本身不限流,单进程限流是各worker独立计数、分片宽松;全局限流需共享内存zone与原子操作,强控qps但有性能开销和配置约束。

worker_processes 本身不提供限流功能,它只控制工作进程数量。所谓“单进程限流”和“多进程全局限流”,实际是指限流策略作用的范围层级不同——前者在单个 worker 进程内生效,后者需跨所有 worker 进程协同实现全局效果。
单进程限流:每个 Worker 独立计数
基于 ngx_http_limit_conn_module 或 ngx_http_limit_req_module 的基础配置(如 limit_req zone=one burst=10),默认按 worker 进程隔离运行。每个 worker 持有自己的共享内存区域副本或本地计数器,彼此不通信。
- 例如设置 limit_req zone=api burst=20,若启动 4 个 worker,则每个进程最多允许 20 个突发请求,理论总突发容量达 80 —— 实际是“分片式宽松限流”
- 适用于轻量级防刷、连接数软限制等场景,开销低、无同步成本
- 缺点明显:无法真正控制全站 QPS 上限;高并发下各 worker 可能同时触发限流,但总量早已远超预期
全局限流:依赖共享内存与原子操作
要实现严格意义上的“全局限流”,必须启用 shared memory zone 并确保所有 worker 进程访问同一块共享内存区。Nginx 通过 atomic operations 和 spinlock 机制保障多进程对 zone 的安全读写。
- 关键配置示例:limit_req_zone $binary_remote_addr zone=global:10m rate=100r/s; 中的 10m 即为所有 worker 共享的内存区域,由 master 进程统一初始化
- 只有使用 $binary_remote_addr、$server_name 等可哈希键,且 zone 大小足够容纳键值对时,才能稳定支撑全局统计
- 注意:共享内存不是无限的,zone 满后新 key 将被剔除(LRU-like),可能造成部分客户端绕过限流
性能与一致性权衡
全局限流带来更强的控制力,但也引入额外开销:
- 每次请求需执行一次共享内存读+原子递增,比纯本地计数慢约 15%~30%(实测于 8 核服务器)
- 高并发写竞争下可能出现短暂的“计数漂移”,尤其在 burst 较大、rate 接近极限时
- 若未配 limit_req_log_level warn 和 limit_req_status 429,失败请求不易被监控捕获
推荐实践路径
- 先用单进程限流做快速防护(如防爬虫连接突增),观察 access.log 中 limit_req 的 hit 频次
- 确认需强控总 QPS 后,再启用 shared zone,并配合 burst + nodelay 控制响应延迟毛刺
- 容器化部署时,务必检查 /proc/sys/kernel/shmmax 是否大于 zone 总大小,否则共享内存创建失败,限流退化为单进程行为











