HTTPS
自动 HTTPS
签发、续期、跳转,Caddy 是第一个默认就这么做的服务器。
Caddy 是第一个把 HTTPS 做成自动且默认开启的 Web 服务器,从 2015 年这件事第一次变得可行那天就开始这么做了。它为所有站点准备 TLS 证书、持续续期,还顺手把 HTTP 跳转到 HTTPS。不需要额外配置,不需要别的工具。
默认行为
- 公网 DNS 域名用公共 ACME CA 签发证书,默认配置了Let's Encrypt 与ZeroSSL
- IP 地址与内部主机名(例如
localhost、127.0.0.1)由 Caddy 自己的本地 CA 签发,并在本机写入信任 - 所有纳管的证书在后台续期,80 端口的 HTTP 请求会自动跳转到 443
什么时候会激活
Caddy 在知道自己在为哪个域名或 IP 服务时就会隐式激活自动 HTTPS。告诉它的方式有:
- Caddyfile 里的站点地址
- JSON 路由顶层的 host 匹配器
- 命令行参数,例如
--domain或--from - JSON 里的
automate证书加载器
自动 HTTPS 永远不会覆盖你写下的显式配置,它只是往上加。地址写成http://example.com 就不会激活,因为协议已经是明确的 HTTP。
公共域名需要什么
这些都是任何生产网站的基本要求,不只是 Caddy:
- 域名的 A/AAAA 记录指向这台服务器
- 80 与 443 端口对外可达(或者把流量转发给 Caddy)
- 数据目录可写且持久
- 域名出现在配置里的某个位置
满足之后就不需要再做任何事了。
本地 HTTPS
本地主机拿不到公共可信证书,Caddy 就自己当 CA:生成根证书与中间证书,叶子证书由中间证书签发,存放在数据目录的pki/authorities/local。本地 CA 由Smallstep的库驱动,不走 ACME,也不做 DNS 验证。
第一次使用根证书时,Caddy 会尝试把它装进系统信任库,权限不够就会提示输入密码。也可以随时手动执行:
caddy trust不想要了,用 caddy untrust 撤掉即可。
ACME 挑战
拿公共可信证书需要第三方机构的验证,这件事由 ACME 协议自动化完成。有三种挑战方式:
| 方式 | 端口 | 说明 |
|---|---|---|
| HTTP-01 | 80 | CA 对域名做 DNS 查询后,通过 HTTP 请求一个临时资源 |
| TLS-ALPN-01 | 443 | CA 在 TLS 握手里带上特殊的 ALPN 值,请求同一个临时资源 |
| DNS-01 | 无 | 在域名下写一条 TXT 记录,需要 DNS 提供商的凭据与插件 |
前两种默认开启。同时开启多种时,Caddy 会随机挑一种,避免形成偶然依赖;随着时间推移它会记住哪种最顺利,并优先使用,失败时再退回其他方式。通配符证书必须用 DNS 挑战。
按需 TLS
Caddy 开创了这项技术:证书不在配置加载时签发,而是在第一次需要它的 TLS 握手时动态获取,因此不需要把域名预先写死在配置里。适合那些启动时还不知道全部域名、或者域名不属于你的场景,例如多租户平台。
{
on_demand_tls {
ask http://127.0.0.1:9000/check
}
}
https:// {
tls {
on_demand
}
}出错之后
证书管理在后台进行,所以不会拖慢启动,也不会拖慢站点。拿不到证书时 Caddy 会:
- 短暂停顿后重试一次,排除偶发
- 换下一种已启用的挑战方式
- 换下一个签发者:Let's Encrypt 失败则转 ZeroSSL
- 都失败后按指数退避,最长 1 天一次,最多持续 30 天
这是目前唯一一家在拿不到证书时能自动回退到其他 CA 的服务器。内部还有速率限制,所以你可以把一百万个域名一次丢给它,它会尽可能快、但又不越界地逐个拿下。
存储与集群
证书、私钥等资产放在配置的存储介质里,默认是文件系统,因此 $HOME必须可写且持久。多个 Caddy 实例如果配置了同一个存储,会自动共享资源并协同证书管理,组成一个集群。
测试配置
{
acme_ca https://acme-staging-v02.api.letsencrypt.org/directory
}加密客户端 Hello
普通 TLS 握手里,ClientHello 里的 SNI 也就是域名,是明文传的。Encrypted ClientHello 把真正的 ClientHello 包在「外层」里,域名因此不出现在网络上。
要让它工作,需要生成 ECH 配置并发布到 DNS 的 HTTPS 记录里。Caddy 是第一个也是唯一一个能自动生成、发布并服务 ECH 配置的服务器,你只需要在全局选项里写:
{
dns <provider config...>
ech example.com
}公共名称(outer name)必须指向你的服务器,Caddy 会为它签证书。建议所有站点共用一个公共名称,以扩大匿名集。