前言
在阿里云 ECS 上部署个人 WordPress 博站时,本以为配置 HTTPS 是一件简单的事,没想到从证书申请到最终浏览器正常访问,踩了
一连串的坑。本文完整记录整个排查过程,希望能帮到遇到类似问题的朋友。
## 环境信息
- 服务器:阿里云 ECS(Ubuntu)
- WordPress:Docker 部署(wordpress + mysql 容器)
- Web 服务器:Nginx 1.18
- 域名:bellwinter.top / www.bellwinter.top
## 第一关:Certbot HTTP 验证失败(403)
### 现象
执行 certbot certonly --webroot 申请证书时,Let’s Encrypt 返回 403 Unauthorized:
Detail: 47.106.178.146: Invalid response from
http://bellwinter.top/.well-known/acme-challenge/xxx: 403
排查
首先检查 Nginx 配置,确认 .well-known/acme-challenge/ 路径已正确指向 /var/www/certbot:
“`nginx
location /.well-known/acme-challenge/ {
alias /var/www/certbot/.well-known/acme-challenge/;
default_type text/plain;
allow all;
}
文件权限也没问题,本地 curl 测试返回 200:
curl http://bellwinter.top/.well-known/acme-challenge/testfile
# 返回 200 OK
但从外部电脑 curl 同一地址返回 403——说明有东西在服务器和外部请求之间拦截了流量。
原因
域名经过阿里云 WAF(Web 应用防火墙)或 CDN 代理,ACME 验证请求被安全策略拦截。
解决
放弃 HTTP 验证,改用 DNS 验证方式:
certbot certonly –manual –preferred-challenges dns \
-d bellwinter.top -d www.bellwinter.top
Certbot 会要求你添加两条 DNS TXT 记录:
主机记录 │ 类型 │ 说明 │
_acme-challenge │ TXT │ 验证 bellwinter.top │
_acme-challenge.www │ TXT │ 验证 http://www.bellwinter.top
在阿里云 DNS 控制台添加后等待 1-2 分钟生效,回到终端按回车即可。
小结: 当 HTTP 验证被 WAF/CDN 拦截时,DNS 验证是最可靠的替代方案。
第二关:配置 HTTPS 后 Nginx 报错
现象
申请到证书后,修改 Nginx 配置启用 SSL,执行 nginx -t 报错:
cannot load certificate “/etc/letsencrypt/live/nellwinter.top/fullchain.pem”:
No such file or directory
原因
配置文件中域名拼写错误:nellwinter.top(n 开头)应为 bellwinter.top(b 开头)。
解决
修正拼写后 nginx -t 通过,nginx -s reload 生效。
教训: 复制粘贴虽好,但一定要检查路径是否正确。
第三关:WordPress 重定向到 8080 端口
现象
浏览器访问 https://bellwinter.top 被重定向到 https://bellwinter.top:8080/,页面无法打开。
原因
WordPress 是 Docker 部署的,容器内部端口是 8080 映射到宿主机的 80。WordPress 的 siteurl 和 home 配置还是旧的
http://47.106.178.146:8080。
解决
方法一:修改 wp-config.php
在 wp-config.php 中 /* That’s all, stop editing! */ 前添加:
define(‘WP_HOME’, ‘https://bellwinter.top’);
define(‘WP_SITEURL’, ‘https://bellwinter.top’);
方法二:直接修改数据库
USE wordpress;
UPDATE wp_options SET option_value = ‘https://bellwinter.top’
WHERE option_name = ‘siteurl’;
UPDATE wp_options SET option_value = ‘https://bellwinter.top’
WHERE option_name = ‘home’;
两种方式都需要重启容器:docker restart wordpress-app
注意: 容器内可能没有 nano 编辑器,可以用 docker cp 把文件拷到宿主机编辑后再拷回去。
第四关:浏览器表现不一致
现象
- Edge:有无 VPN 都能访问
- Firefox:不开 VPN 能访问,开 VPN 不行
- Chrome:有无 VPN 都不能访问 原因
- Chrome 有独立的 DNS 缓存,记住了旧的解析结果
- VPN 会干扰 SSL 握手,部分浏览器受影响 解决
- Chrome:访问 chrome://net-internals/#dns 清除 DNS 缓存,再访问 chrome://net-internals/#sockets 刷新 socket 连接
- 通用:使用无痕模式(Ctrl + Shift + N)访问
- VPN:访问自己的服务器时建议关闭 VPN
总结
这次部署踩坑让我学到了几点:
- 分层排查:从 Nginx → 文件权限 → 网络层 → 浏览器缓存,逐层定位问题
- ACME 验证方式:HTTP 验证依赖域名直接可达,有 WAF/CDN 时应直接用 DNS 验证
- Docker 中的 WordPress:修改配置需要考虑容器隔离,注意编辑器可用性和文件拷贝
- 浏览器缓存:不同浏览器有独立的 DNS 和连接缓存,排查时要用无痕模式排除干扰 希望这篇文章能帮你少走弯路!
