Nginx 负载均衡
负载均衡把请求分发到多台后端服务器,既能提升整体吞吐,也能在单台故障时自动转移流量。Nginx 用 upstream 块定义一组后端,再由 location 里的 proxy_pass 转发到该组。
最小 upstream 配置
upstream 只能写在 http 层(与 server 平级),不能写进 location:
http {
upstream backend { # 自定义组名
server 192.168.1.10:8080;
server 192.168.1.11:8080;
}
server {
listen 80;
location / {
proxy_pass http://backend; # 转发到 upstream 组
}
}
}
默认采用轮询(round-robin):请求按顺序轮流分给每台后端。改完 nginx -t && reload 即生效。
server 参数:权重与状态
upstream 里每个 server 后可带参数:
upstream backend {
server 192.168.1.10:8080 weight=2 max_fails=2 fail_timeout=30s;
server 192.168.1.11:8080 weight=1 max_fails=2 fail_timeout=30s;
server 192.168.1.12:8080 backup; # 备份机:主服务器都不可用时才接管
server 192.168.1.13:8080 down; # 手动下线,不参与分发
}
| 参数 | 默认值 | 作用 |
|---|---|---|
| weight | 1 | 权重,值越大分到的请求越多 |
| max_fails | 1 | fail_timeout 周期内累计失败几次即判不可用 |
| fail_timeout | 10s | 统计失败的时间窗,也是摘除后的冷却时长 |
| backup | - | 备份服务器,仅当其他主服务器都不可用时才接管 |
| down | - | 标记永久下线 |
例如 max_fails=2 fail_timeout=30s:某台后端在 30 秒内失败 2 次就被摘除 30 秒,冷却结束后自动放回试探。这是开源版自带的"被动健康检查"。
分发策略
| 策略 | 写法 | 语义与适用 |
|---|---|---|
| 轮询 | 默认 | 请求轮流分发,后端无状态时最常用 |
| 加权轮询 | weight | 按机器性能分配流量比例 |
| ip_hash | ip_hash; | 同一客户端 IP 固定打到同一台后端(会话保持) |
| 最少连接 | least_conn; | 分给当前活跃连接最少的一台,适合请求耗时不均 |
| 自定义 hash | hash $request_uri consistent; | 按变量散列,consistent 为一致性哈希 |
upstream backend {
ip_hash; # 会话粘连:同一 IP 永远同一台后端
server 192.168.1.10:8080;
server 192.168.1.11:8080;
}
注意:ip_hash 依据客户端 IP,客户端前面再套 CDN/代理时 IP 会失真,此时可改按 Cookie 或 URI 做 hash 策略。
健康检查说明
开源版默认只有被动检查(请求失败才摘除,靠 max_fails/fail_timeout);定时主动探测需要商业版 Nginx Plus 或第三方模块(如 OpenResty 生态)。别误以为配好 upstream 就会主动巡检后端。
完整示例:加权轮询 + keepalive 长连接
为后端保留空闲长连接,减少反复 TCP 握手(前提是反向代理走 HTTP/1.1):
upstream backend {
server 192.168.1.10:8080 weight=2 max_fails=2 fail_timeout=30s;
server 192.168.1.11:8080 weight=1 max_fails=2 fail_timeout=30s;
keepalive 16; # 每个 worker 最多保留 16 条空闲长连接
}
server {
listen 80;
server_name app.example.com;
location / {
proxy_http_version 1.1; # keepalive 的前提条件
proxy_set_header Connection "";
proxy_pass http://backend;
}
}
验证分发效果:给每台后端返回不同的标识内容,或用 curl 连续请求观察后端应用日志中来源 IP 的轮换。
小结:负载均衡 = upstream 定义后端组 + proxy_pass 转发;按需选轮询/加权/ip_hash/least_conn,用 max_fails 与 fail_timeout 做被动故障转移,再开 keepalive 优化连接,即可组成一套生产可用的负载均衡入口。