文档
一个 项目

tls

为站点配置 TLS。

Caddy 的默认 TLS 设置是安全的。仅当您有充分的理由并理解其含义时才更改这些设置。 此指令最常见的用途是指定 ACME 账户电子邮件地址、更改 ACME CA 端点或提供您自己的证书。

兼容性注意:由于 TLS 作为安全协议的敏感性,可能会在新次要版本或补丁版本中对 TLS 默认设置进行有意调整。旧的或损坏的 TLS 版本、密码、功能等可能会随时被删除。如果您的部署对更改极其敏感,您应显式指定必须保持不变的那些值,并对升级保持警惕。在几乎所有情况下,我们都建议使用默认设置。

语法

tls [internal|<email>] | [<cert_file> <key_file>] {
	protocols <min> [<max>]
	ciphers   <cipher_suites...>
	curves    <groups...>
	alpn      <values...>
	load      <paths...>
	ca        <ca_dir_url>
	ca_root   <pem_file>
	key_type  ed25519|p256|p384|rsa2048|rsa4096
	dns       <provider_name> [<params...>]
	propagation_timeout <duration>
	propagation_delay   <duration>
	dns_ttl             <duration>
	dns_challenge_override_domain <domain>
	resolvers <dns_servers...>
	eab       <key_id> <mac_key>
	on_demand
	reuse_private_keys
	client_auth {
		mode                   [request|require|verify_if_given|require_and_verify]
		trust_pool             <module>
		verifier 			   <module>
	}
	issuer          <issuer_name>  [<params...>]
	get_certificate <manager_name> [<params...>]
	insecure_secrets_log <log_file>
}
  • internal 表示使用 Caddy 的内部、本地信任的 CA 为此站点生成证书。要进一步配置 internal 颁发者,请使用 issuer 子指令。

  • <email> 是用于管理站点证书的 ACME 帐户的电子邮件地址。您可能更喜欢使用 email 全局选项,以便一次性为所有站点配置此选项。

  • <cert_file><key_file> 是证书和私钥 PEM 文件的路径。仅指定一个无效。

  • protocols 指定最小和最大协议版本。 除非您知道自己在做什么,否则请勿更改这些设置。 配置此项很少是必要的,因为 Caddy 将始终使用现代默认值。

    默认最小值:tls1.2,默认最大值:tls1.3

  • ciphers 指定密码套件名称列表,按偏好降序排列。 除非您知道自己在做什么,否则请勿更改这些设置。 请注意,密码套件对于 TLS 1.3 是不可自定义的;并非所有 TLS 1.2 密码都默认启用。 支持的名称是(按 Go stdlib 的偏好顺序):

    • TLS_AES_128_GCM_SHA256
    • TLS_CHACHA20_POLY1305_SHA256
    • TLS_AES_256_GCM_SHA384
    • TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256
    • TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256
    • TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384
    • TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384
    • TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305_SHA256
    • TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305_SHA256
    • TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA
    • TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA
    • TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA
    • TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA
    • TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA
  • curves 指定要支持的 EC 组列表。 建议不要更改默认值。 支持的值为:

    • x25519mlkem768 (PQC)
    • x25519
    • secp256r1
    • secp384r1
    • secp521r1
  • alpn 是要在 TLS 握手的 ALPN 扩展 中公布的值列表。

  • load 指定要从中加载证书+密钥捆绑包 PEM 文件的文件夹列表。

  • ca 更改 ACME CA 端点。 这最常用于设置 Let's Encrypt 的暂存端点 以进行测试,或设置内部 ACME 服务器。(要为整个 Caddyfile 更改此值,请改用 acme_ca 全局选项。)

  • ca_root 指定包含 ACME CA 端点的受信任根证书的 PEM 文件,如果该证书不在系统信任存储中。

  • key_type 是生成 CSR 时要使用的密钥类型。 仅当您有特定要求时才设置此项。

  • dns 启用使用指定提供商插件的 DNS 质询,该插件必须从 caddy-dns 存储库之一插入。 每个提供商插件可能有自己的语法,紧随其名称之后;有关详细信息,请参阅其文档。 维护对每个 DNS 提供商的支持是一项社区工作。 了解如何在我们的 wiki 上为您的提供商启用 DNS 质询。

  • propagation_timeout 是一个 持续时间值,用于设置使用 DNS 质询时等待 DNS TXT 记录出现的最长时间。 设置为 -1 以禁用传播检查。 默认值为 2 分钟。

  • propagation_delay 是一个 持续时间值,用于设置在使用 DNS 质询时,在开始 DNS TXT 记录传播检查之前等待多长时间。 默认值 0(不等待)。

  • dns_ttl 是一个 持续时间值,用于设置 DNS 质询使用的 TXT 记录的 TTL。 很少需要。

  • dns_challenge_override_domain 覆盖用于 DNS 质询的域名。 这是为了将质询委托给不同的域。

    如果您的主域的 DNS 提供商没有可用的 DNS 插件 ,您可能需要使用此选项。 您可以改为为主域添加一个子域名为 _acme-challengeCNAME 记录,指向您确实拥有插件的辅助域。 此选项不需要来自插件的特殊支持。

    当 ACME 颁发者尝试为主域解决 DNS 质询时,他们将遵循 CNAME 到您的辅助域以查找 TXT 记录。

    注意: 在此处使用来自 CNAME 记录的完整规范名称作为值 - _acme-challenge 子域名不会自动预先添加。

  • resolvers 自定义执行 DNS 质询时使用的 DNS 解析器;这些解析器优先于系统解析器或任何默认解析器。 如果在此处设置,解析器将传播到所有配置的证书颁发者。

    这通常是 IP 地址列表。 例如,要使用 Google Public DNS

    resolvers 8.8.8.8 8.8.4.4
    
  • eab 为此站点配置 ACME 外部帐户绑定 (EAB),使用您的 CA 提供的密钥 ID 和 MAC 密钥。

  • on_demand 为站点块地址中给定的主机名启用 按需 TLS安全警告: 除非您还配置 on_demand_tls 全局选项 以缓解滥用,否则在生产环境中这样做是不安全的。

  • reuse_private_keys 启用在续订证书时重用私钥。 默认情况下,为每个新证书创建一个新密钥,以缓解密钥固定并减少密钥泄露的范围。 密钥固定违反了行业最佳实践。 除非您有使用它的特定理由,否则不建议使用此选项;此选项可能会在未来版本中删除。

  • client_auth 启用和配置 TLS 客户端身份验证:

    • mode 是客户端身份验证的模式。 允许的值为:

      模式 描述
      request 要求客户端提供证书,但即使没有证书也允许;不验证证书
      require 要求客户端出示证书,但不验证证书
      verify_if_given 要求客户端提供证书;即使没有证书也允许,但如果有证书则验证证书
      require_and_verify 要求客户端出示已验证的有效证书

      默认值:如果提供了 trust_pool 模块,则为 require_and_verify;否则为 require

    • trust_pool 配置证书颁发机构 (CA) 的来源,这些机构提供用于验证客户端证书的证书。

      提供受信任证书池的证书颁发机构以及段落内的配置取决于配置的信任池模块的来源。 Caddy 中可用的标准模块在下面列出。完整模块列表,包括第三方模块,在 trust_pool JSON 文档 中列出。

      可以使用多个 trusted_* 指令来指定多个 CA 或叶证书。 未列为叶证书之一或未由任何指定的 CA 签名的客户端证书将根据 mode 被拒绝。

    • verifier 启用自定义客户端证书验证器模块的使用。 这些模块可以执行自定义客户端身份验证检查,例如确保证书未被吊销。

  • issuer 配置自定义证书颁发者,或获取证书的来源。

    使用的颁发者以及此段落中遵循的选项取决于可用的 颁发者模块。 一些其他子指令(例如 cadns)实际上是配置 acme 颁发者的快捷方式(此子指令稍后添加),因此指定此指令和某些其他指令会令人困惑,因此被禁止。

    可以多次指定此子指令以配置多个冗余颁发者;如果一个颁发者未能颁发证书,将尝试下一个颁发者。

  • get_certificate 允许在握手时从 管理器模块 获取证书。

  • insecure_secrets_log 启用将 TLS 密钥记录到文件。 这也称为 SSLKEYLOGFILE。 使用 NSS 密钥日志格式,然后可以由 Wireshark 或其他工具解析。 ⚠️ 安全警告: 这是不安全的,因为它允许其他程序或工具解密 TLS 连接,因此完全损害了安全性。 但是,此功能对于调试和故障排除可能很有用。

