需将 nginx error_log 设为 debug 级别并确认 --with-debug 已启用,再结合 ssl_protocols、ssl_ciphers、proxy_ssl_server_name 等配置,才能捕获 tls 版本不匹配、证书验证失败、sni 缺失、alpn 协商异常等底层 ssl 握手错误。

要让 Nginx 的 error_log 真正记录 SSL 握手过程中的底层报错(比如 TLS 版本不匹配、证书验证失败、SNI 缺失、ALPN 协商异常等),不能只靠默认日志级别。关键在于启用 debug 级别日志 + 确保 SSL 模块支持 + 针对性过滤关键线索。
? 开启 SSL 相关 debug 日志
Nginx 默认的 error_log 级别(如 warn 或 error)几乎不输出握手细节。必须显式设为 debug,且需确认编译时已启用 --with-debug(主流发行版包通常已包含):
error_log /var/log/nginx/ssl_debug.log debug;
⚠️ 注意:
- 该指令需放在
main(全局)或至少http块中才生效; -
debug日志量极大,仅用于临时排查,问题定位后建议调回info或warn; - 若启动时报
unknown log level "debug",说明 Nginx 未带 debug 支持,需重编译或换用含 debug 的包。
? 重点捕获的 SSL 握手错误线索
开启 debug 后,关注日志中以下几类高频、高价值条目:
-
TLS 协议协商失败
-
SSL_do_handshake() failed -
SSL_connect() failed -
SSL routines:tls_process_server_hello:wrong version number -
SSL routines:ssl3_get_record:wrong version number
-
-
证书与验证问题
-
SSL certificate problem: unable to get local issuer certificate -
SSL certificate problem: self signed certificate in certificate chain -
SSL certificate verify ok(成功时出现,可作对比基准) -
peer closed connection in SSL handshake(常因证书链不全或 SNI 错误触发)
-
-
SNI 和 ALPN 相关
-
SSL server name: "example.com"→ 表示 SNI 已发送 -
ALPN protocols: h2,http/1.1→ 显示协商出的协议 -
no suitable ALPN protocol→ 客户端与服务端 ALPN 不匹配 -
SSL routines:ssl_choose_client_version:unsupported protocol→ TLS 版本不兼容(如客户端只支持 TLSv1.3,而 Nginx 配了ssl_protocols TLSv1.2)
-
⚙️ 配合关键配置提升日志有效性
光开 debug 不够,还需确保相关 SSL 指令已正确配置,否则日志里连“尝试握手”都不会出现:
-
确认监听句柄启用了 SSL:
listen 443 ssl http2; # 必须含 ssl 参数
-
显式指定 TLS 版本和加密套件(避免协商失败静默降级):
ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:...;
-
若代理 HTTPS 上游,务必打开 SNI 并指定域名:
proxy_ssl_server_name on; proxy_ssl_name "api.example.com"; # 字符串字面量,不可用变量
-
如需验证上游证书,必须配可信 CA:
proxy_ssl_verify on; proxy_ssl_trusted_certificate /etc/nginx/certs/ca-bundle.pem;
? 快速筛选日志的小技巧
debug 日志文件庞大,可用如下命令聚焦 SSL 握手段:
# 查看最近 200 行中含 SSL 关键词的记录 tail -200 /var/log/nginx/ssl_debug.log | grep -i "ssl\|tls\|alpn\|sni" # 实时跟踪并高亮关键词 tail -f /var/log/nginx/ssl_debug.log | grep --color=always -i "ssl\|handshake\|certificate\|alpn"
配合一次真实请求(如 curl -vk https://yoursite.com),再查日志,能快速锁定从连接建立到握手终止的完整链路。











