装了 SSL 证书浏览器还是报不安全,记录几次排查经历

做运维这几年,"证书装好了但浏览器还是提示不安全"这种工单接了不下十次。问题看起来都一样,实际原因各不相同。记录几个典型的,给遇到同样问题的人提供排查思路。

案例一:改版后部分页面提示不安全

某次项目改版上线后,首页 HTTPS 正常,但几个子页面地址栏出现了感叹号。

排查发现是混合内容问题。改版时新加了一批图片,运营同学在后台上传图片时,编辑器生成的 URL 是 http:// 开头的。浏览器加载 HTTPS 页面时遇到 HTTP 资源,就会标记为"不完全安全"。

解决方案:全局搜索数据库和模板文件里的 http:// 资源引用,改成 https:// 或协议相对路径 //。后台编辑器的默认配置也改了,新上传的资源默认用 HTTPS 路径。

这个问题出现频率很高,尤其是有 CMS 或后台编辑器的项目。

案例二:部分浏览器报证书不可信

Chrome 正常,但 Safari 和一些 Android 浏览器报证书不可信。

原因是证书链不完整。我们的证书文件里只有终端证书,没有包含中间证书。Chrome 有自动补全证书链的机制,所以不报错;但其他浏览器没有这个能力。

用 openssl 验证:

openssl s_client -connect example.com:443 -servername example.com

输出里 Certificate chain 部分如果只有 depth=0(一层),说明缺少中间证书。

修复:把 CA 给的中间证书文件和你的终端证书合并成一个文件,终端证书在前、中间证书在后,然后在 Nginx 的 ssl_certificate 里指向这个合并后的文件。

案例三:通配符证书不覆盖裸域名

用了 *.example.com 的通配符证书,www.example.comapi.example.com 都正常,唯独 example.com(裸域名)报证书错误。

通配符证书的 * 只匹配一级子域名,不覆盖裸域名本身。这是 SSL/TLS 规范决定的。

解决方案有两个:一是申请证书时让 SAN 同时包含 *.example.comexample.com;二是把裸域名 301 到 www.example.com

案例四:证书悄悄过期了

有一次客户反馈网站打不开,检查下来是证书过期了。一张一年期的证书,到期时间正好在国庆假期,没人注意到。

快速检查命令:

echo | openssl s_client -connect example.com:443 2>/dev/null | openssl x509 -noout -dates

这次之后我们给所有管理的域名加了证书到期监控。设了提前 30 天和提前 7 天两个提醒节点,通过微信和邮件双通道通知。到现在没有再出过到期没人管的情况。

案例五:HTTP 没跳 HTTPS

严格来说这不是"不安全"的提示,但用户体验上效果差不多。证书装好了、HTTPS 正常,但 HTTP 版本的站没有做重定向,用户直接输域名访问到的还是 HTTP。

Nginx 加一个 301 重定向:

server {
    listen 80;
    server_name example.com;
    return 301 https://$host$request_uri;
}

再加一个 HSTS header,告诉浏览器后续直接走 HTTPS,不再尝试 HTTP:

add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;

排查清单

遇到类似问题时,按这个顺序查:

打开 DevTools Console 看有没有 Mixed Content 警告。用 openssl 检查证书链是否完整、域名是否匹配、是否过期。检查 HTTP 到 HTTPS 的 301 跳转是否生效。跑一遍 SSL Labs 看整体评级和配置建议。

大部分情况前两步就能定位到。


证书管理和到期监控我用的是 ssl.spug.cc,感兴趣可以看看。

posted @ 2026-07-20 15:24  外滩运维专家  阅读(15)  评论(0)    收藏  举报