信任池提供程序

这些是可以在 trust_pool 子指令中使用的标准信任池提供程序

inline

inline 模块直接在 Caddyfile 中以 base64 DER 编码格式解析列出的受信任根证书。 trust_der 指令可以重复多次。

trust_pool inline {
	trust_der      <base64_der>
}
  • trust_der 是用于验证客户端证书的 base64 DER 编码的 CA 证书。

file

file 模块从磁盘上的 PEM 文件读取受信任的根证书。 pem_file 指令可以在同一行上接受多个文件路径,并且可以重复多次。

... file [<pem_file>...] {
	pem_file <pem_file>...
}
  • pem_file 是 PEM CA 证书文件的路径,用于验证客户端证书。

pki_root

pki_root 模块从 PKI 应用程序 中定义的证书颁发机构获取证书和信任证书。 authority 指令可以同时接受多个颁发机构,并且可以重复多次。

... pki_root [<ca_name>...] {
	authority <ca_name>...
}
  • authority 是在 PKI 应用程序中配置的证书颁发机构的名称。

pki_intermediate

pki_intermediate 模块从 PKI 应用程序 中定义的证书颁发机构获取中间证书和信任证书。 authority 指令可以同时接受多个颁发机构,并且可以重复多次。

... pki_intermediate [<ca_name>...] {
	authority <ca_name>...
}
  • authority 是在 PKI 应用程序中配置的证书颁发机构的名称。

