在Docker中用Nginx做API网关,需构建自定义网络使Nginx通过服务名访问后端,配置limit_req实现基于IP的漏桶限流,透传Host、X-Real-IP等关键Header,并通过日志和curl验证限流生效。

在 Docker 中用 Nginx 做 API 网关,核心是把 Nginx 当作轻量、可控的流量入口,不依赖 Spring Cloud Gateway 或 Kong 这类重型组件。限流不是附加功能,而是从第一版配置就该写进去的关键策略。
基础容器化部署:Nginx + 多后端服务
先确保后端服务已容器化(如用户服务、订单服务),并加入同一 Docker 网络。Nginx 容器通过服务名直接访问它们,无需写死 IP。
- 创建自定义网络:
docker network create api-net - 启动后端服务时指定网络和别名:
docker run --network api-net --name user-service -p 3000:3000 your-user-app - Nginx 配置中
proxy_pass http://user-service:3000/即可自动解析
限流配置:用 limit_req 模块实现漏桶控制
Nginx 的 limit_req 是生产级限流的标配,它基于客户端 IP($binary_remote_addr)做统计,稳定且低开销。
- 在
http块定义限流区域:limit_req_zone $binary_remote_addr zone=api_limit:10m rate=5r/s;
表示每秒最多 5 个请求,10MB 内存存状态 - 在具体
location中启用:location /api/order/ {<br> limit_req zone=api_limit burst=10 nodelay;<br> proxy_pass http://order-service:4000/;<br>}burst=10允许短时突发,nodelay表示不排队等待,超限直接返回 503 - 若需按用户 ID 限流(如 JWT 中的
sub字段),需配合auth_request模块做前置鉴权提取变量
真实路径路由与 header 透传
API 网关不能只转发,还要让后端拿到真实上下文。常见遗漏点是 Host 和客户端 IP 丢失。
- 每个
location下必须加:proxy_set_header Host $host;<br>proxy_set_header X-Real-IP $remote_addr;<br>proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;<br>proxy_set_header X-Forwarded-Proto $scheme;
- 注意
proxy_pass末尾斜杠:proxy_pass http://user-service:3000/;(带 /)会剥离/api/user/前缀;proxy_pass http://user-service:3000;(不带 /)则完整转发路径
验证与可观测性:快速确认是否生效
限流配置容易写对但没生效——常见原因是没重载配置或 location 匹配失败。
- 进容器重载:
docker exec nginx-container nginx -s reload - 用 curl 测试限流:
for i in {1..10}; do curl -I http://localhost/api/order/list 2>/dev/null | head -1; done,观察是否出现大量 503 - 查 Nginx 日志:
docker logs nginx-container | grep "limiting requests",有输出即说明模块已触发 - 加一个健康检查接口:
location /gateway/health { return 200 '{"ok":true}'; },便于监控探活


















