高并发下SSL会话缓存需协同容量、超时与票据:按QPS×超时×0.5KB估算大小,启用session tickets兜底,统一声明shared缓存,监控命中率并分场景调优。

配置 ssl_session_cache 在高并发场景下,关键不是“堆大内存”,而是让缓存容量、超时策略与会话票据(session tickets)协同工作,避免因缓存满导致握手退化、CPU飙升、延迟跳变。
按业务节奏估算真实缓存需求
共享缓存不是越大越好,盲目设 shared:SSL:100m 可能浪费内存且降低周转率。应基于实际连接特征计算:
- 统计每秒新建 HTTPS 会话数(
new_sessions_per_sec),可通过 Nginx 日志或 Prometheus + nginx-exporter 抓取nginx_ssl_handshakes_total{type="full"}的速率 - 观察客户端平均复用窗口:多数现代浏览器/APP 在 5–15 分钟内重连,
ssl_session_timeout设为 10–20 分钟 比 4 小时更合理——既保障复用,又防止无效条目长期占位 - 单条会话内存占用约 300–600 字节(含证书链、密钥材料等),公式简化为:
推荐缓存大小 ≈ new_sessions_per_sec × timeout_sec × 0.5KB - 例:QPS=2000 的 API 网关,平均复用窗口 12 分钟 → 2000 × 720 × 0.5KB ≈ 720MB;此时应分两层应对:主缓存设
shared:SSL:512m,再启用 session tickets 作无状态兜底
必须启用 session tickets 作为无状态补充
仅靠 shared cache 无法应对突发流量洪峰——缓存区满后新会话直接 fallback 到全握手。启用 ssl_session_tickets on 可绕过服务端存储,把会话状态加密后交给客户端携带:
由 ReMe 驱动的记忆管理系统,支持跨会话记忆持久化、自动应用用户偏好以及智能上下文压缩...
- 必须配
ssl_session_ticket_key /etc/nginx/ssl/ticket.key,密钥为 32+ 字节二进制文件(可用openssl rand 48 > ticket.key生成) - 建议每月轮换密钥:生成新 key 后 reload Nginx,旧 ticket 仍可解密复用,新 ticket 使用新密钥,平滑过渡
- 注意兼容性:TLSv1.3 下 PSK 成为主力复用机制,ticket 仍有效;但若禁用
ssl_session_tickets,则完全依赖 shared cache,高并发下极易击穿
规避共享内存溢出的实操要点
缓存满不会报错,但会导致 $ssl_session_reused 变量中 .r(reused)比例骤降、.n(new)激增,同时 ssl_handshake_time P95 延迟明显上升:
- 不要在多个
server块里重复定义同名 shared 缓存(如都写shared:SSL:10m),应在http块顶层统一声明一次 - 禁用
ssl_session_cache builtin单独使用——它不跨 worker,高并发下各进程缓存互不感知,复用率极低 - Windows 环境无 shared 支持,只能用
builtin:1024+worker_processes 1组合,此时务必启用ssl_session_tickets补足复用能力 - 监控建议:用
nginx-module-vts或 OpenResty 的ssl_session_cache_hits/misses指标,设置命中率低于 85% 时告警
分场景适配缓存策略
不同业务对“复用”诉求不同,不能一套参数打天下:
-
API 接口 / 收银系统:短连接高频调用,用户操作间隔常在 1–3 分钟 →
ssl_session_timeout 5m+shared:SSL:64m+ ticket 轮换周期缩短至每周 -
Web 前端资源(JS/CSS/图片):CDN 已分担压力,Nginx 主要处理首屏 HTML 和动态接口 →
shared:SSL:20m足够,重点优化 keepalive 和 http/2 多路复用 -
长连接类应用(游戏登录、IoT 心跳):需维持小时级会话,但并发用户数可控 →
ssl_session_timeout 2h+shared:SSL:128m,并确保 ticket key 长期稳定(轮换间隔拉长)