storage

storage 模块从 Caddy 存储 中提取受信任的证书根。 authority 指令可以同时接受多个颁发机构,并且可以重复多次。

... storage [<storage_keys>...] {
	storage <storage_module>
	keys    <storage_keys>...
}
  • storage 是要使用的可选存储模块。 如果未指定,将使用默认存储模块。 如果指定,则只能指定一次。

  • keys 是存储 PEM 证书文件的存储键列表。 该指令在同一行上接受多个值,并且可以多次指定。

http

http 模块从 HTTP 端点获取受信任的证书。 endpoints 指令可以同时接受多个端点,并且可以重复多次。

... http [<endpoints...>] {
	endpoints   <endpoints...>
	tls         <tls_config>
}
  • endpoints 是从中获取证书的 HTTP 端点列表。 该指令在同一行上接受多个值,并且可以多次指定。

  • tls 是连接到 HTTP 端点时要使用的可选 TLS 配置。 段落解析在 以下部分 中定义。

TLS
... {
	ca                    <ca_module>
	insecure_skip_verify
	handshake_timeout     <duration>
	server_name           <name>
	renegotiation         <never|once|freely>
}
  • ca 是一个可选指令,用于定义信任池的提供程序。 配置遵循 trust_pool 的相同行为。 如果指定,则只能指定一次。

  • insecure_skip_verify 关闭 TLS 握手验证,使连接不安全且容易受到中间人攻击。 请勿在生产环境中使用。 验证是针对系统信任的证书颁发机构或由 ca 指令确定的证书颁发机构进行的。

  • handshake_timeout 是等待 TLS 握手完成的最长 持续时间。 默认值:无超时。

  • server_name 设置在验证 TLS 握手中收到的证书时使用的服务器名称。 默认情况下,这将使用上游地址的主机部分。

  • renegotiation 设置 TLS 重新协商级别。 TLS 重新协商是在第一次握手之后执行后续握手的行为。 级别可以是以下之一:

    • never(默认值)禁用重新协商。
    • once 允许远程服务器每个连接请求重新协商一次。
    • freely 允许远程服务器重复请求重新协商。

颁发者

这些颁发者是 tls 指令的标准配置

acme

