全局限流是在Nginx第一层统一节流,通过http块中limit_req_zone定义共享内存区(如zone=alllimit:10m),以$binary_remote_addr为key、rate=5r/s为基础速率,在server块中用limit_req zone=alllimit burst=30 nodelay全局生效,并设limit_req_status 429,对白名单或特定请求头跳过限流,同时需配合连接限制与上游重试机制。

全局限流不是给某个接口加个开关,而是让 Nginx 在请求进入的第一层就做统一节流,避免后端被突发流量打穿。核心是用 limit_req_zone 定义全局速率策略,并在 server 或 http 块中生效,覆盖所有未单独配置的路径。
定义共享限流区域(http 块内)
这是全局限流的基础,必须放在 http{} 顶层,不能嵌套在 server 或 location 里:
-
$binary_remote_addr作为 key,比文本 IP 节省内存约 50%,10MB 内存可存约 16 万个 IP 记录; -
zone=alllimit:10m表示创建一个名为alllimit、大小为 10MB 的共享内存区; -
rate=5r/s是基础速率,建议从 3–10 r/s 起步,结合业务监控逐步调优; - 若需区分普通用户和登录用户,可用
$cookie_uid或$arg_token替代 IP,但要注意 cookie 可伪造,需配合后端校验。
应用到全部请求(server 块内)
在 server{} 中直接写限流指令,不指定 location,即默认作用于该 server 下所有路径:
-
limit_req zone=alllimit burst=30 nodelay;—— 允许最多 30 个请求排队,且不延迟处理(即“突增即放行”,避免排队等待); -
limit_req_status 429;把默认的 503 改为标准 HTTP 状态码 429,语义更清晰,前端也更容易识别; - 如果某些路径(如健康检查
/healthz或静态资源)不该被限,需在其 location 中显式关闭:limit_req off;。
防止误伤合法突发流量
纯按 IP 限流在 NAT 环境或 CDN 后容易误杀,可通过 geo 或 map 模块做简单分层:
- 用
geo $limited_ip标记白名单 IP(如运维出口、监控探针),再配合map设置不同 rate; - 对 User-Agent 包含
HealthCheck或请求头带X-Internal: 1的请求,跳过限流; - 避免把
burst设得过大(如 >50),否则队列积压会导致响应延迟升高,反而影响体验。
配套必须启用的防护项
单靠限流不够,需与连接控制、错误重试协同:
- 加
limit_conn_zone $binary_remote_addr zone=conn_perip:10m;和limit_conn conn_perip 10;,防止单 IP 建立过多空闲连接耗尽 fd; - 在 upstream 中设置
proxy_next_upstream_tries 3;和proxy_next_upstream_timeout 10s;,避免失败请求反复冲击后端; - 配合日志记录被限流的请求:
log_format main '$remote_addr - $status $request_time $limit_req_status';,便于定位问题。


















