Nginx会话粘性(Sticky Sessions)本质是通过反向代理层绑定客户端与后端服务器,解决有状态应用在无共享Session架构下的上下文丢失问题;它依赖Cookie实现首次分配与后续识别闭环,相比ip_hash更可靠支持移动网络、NAT环境及SignalR等长连接场景。

会话粘性(Sticky Sessions)在 Nginx 负载均衡中,本质是解决“有状态应用”与“无共享 Session 架构”之间的矛盾。它不依赖后端改造,而是由 Nginx 在反向代理层主动绑定客户端与某台后端服务器,确保登录态、购物车、SignalR 连接等关键上下文不丢失。
为什么生产环境常需要 sticky 而非 ip_hash
ip_hash 看似简单,但在真实业务中容易失效:
- 移动网络下用户 IP 频繁变动,导致会话中断
- 企业或校园出口共用 NAT 网关,大量用户被哈希到同一台后端,引发负载倾斜甚至雪崩
- 无法支持 WebSocket 协商阶段与传输阶段的请求一致性(如 SignalR 的 /negotiate → /connect 流程)
- 不支持 Cookie 过期、域名作用域、安全属性等精细化控制
sticky 模块的核心工作逻辑
模块通过 Cookie 实现“首次分配 + 后续识别”的闭环:
- 客户端首次请求无 route 类 Cookie → Nginx 按轮询选一台后端,并在响应头中写入 Set-Cookie: srv_id=abc123; Path=/; Domain=.example.com; Expires=...
- srv_id 值由 Nginx 自动生成,与后端节点唯一绑定(非明文 IP,通常为 hash 标识)
- 后续请求携带该 Cookie → Nginx 解析值,直接路由至对应后端,跳过负载算法
- 若目标后端宕机且未标记 down,请求将失败;建议配合健康检查或手动标记 server ... down;
生产部署的关键实操要点
编译与配置需严守版本和细节:
- 仅适配 Nginx ≤1.18.x(如 1.18.0),1.19+ 及主线新版已不兼容,强行编译会报错或运行异常
- configure 时必须复用原 Nginx 的全部编译参数(用 nginx -V 查看),再追加 --add-module=/path/to/nginx-sticky-module-ng
- 替换二进制前务必停止服务、备份旧 nginx 文件,避免启动失败导致服务中断
- upstream 中启用方式为:sticky cookie srv_id expires=30m domain=.example.com path=/ secure httponly; —— secure 和 httponly 需 Nginx 版本及模块分支支持,否则忽略
- 验证方法:用 curl -I 或浏览器 DevTools 查响应头是否含 Set-Cookie;再连续请求,比对后端 access_log 的 remote_addr 或自定义响应 header(如 X-Backend-ID)是否一致
替代方案与适用边界
sticky 不是万能解,需结合架构演进判断:
- 短期救急、遗留系统改造成本高时,sticky 是最轻量的会话保持手段
- 新项目或已有 Redis/数据库共享 Session 能力,应优先走无状态设计,彻底摆脱粘性依赖
- 若必须用 Cookie 方案但受限于 Nginx 版本,可考虑 OpenResty + lua-resty-iputils + 自定义 cookie 路由逻辑(需 Lua 开发能力)
- 对于 SignalR、WebRTC 等长连接场景,sticky 是当前最稳定可靠的生产级选择