使用 ACME 协议获取证书。 请注意,acme 是默认颁发者(使用 Let's Encrypt),因此显式配置它通常是不必要的。

... acme [<directory_url>] {
	dir      <directory_url>
	test_dir <test_directory_url>
	email    <email>
	timeout  <duration>
	disable_http_challenge
	disable_tlsalpn_challenge
	alt_http_port    <port>
	alt_tlsalpn_port <port>
	eab <key_id> <mac_key>
	trusted_roots <pem_files...>
	dns [<provider_name> [<options>]]
	propagation_timeout <duration>
	propagation_delay   <duration>
	dns_ttl             <duration>
	dns_challenge_override_domain <domain>
	resolvers <dns_servers...>
	preferred_chains [smallest] {
		root_common_name <common_names...>
		any_common_name  <common_names...>
	}
}
  • dir 是 ACME CA 目录的 URL。

    默认值:https://acme-v02.api.letsencrypt.org/directory

  • test_dir 是一个可选的备用目录,用于在重试质询时使用;如果所有质询都失败,则在重试期间将使用此端点;如果 CA 有一个暂存端点,您想避免对其生产端点进行速率限制,这将非常有用。

    默认值:https://acme-staging-v02.api.letsencrypt.org/directory

  • email 是 ACME 帐户联系电子邮件地址。

  • timeout 是一个 持续时间值,用于设置 ACME 操作超时前的等待时间。

  • disable_http_challenge 将禁用 HTTP 质询。

  • disable_tlsalpn_challenge 将禁用 TLS-ALPN 质询。

  • alt_http_port 是用于服务 HTTP 质询的备用端口;它必须发生在端口 80 上,因此您必须将数据包转发到此备用端口。

  • alt_tlsalpn_port 是用于服务 TLS-ALPN 质询的备用端口;它必须发生在端口 443 上,因此您必须将数据包转发到此备用端口。

  • eab 指定外部帐户绑定,某些 ACME CA 可能需要此绑定。

  • trusted_roots 是一个或多个根证书(作为 PEM 文件名),用于在连接到 ACME CA 服务器时信任。

  • dns 配置 DNS 质询。 除非 dns 全局选项 指定了全局适用的 DNS 提供商模块,否则必须在此处配置提供商。

  • propagation_timeout 是一个 持续时间值,用于设置使用 DNS 质询时等待 DNS TXT 记录出现的最长时间。 设置为 -1 以禁用传播检查。 默认值为 2 分钟。

  • propagation_delay 是一个 持续时间值,用于设置在使用 DNS 质询时,在开始 DNS TXT 记录传播检查之前等待多长时间。 默认值为 0(不等待)。

  • dns_ttl 是一个 持续时间值,用于设置 DNS 质询使用的 TXT 记录的 TTL。 很少需要。

  • dns_challenge_override_domain 覆盖用于 DNS 质询的域名。 这是为了将质询委托给不同的域。

    如果您的主域的 DNS 提供商没有可用的 DNS 插件 ,您可能需要使用此选项。 您可以改为为主域添加一个子域名为 _acme-challengeCNAME 记录,指向您确实拥有插件的辅助域。 此选项不需要来自插件的特殊支持。

    当 ACME 颁发者尝试为主域解决 DNS 质询时,他们将遵循 CNAME 到您的辅助域以查找 TXT 记录。

    注意: 在此处使用来自 CNAME 记录的完整规范名称作为值 - _acme-challenge 子域名不会自动预先添加。

  • resolvers 自定义执行 DNS 质询时使用的 DNS 解析器;这些解析器优先于系统解析器或任何默认解析器。 如果在此处设置,解析器将传播到所有配置的证书颁发者。

    这通常是 IP 地址列表。 例如,要使用 Google Public DNS

    resolvers 8.8.8.8 8.8.4.4
    
  • preferred_chains 指定 Caddy 应首选哪个证书链;如果您的 CA 提供多个链,这将非常有用。 使用以下选项之一:

    • smallest 将告诉 Caddy 首选字节数最少的链。

    • root_common_name 是一个或多个通用名称的列表;Caddy 将选择第一个根与至少一个指定的通用名称匹配的链。

    • any_common_name 是一个或多个通用名称的列表;Caddy 将选择第一个颁发者与至少一个指定的通用名称匹配的链。

zerossl

使用 ZeroSSL 的专有证书颁发 API 获取证书。 需要 API 密钥,并且可能还需要付款,具体取决于您的计划。 请注意,此问题与 ZeroSSL 的 ACME 端点 不同。 要使用 ZeroSSL 的 ACME 端点,请使用配置了 ZeroSSL ACME 目录端点的上述 acme 颁发者。

... zerossl <api_key> {
	validity_days <days>
	alt_http_port <port>
	dns <provider_name> ...
	propagation_delay <duration>
	propagation_timeout <duration>
	resolvers <list...>
	dns_ttl <duration>
}
  • validity_days 定义证书有效期。 仅接受某些值;有关详细信息,请参阅 ZeroSSL 的文档
  • alt_http_port 是用于完成 ZeroSSL 的 HTTP 验证的端口,如果不是端口 80。
  • dns 启用 CNAME 验证方法,使用命名的 DNS 提供商和给定的配置进行自动记录配置。 必须从 caddy-dns 存储库安装 DNS 提供商插件。 每个提供商插件可能有自己的语法,紧随其名称之后;有关详细信息,请参阅其文档。 维护对每个 DNS 提供商的支持是一项社区工作。
  • propagation_delay 是在检查 CNAME 记录传播之前等待多长时间。
  • propagation_timeout 是在放弃之前等待 CNAME 记录传播多长时间。
  • resolvers 定义在检查 CNAME 记录传播时使用的自定义 DNS 解析器。
  • dns_ttl 配置作为验证过程一部分创建的 CNAME 记录的 TTL。

internal

从内部证书颁发机构获取证书。

... internal {
	ca       <name>
	lifetime <duration>
	sign_with_root
}
  • ca 是要使用的内部 CA 的名称。 默认值:local。 请参阅 PKI 应用程序全局选项 以配置 local CA,或创建备用 CA。

    默认情况下,根 CA 证书的有效期为 3600d(10 年),中间证书的有效期为 7d(7 天)。

    Caddy 将尝试将根 CA 证书安装到系统信任存储中,但这在 Caddy 以非特权用户身份运行时或在 Docker 容器中运行时可能会失败。 在这种情况下,需要手动安装根 CA 证书,可以使用 caddy trust 命令,或者 从容器中复制出来

  • lifetime 是一个 持续时间值,用于设置内部颁发的叶证书的有效期。 默认值:12h。 不建议更改此值,除非绝对必要。 它必须短于中间证书的有效期。

  • sign_with_root 强制根证书成为颁发者而不是中间证书。 不建议这样做,仅应在设备/客户端未正确验证证书链时使用(非常罕见)。

证书管理器

证书管理器模块与颁发者模块不同之处在于,管理器模块的使用意味着外部工具或服务正在保持证书续订,而颁发者模块意味着 Caddy 本身正在管理证书。(颁发者模块将证书签名请求 (CSR) 作为输入,但证书管理器模块将 TLS ClientHello 作为输入。)

这些管理器模块是 tls 指令的标准配置

tailscale

从本地运行的 Tailscale 实例获取证书。 必须在您的 Tailscale 帐户中启用 HTTPS(或您的开源 Headscale 服务器 );并且 Caddy 进程必须以 root 身份运行,或者您必须配置 tailscaled 以授予您的 Caddy 用户 获取证书的权限

注意:这通常是不必要的! Caddy 会自动为所有 *.ts.net 域使用 Tailscale,而无需任何额外的配置。

get_certificate tailscale  # often unnecessary!

http

http

get_certificate http <url>
  • 通过发出 HTTP(S) 请求来获取证书。 响应必须具有 200 状态代码,并且正文必须包含 PEM 链,包括完整证书(带中间证书)以及私钥。

    • url 是要向其发出请求的完全限定 URL。 强烈建议这是一个本地端点,以提高性能。 URL 将使用以下查询字符串参数进行扩充:
    • server_name: SNI 值
    • signature_schemes: 签名算法的逗号分隔的十六进制 ID 列表

cipher_suites: 密码套件的逗号分隔的十六进制 IDS 列表

示例

example.com {
	tls cert.pem key.pem
}

使用自定义证书和密钥。 证书应具有与站点地址匹配的 SAN

example.com {
	tls internal
}

对当前站点块上的所有主机使用 本地信任的 证书,而不是通过 ACME / Let's Encrypt 获取公共证书(在开发环境中很有用)

https:// {
	tls internal {
		on_demand
	}
}

