如何修复 ERR_CERT_COMMON_NAME_INVALID:完整指南
ERR_CERT_COMMON_NAME_INVALID 是 Chrome 在地址栏中输入的域名与网站 SSL 证书上列出的域名不一致时显示的错误。在 TLS 握手期间,浏览器会检查请求的主机名是否与证书的通用名称(CN)或某个使用者可选名称(SAN)条目匹配。当匹配失败时,Chrome 会以"您的连接不是私密连接"阻止连接,并将 NET::ERR_CERT_COMMON_NAME_INVALID 标为原因。
该错误纯粹是名称匹配问题 — 它与证书是否过期、被吊销或由受信任的机构签发无关。一张完全有效、未过期且链路完整的证书,如果签发给 example.com 而访客访问的是 www.example.com,或证书只列出根域名而 SAN 中省略了 www 变体,仍会触发此警告。本指南将逐一讲解每个根本原因,并提供完整的六步修复流程。
什么是 ERR_CERT_COMMON_NAME_INVALID?
当浏览器连接到 HTTPS 网址时,服务器会出示其 SSL/TLS 证书。随后 Chrome 会验证 URL 中的主机名 — 例如 blog.example.com — 是否出现在证书的身份字段中。历史上这指的是通用名称(CN)字段,但由于 CN 无法可靠地容纳多个名称,现代浏览器依赖使用者可选名称(SAN)扩展。Chrome 优先检查 SAN 列表,仅将 CN 作为向后兼容的回退。如果请求的主机名在两者中都未出现,握手就会被中止并显示 ERR_CERT_COMMON_NAME_INVALID。
区分相关错误很重要。ERR_CERT_AUTHORITY_INVALID 针对的是谁签发了证书,ERR_CERT_DATE_INVALID 针对的是过期问题,而 ERR_CERT_COMMON_NAME_INVALID 严格针对证书上的名称是否与你请求的名称匹配。一张证书可能由受信任的 CA 签发、未过期且提供完整链路,但当主机名即使只差一个子域标签时,仍会触发此错误。
常见原因
六个根本原因几乎涵盖了 ERR_CERT_COMMON_NAME_INVALID 的每一次出现。识别出哪一条适用,是通往修复的最快路径。
- 证书签发给错误的域名:CSR 使用了错误的 CN 生成,或 CA 为一个拼写错误的域名签发了证书,与服务器实际托管的域名不匹配。
- www 与非 www 不匹配:证书覆盖
example.com,但访客到达的是www.example.com(反之亦然),且缺失的变体未列入 SAN。 - 缺少 SAN 条目:证书仅在 CN 中列出主机名,SAN 为空或不完整。现代浏览器忽略 CN 进行匹配,要求名称出现在 SAN 中。
- 自签名证书 CN 不正确:为
localhost或 IP 地址生成的自签名证书被用于真实域名,因此名称不匹配。 - 通配符证书范围错误:
*.example.com的通配符证书覆盖一级子域,但不覆盖根域example.com或嵌套主机如api.staging.example.com。 - 证书尚未部署:新证书已签发但未在服务器上安装,因此仍在提供缺少新域名的旧证书。
分步修复指南
按顺序执行以下六个步骤。前两步诊断确切的不匹配;其余四步在服务器上加以修正。
1. 确认请求的确切主机名
首先读取地址栏中的完整主机名,包括每一个子域标签和任何 www 前缀。www.example.com 与 example.com 之间如此微小的差异就足以触发错误。然后解析 DNS 以查看实际提供服务的服务器和证书:
# 将主机名解析为 IP 地址
dig +short example.com
dig +short www.example.com
# 如果两者指向同一 IP,则为两者提供同一张证书,
# 可能是某个变体在 SAN 中缺失。
如果两个主机名解析到不同的 IP,第二台服务器可能提供的是完全不同的证书。请确保你诊断的正是产生错误的确切主机名。
2. 检查证书的 CN 和 SAN 条目
使用 OpenSSL 连接服务器并打印证书的使用者和 SAN 扩展。这会揭示证书声称保护的每个名称:
echo | openssl s_client -connect example.com:443 -servername example.com 2>/dev/null \
| openssl x509 -noout -subject -issuer -ext subjectAltName
-subject 行显示通用名称;subjectAltName 行列出证书有效的每个主机名。将每个条目与地址栏中的主机名进行比对。如果请求的名称在 CN 和 SAN 中均未出现,你就确认了不匹配,可以进入修复阶段。
3. 解决 www 与非 www 不匹配问题
最常见的触发因素是证书只覆盖 example.com 和 www.example.com 中的一个。最干净的修复是重新签发证书,使两个变体都出现在 SAN 中。大多数 CA — 包括 Let's Encrypt — 允许你一次性请求两者:
# Certbot:签发一张同时覆盖两个变体的证书
sudo certbot certonly --nginx \
-d example.com -d www.example.com
如果无法立即重新签发,请配置服务器端重定向,使每位访客都落在证书已覆盖的主机名上。在 Nginx 中,将 www 重定向到根域:
# Nginx:将 www 重定向到非 www
server {
listen 443 ssl;
server_name www.example.com;
ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
return 301 https://example.com$request_uri;
}
请注意,重定向块仍需要一张对 www.example.com 有效的证书才能完成 TLS 握手,因此同时签发两个名称通常比重定向更简单。
4. 为正确的域名重新签发或重新配置证书
如果证书完全签发给了错误的域名,请生成带有正确通用名称的新 CSR,并在 SAN 中列出所有需要的主机名。现代证书应将所有名称放入 SAN;CN 仅出于向后兼容而保留:
# 生成带 SAN 配置的私钥和 CSR
openssl req -newkey rsa:2048 -nodes \
-keyout example.com.key -out example.com.csr \
-subj "/CN=example.com" \
-addext "subjectAltName=DNS:example.com,DNS:www.example.com,DNS:blog.example.com"
将 CSR 提交给 CA。新证书签发后,进入第 6 步进行部署。如果你使用控制面板或 CDN,请在其中更新域名列表,使 SAN 包含网站应答的每个主机名。
5. 修正通配符证书的范围
*.example.com 的通配符证书只匹配一级子域 — 它覆盖 www.example.com 和 api.example.com,但不覆盖根域 example.com,也不覆盖嵌套主机如 api.staging.example.com。如果访客访问了通配符范围之外的名称,Chrome 就会抛出 ERR_CERT_COMMON_NAME_INVALID。通过将未覆盖的名称添加到 SAN 来修复:
# 一张证书中同时包含通配符和根域
openssl req -newkey rsa:2048 -nodes \
-keyout wildcard.key -out wildcard.csr \
-subj "/CN=*.example.com" \
-addext "subjectAltName=DNS:*.example.com,DNS:example.com"
对于 api.staging.example.com 这类嵌套子域,要么为该主机签发单独的证书,要么申请第二个通配符 *.staging.example.com。单个通配符永远不会跨多个标签层级。
6. 部署新证书并验证修复
在服务器上安装重新签发的证书和密钥,让 Web 服务器指向它们并重新加载。然后用 OpenSSL 验证现在提供的是正确的名称:
# 安装新的证书文件
sudo cp fullchain.pem /etc/ssl/certs/example.com.crt
sudo cp privkey.pem /etc/ssl/private/example.com.key
# 重新加载 Nginx(或 Apache)
sudo nginx -t && sudo systemctl reload nginx
sudo apachectl configtest && sudo systemctl reload apache2
# 验证主机名现在是否匹配
openssl s_client -connect example.com:443 -servername example.com \
-verify_hostname example.com </dev/null
清除浏览器缓存或在隐身窗口中测试,因为 Chrome 会在短时间内缓存证书决策。当验证输出报告 Verification: OK 且页面无警告加载时,修复即告完成。
证书诊断命令
下面的命令能让你全面了解提供的是哪张证书、它声称保护哪些名称,以及 DNS 指向何处。在出现错误的机器上从终端运行它们。
# 1. 打印服务器出示的完整证书及验证码
openssl s_client -connect example.com:443 -servername example.com -showcerts </dev/null
# 2. 显示使用者(CN)、颁发者和每个 SAN 条目
echo | openssl s_client -connect example.com:443 -servername example.com 2>/dev/null \
| openssl x509 -noout -subject -issuer -ext subjectAltName
# 3. 用 openssl x509 -text 解码整张证书并 grep SAN
echo | openssl s_client -connect example.com:443 -servername example.com 2>/dev/null \
| openssl x509 -noout -text | grep -A1 "Subject Alternative Name"
# 4. 解析每个主机名指向的 IP
dig +short example.com
dig +short www.example.com
# 5. 检查为特定 SNI 主机名提供的是哪张证书
echo | openssl s_client -connect 203.0.113.10:443 -servername www.example.com 2>/dev/null \
| openssl x509 -noout -subject -ext subjectAltName
# 6. 使用 OpenSSL 内置检查验证主机名是否匹配
openssl s_client -connect example.com:443 -servername example.com \
-verify_hostname example.com </dev/null
快速参考表
用此表将症状匹配到其根本原因及相应的修复方法。
| 症状 | 原因 | 修复方法 |
|---|---|---|
| 证书覆盖 example.com 但 www.example.com 报错 | www 与非 www 不匹配;SAN 缺少 www 变体 | 重新签发包含两个名称的证书(步骤 3) |
| 错误出现在证书未列出的子域上 | 子域未列入 SAN 列表 | 将子域添加到 SAN 或重新签发(步骤 4) |
| 通配符证书在根域上失败 | *.example.com 不覆盖根域 |
在 SAN 中包含根域(步骤 5) |
| 通配符在 api.staging.example.com 上失败 | 通配符只覆盖一个标签层级 | 签发单独证书或更深的通配符(步骤 5) |
| 自签名证书用于真实域名 | 证书为 localhost 或 IP 生成,而非域名 | 获取具有正确 CN/SAN 的 CA 签名证书(步骤 4) |
| 新证书已签发但错误仍出现 | 替换证书尚未在服务器上部署 | 安装并重新加载新证书(步骤 6) |
常见问题
通用名称(CN)在现代浏览器中还重要吗?
对于匹配已不重要。Chrome 和其他所有当前浏览器都忽略通用名称进行主机名验证,仅依赖使用者可选名称扩展。CN 在证书上仍因向后兼容而需要保留,但如果某个主机名未列入 SAN,即使 CN 匹配,连接也会以 ERR_CERT_COMMON_NAME_INVALID 失败。请始终用证书必须保护的每个主机名填充 SAN。
为什么我的通配符证书不覆盖根域?
通配符 *.example.com 只匹配一个 DNS 标签,因此它覆盖 www.example.com,但不覆盖 example.com 本身,因为根域前面没有标签。要同时保护两者,请申请一张 SAN 中同时列出 *.example.com 和 example.com 的证书。大多数 CA 会免费将此组合签发在一张证书中。
仅靠将 www 重定向到非 www 能修复此错误吗?
只能部分修复。重定向仍要求在浏览器跟随重定向之前,重定向主机名上完成有效的 TLS 握手,因此 www 服务器需要一张覆盖 www.example.com 的证书。可靠的修复是重新签发证书,在 SAN 中包含两个变体,然后为 SEO 和一致性添加重定向。仅靠重定向无法消除证书警告。
部署新证书后错误多久会消失?
对新访客几乎立即消失,因为浏览器在每次新握手时都会验证证书。如果你仍看到警告,浏览器很可能在缓存旧的证书决策 — 关闭并重新打开标签页、在隐身窗口中测试,或等待几分钟让内存缓存过期。由 CDN 前置的网站可能还需要清除缓存,以便边缘节点提供更新后的证书。
总结
ERR_CERT_COMMON_NAME_INVALID 始终表示同一件事:URL 中的主机名未出现在证书的通用名称或使用者可选名称列表中。原因几乎总是六种之一 — 证书签发给错误域名、www 与非 www 不匹配、缺少 SAN 条目、CN 错误的自签名证书、范围不当的通配符,或从未部署的新证书。按顺序执行这六个步骤:确认主机名、检查 CN 和 SAN、解决 www 不匹配、为正确域名重新签发、修正通配符范围,以及部署并验证。
错误消除后,请将每个主机名保留在 SAN 中、同时覆盖根域和 www 变体,并自动续期,使证书永远不会与服务器实际服务的域名脱节。几分钟的主动证书维护即可避免此警告波及你的访客。