s_client 进阶用法
s_client 是 OpenSSL 自带的 TLS 客户端,用途远不止「测连通」:它可以携带客户端证书做双向认证测试、限定协议版本与套件、通过 starttls 连接邮件等非 HTTPS 服务。由于参数完全可控,它也是验证服务端配置是否符合预期的通用工具——浏览器会替使用者做的容错,在这里都不会发生。
基本信息
| mTLS 测试 | -cert client.crt -key client.key -CAfile ca.pem |
|---|---|
| 限制协商 | -tls1_2、-tls1_3、-cipher、-ciphersuites |
| STARTTLS | -starttls smtp、imap、xmpp 等 |
| 输出解读 | Verify return code、Protocol、Cipher 与 Certificate chain 段 |
| 常用组合 | -servername 指定 SNI,-verify_return_error 让验证失败即中断 |
| 主要用途 | 验证服务端配置与客户端证书是否契合 |
典型使用场景
- 验证证书链与 SNI:确认服务端返回的是目标域名的证书
- 双向认证测试:带上客户端证书验证 mTLS 配置是否生效
- 协议与套件核查:限定版本或套件,确认服务端是否仍接受旧配置
- 非 HTTPS 服务排查:用 starttls 测试邮件服务的 TLS 能力
- 加固前后对比:记录协商结果,确认改动确实生效
mTLS 与协议限定测试
mTLS 与协议限定测试
# 携带客户端证书做双向认证测试,验证失败即中断
openssl s_client -connect api.example.com:443 -servername api.example.com -cert client.crt -key client.key -CAfile ca.pem -verify_return_error </dev/null
# 通过 STARTTLS 测试邮件服务的 TLS 能力
openssl s_client -connect mail.example.com:25 -starttls smtp </dev/null | head -10
# 限定协议版本,确认服务端是否仍接受旧版本
openssl s_client -connect example.com:443 -tls1_2 -servername example.com </dev/null | grep -i protocol输出段读法
| 输出段 | 含义 | 异常表现 |
|---|---|---|
| Verify return code | 链验证结果 | 非 0 即失败,可按错误表对照 |
| Protocol | 协商出的协议版本 | 出现旧版本说明服务端仍允许 |
| Cipher | 协商出的套件 | 出现已弃用套件需要整改 |
| Certificate chain | 服务端下发的链 | 缺中间证书或顺序错误 |
排查 mTLS 失败时先确认服务端是否发送了证书请求,以及客户端证书的用途扩展是否包含 clientAuth。
忘记 -servername 时服务端会返回默认站点的证书,据此得出的结论可能是错的;多域名环境下这一条尤其容易踩。
客户端证书链不全时服务端会直接拒绝,而详细原因通常只在服务端日志中,命令行看到的往往只是一个笼统的握手失败信息。