千万级活跃IP场景下,limit_req_zone内存需按64字节/IP精确计算并预留20%~30%冗余,如800万IP至少需488MB,建议配600m;应分层拆分zone、避免全局大zone、监控使用率超85%及时扩容。

千万级活跃 IP 场景下,limit_req_zone 的内存配置不能靠经验估算,必须基于真实活跃基数建模,否则极易因状态存储不足导致限流失效或资源严重浪费。
按活跃 IP 数精确计算共享内存大小
每个 IP 状态在 64 位系统中约占 64 字节(使用 $binary_remote_addr 可避免字符串开销);1MB 共享内存 ≈ 存储 1.6 万个活跃 IP。因此:
- 若日志/监控统计出峰值活跃 IP 为 800 万,则理论最小内存 = 8,000,000 × 64 ÷ 1,048,576 ≈ 488 MB
- 生产环境需预留 20%~30% 冗余,建议配置
zone=ip_limit:600m - 切忌直接写
10m或100m—— 对千万级流量,这点空间连 0.1% 的活跃 IP 都存不下
拆分 zone 实现多维度、可伸缩的流控
单 zone 承载全部 IP 在千万级下易成性能瓶颈,应按业务特征分层建模:
-
高频路径独立 zone:如
/api/v1/login单独用zone=login_limit:200m,rate 设严(如 5r/s),burst 控小(如 10) -
低频静态资源共用轻量 zone:如
/static/使用zone=static_limit:50m,rate 放宽(100r/s),不设 burst -
按地域或运营商分流 zone:结合
map提取$geoip_country_code或 AS 号,为高风险区域单独限流
规避共享内存争抢与状态抖动
千万级并发下,worker 进程频繁读写同一 zone 容易引发锁竞争和状态覆盖:
- 启用
worker_connections与worker_processes auto匹配 CPU 核数,减少跨 worker 状态同步压力 - 避免在
http块顶层定义超大 zone 后全站复用;优先在server或location上按需引用 - 配合
limit_req_status 429+ 自定义 error_page,让客户端感知限流而非静默丢包,降低重试风暴
动态验证与容量水位监控
上线后必须持续观测 zone 实际使用率,而非仅看请求成功率:
- 通过
nginx -T | grep limit_req_zone确认配置加载无误 - 定期调用
curl -s 'http://127.0.0.1/nginx_status' | grep -i 'limit'(需开启 stub_status)查看命中/拒绝计数 - 采集
shm_zone_ip_limit_used_size指标(通过 nginx-module-vts 或 openresty prometheus 模块),当使用率持续 >85%,立即扩容 zone

