使用本地信任的证书,但以 按需 方式管理,而不是在后台管理。 这允许您将任何域指向您的 Caddy 实例,并让它自动为您配置证书。 如果您的 Caddy 实例可公开访问,则不应使用此功能,因为攻击者可能会使用它来耗尽服务器的资源

example.com {
	tls {
		issuer internal {
			ca foo
		}
	}
}

对内部 CA 使用自定义选项(不能使用 tls internal 快捷方式)

example.com {
	tls your@email.com
}

为您的 ACME 帐户指定电子邮件地址(但如果所有站点仅使用一个电子邮件地址,我们建议改用 email 全局选项

*.example.com {
	tls {
		dns cloudflare {env.CLOUDFLARE_API_TOKEN}
	}
}

为在 Cloudflare 上管理的域启用 DNS 质询,帐户凭据在环境变量中。 这解锁了通配符证书支持,这需要 DNS 验证

https:// {
	tls {
		get_certificate http http://localhost:9007/certs
	}
}

通过 HTTP 获取证书链,而不是让 Caddy 管理它。 请注意,get_certificate 意味着 on_demand 已启用,使用模块获取证书而不是触发 ACME 颁发

example.com {
	tls {
		client_auth {
			trust_pool file ../caddy.ca.cer ../root.ca.cer
		}
	}
}