🌐 一文彻底搞懂 Let's Encrypt 泛域名证书自动续期:告别手动配置,拥抱自动化运维

在现代 Web 开发与运维中,HTTPS 已成为标配。而 Let's Encrypt 作为免费、自动化、开放的证书颁发机构(CA),极大降低了 HTTPS 的使用门槛。然而,当你需要为 *.yourdomain.com 这样的泛域名(Wildcard)申请证书时,事情就变得复杂起来——HTTP-01 验证不再适用,必须使用 DNS-01 挑战,且续期过程若不自动化,将带来巨大运维负担。

本文将手把手带你从零配置 Let's Encrypt 泛域名证书的自动申请与续期,涵盖原理剖析、实战操作、安全加固与故障排查,助你真正实现“一次配置,终身无忧”。


1. 为什么泛域名证书必须用 DNS-01 验证?

1.1 Let's Encrypt 的验证机制简介

Let's Encrypt 通过 ACME 协议(Automated Certificate Management Environment)验证你对域名的控制权。目前主流验证方式有两种:

  • HTTP-01:在网站根目录放置一个随机文件,由 CA 通过 HTTP 访问验证。
  • DNS-01:在域名的 DNS 记录中添加一条特定的 TXT 记录,由 CA 查询验证。

1.2 泛域名为何不能用 HTTP-01?

1.2.1 技术限制

泛域名 *.example.com 表示“所有一级子域”,但 Let's Encrypt 无法预测你未来会创建哪些子域。例如,你无法为 random123.example.com 提前部署验证文件,因为该子域可能尚未存在。

1.2.2 安全策略

Let's Encrypt 官方明确禁止对泛域名使用 HTTP-01 验证(ACME 规范要求)。这是为了防止攻击者通过控制某个子域来申请覆盖整个泛域的证书。

结论:泛域名证书 = DNS-01 验证,别无选择。

2. 自动化续期的核心:Certbot + DNS 插件

2.1 什么是 Certbot?

Certbot 是由 EFF(电子前沿基金会)开发的 官方推荐 ACME 客户端,支持自动申请、安装、续期 Let's Encrypt 证书。它通过“插件”机制支持多种 DNS 服务商。

2.2 DNS 插件的作用

DNS 插件允许 Certbot 自动操作你的 DNS 记录,完成以下流程:

  1. 向 Let's Encrypt 请求证书
  2. 自动生成 _acme-challenge.yourdomain.com 的 TXT 记录内容
  3. 调用 DNS 服务商 API 添加该记录
  4. 等待 DNS 生效后通知 Let's Encrypt 验证
  5. 验证成功后下载并安装证书
  6. 自动清理临时 DNS 记录
💡 关键优势:全程无需人工干预,完美支持自动续期!

3. 实战:以 Cloudflare 为例配置自动续期

本文以 Cloudflare 为例(因其 API 稳定、免费、易用),但方法可迁移到阿里云、AWS Route53 等平台。

3.1 环境准备

3.1.1 系统要求

  • Ubuntu 20.04 / 22.04 或 Debian 11+
  • 已将域名 DNS 托管至 Cloudflare
  • 服务器可访问公网(用于 ACME 通信)

3.1.2 安装 Certbot 与 Cloudflare 插件

sudo apt update
sudo apt install -y certbot python3-certbot-dns-cloudflare
🔍 插件包名规律:python3-certbot-dns-<服务商名小写>

3.2 配置 Cloudflare API 凭据

3.2.1 创建 API Token(推荐)

  1. 登录 Cloudflare 控制台 → My Profile → API Tokens
  2. 点击 Create Token
  3. 使用模板:Edit zone DNS(编辑区域 DNS)
  4. 权限设置:

    • Zone: example.com(你的域名)
    • Permissions: Zone / DNS / Edit
  5. 生成 Token 并复制(仅显示一次!)

3.2.2 创建凭据文件

sudo mkdir -p /etc/letsencrypt/secrets
sudo nano /etc/letsencrypt/secrets/cloudflare.ini

填入内容:

# Cloudflare API Token(非 Global API Key!)
dns_cloudflare_api_token = your_api_token_here

3.2.3 严格限制文件权限

sudo chmod 600 /etc/letsencrypt/secrets/cloudflare.ini
sudo chown root:root /etc/letsencrypt/secrets/cloudflare.ini
⚠️ 安全警告:若权限过宽(如 644),Certbot 将拒绝运行!

3.3 首次申请泛域名证书

3.3.1 执行申请命令

sudo certbot certonly \
  --dns-cloudflare \
  --dns-cloudflare-credentials /etc/letsencrypt/secrets/cloudflare.ini \
  --dns-cloudflare-propagation-seconds 60 \
  -d '*.example.com' \
  -d 'example.com' \
  --preferred-challenges dns-01 \
  --server https://acme-v02.api.letsencrypt.org/directory \
  --non-interactive \
  --agree-tos \
  --email [email protected]

