要准确记录ssl协议版本与加密套件,必须在启用ssl的server块中使用$ssl_protocol和$ssl_cipher变量定义专用日志格式,配合正确的ssl_protocols、ssl_ciphers及ssl_prefer_server_ciphers配置,并通过日志筛查老旧协议、弱套件等风险。

要在 Nginx 访问日志中准确记录 SSL 协议版本与加密套件,关键不是“写进配置”,而是捕获每次 HTTPS 连接真实协商出的结果——这必须依赖 TLS 握手完成后由 Nginx 自动填充的内置变量,且只在启用 SSL 的上下文中有效。
必须用对变量并限定作用域
$ssl_protocol 和 $ssl_cipher 是唯二能反映真实握手结果的变量,值如 TLSv1.3 或 ECDHE-RSA-AES256-GCM-SHA384。它们仅在 listen 443 ssl 的 server 块中可用:
- 不能放在全局
http{}块或监听 80 的 server 块里,否则字段为空或报错 - HTTP 请求中这两个变量恒为空或显示为 “-”,不影响日志完整性
- Nginx 1.11.5+ 原生支持,无需额外编译模块
定义专用日志格式并绑定到 HTTPS server
在 http{} 块中定义结构清晰、便于解析的格式,推荐使用竖线(|)分隔:
log_format tls_audit '$time_iso8601|$remote_addr|$ssl_protocol|$ssl_cipher|$ssl_server_name|$request_method|$uri|$status|$bytes_sent|$request_time|"$http_user_agent"';
然后仅在启用 SSL 的 server 块中启用:
access_log /var/log/nginx/tls-audit.log tls_audit;- 确保日志路径存在,且 nginx worker 进程有写权限(如
chown nginx:adm /var/log/nginx) - 避免复用
combined格式,防止 HTTP/HTTPS 日志语义混淆
确保底层 SSL 配置真正生效
日志能记下 TLSv1.3,不代表客户端真用了 TLSv1.3。必须同步验证三项基础配置是否落地:
-
ssl_protocols TLSv1.2 TLSv1.3;—— 显式禁用 TLSv1.0/TLSv1.1 -
ssl_ciphers 'TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256';—— 精简明确,不含弱套件 -
ssl_prefer_server_ciphers on;—— 防止客户端主导导致协议或套件降级
配置后执行 nginx -t && nginx -s reload,再用 curl -I https://yoursite.com 触发一次请求,检查日志是否出现含 TLSv1.3 和对应 AEAD 套件的完整条目。
用日志做实时安全筛查
日志积累后,用简单命令即可快速识别风险连接:
- 查老旧协议:
grep -E 'TLSv1\.0|TLSv1\.1' /var/log/nginx/tls-audit.log - 查弱套件:
grep -i -E '(rc4|des|export|null|md5|sha1)' /var/log/nginx/tls-audit.log - 查缺失前向保密(TLSv1.2 场景):
grep 'TLSv1\.2' /var/log/nginx/tls-audit.log | grep -v -E '(ECDHE|DHE)' - 查明文流量(SSL 未终止):
awk -F'|' '$3 == "-" {print}' /var/log/nginx/tls-audit.log(假设 $ssl_protocol 是第 3 字段)