📌 关键参数说明

  • -d '*.example.com':泛域名
  • -d 'example.com'必须同时包含根域,否则 https://example.com 会证书错误
  • --dns-cloudflare-propagation-seconds 60:等待 DNS 生效时间(Cloudflare 通常很快,30~60 秒足够)

3.3.2 验证证书生成

成功后,证书将存放在:

/etc/letsencrypt/live/example.com/
├── cert.pem      → 服务器证书
├── chain.pem     → 中间证书
├── fullchain.pem → cert.pem + chain.pem(Nginx/Apache 推荐使用)
└── privkey.pem   → 私钥

3.4 配置 Web 服务器(以 Nginx 为例)

server {
    listen 443 ssl;
    server_name example.com *.example.com;

    ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;

    # 其他配置...
}

重载配置:

sudo nginx -t && sudo systemctl reload nginx

4. 实现全自动续期:让运维“躺平”

4.1 Certbot 的自动续期机制

Certbot 默认通过 systemd timer(或 cron)每天检查证书有效期。若剩余有效期 < 30 天,则自动续期。

4.1.1 验证自动续期是否启用

systemctl list-timers | grep certbot

正常应看到类似:

Mon 2025-10-27 06:12:00 CST  12h left   certbot.timer

4.2 手动测试续期(强烈建议!)

sudo certbot renew --dry-run
✅ 若输出 Congratulations, all simulated renewals succeeded,说明配置正确。

4.3 真实续期命令(无需参数)

sudo certbot renew

Certbot 会自动读取 /etc/letsencrypt/renewal/example.com.conf 中的配置(包括 DNS 插件和凭据路径)。

4.4 自动重载 Web 服务(可选但推荐)

续期后需重载 Nginx/Apache 使新证书生效。可通过 renewal hooks 实现:

sudo mkdir -p /etc/letsencrypt/renewal-hooks/post/
sudo nano /etc/letsencrypt/renewal-hooks/post/reload-nginx.sh

内容:

#!/bin/bash
systemctl reload nginx

赋予执行权限:

sudo chmod +x /etc/letsencrypt/renewal-hooks/post/reload-nginx.sh
🔄 此脚本会在每次成功续期后自动执行。

5. 迁移到其他 DNS 服务商

5.1 常见服务商插件对照表

DNS 服务商插件包名凭据配置方式
Cloudflarepython3-certbot-dns-cloudflaredns_cloudflare_api_token
阿里云python3-certbot-dns-alidnsdns_alidns_access_key + dns_alidns_access_secret
AWS Route53python3-certbot-dns-route53IAM 权限(无需密钥文件)
腾讯云 DNSPodcertbot-dns-dnspod(第三方)dns_dnspod_api_id + dns_dnspod_api_token

5.2 以阿里云为例(简要步骤)

  1. 安装插件:

    pip3 install certbot-dns-alidns
  2. 创建凭据文件 /etc/letsencrypt/secrets/alidns.ini

    dns_alidns_access_key = LTAIxxxxxx
    dns_alidns_access_secret = xxxxxxxxxxxx
  3. 申请证书时使用 --dns-alidns 参数
📚 详细文档请参考各插件 GitHub 仓库。

6. 故障排查与最佳实践

6.1 常见错误及解决

6.1.1 “Permission denied” on credentials file

  • 原因:凭据文件权限 > 600
  • 解决sudo chmod 600 /path/to/credentials.ini

6.1.2 DNS 记录未生效(“Failed authorization”)

  • 原因:DNS 传播延迟或插件未正确添加记录
  • 解决

    • 增加 --dns-xxx-propagation-seconds(如 120)
    • 手动检查 _acme-challenge.example.com TXT 记录:

      dig TXT _acme-challenge.example.com +short

6.1.3 API Token 权限不足

  • 现象:插件报错 “insufficient permissions”
  • 解决:确保 Token 有 Zone DNS Edit 权限(Cloudflare)或等效权限

6.2 安全最佳实践

  • 永远使用 API Token 而非 Global API Key(最小权限原则)
  • 定期轮换 API Token
  • 不要将凭据文件提交到 Git
  • 监控证书有效期(可用 check_http 或 Prometheus exporter)

7. 结语:自动化是运维的终极浪漫

通过本文的配置,你已经拥有了一个全自动、高安全、低维护的泛域名 HTTPS 证书体系。Let's Encrypt 的证书有效期为 90 天,但借助 Certbot 与 DNS 插件,你再也不用手动干预——系统会在后台默默完成续期,确保你的网站始终安全可信。

🌟 记住:真正的 DevOps 不是“救火”,而是“防火”。自动化,就是那道防火墙。

现在,去享受你的 https://*.yourdomain.com 吧!🔒✨


附录

标签: none

仅有一条评论

  1. 一年不见 一年不见

    内容有点多,其实把关键的脚本放出来即可。

添加新评论