☰
Harbor 复制端点 CA 证书配置:per-endpoint 自定义 CA 校验与连接测试全解析
2026/10/17 2:01:39 网站建设 项目流程

Harbor 复制端点 CA 证书配置:per-endpoint 自定义 CA 校验与连接测试全解析

【免费下载链接】harborAn open source trusted cloud native registry project that stores, signs, and scans content.项目地址: https://gitcode.com/GitHub_Trending/ha/harbor

导读

在 Harbor 的跨实例复制(Replication)场景中,远端 Registry 若使用自签名或私有 CA 签发的 HTTPS 证书,传统做法是关闭「Verify Remote Cert」校验,但这会牺牲传输安全。Harbor 为每个复制端点(endpoint)提供了独立的CA Certificate配置字段,允许管理员按端点粘贴 PEM 格式的 CA 证书,在保持证书校验开启的前提下建立可信连接。本文将结合 Harbor 官方测试用例与仓库源码,完整讲解 per-endpoint CA 证书的配置方法、底层 TLS 校验机制、连接测试的判定逻辑,以及常见坑点。

测试用例背景:验证什么、需要什么环境

本主题对应仓库中的系统测试用例 7-16-Endpoints-per-endpoint-ca-certificate.md,该用例的验证目标是:

确认管理员可以为使用自签名(或其他不受信任)证书的 Registry 端点配置 per-endpoint CA 证书,并且 Harbor 会使用该证书校验连接,而不是必须关闭「Verify Remote Cert」。

用例对环境的要求是:

  • 至少两个 Harbor 实例处于运行且可访问状态;
  • 远端实例以HTTPS + 自签名证书提供服务。

这说明该特性面向的是真实的跨 Harbor 复制场景——两个 Harbor 之间互为主备或数据同步时,远端 Harbor 的 HTTPS 证书往往由企业内部 CA 签发或为自签名,此时为端点单独配置信任证书是保证复制安全性的关键手段。

核心配置字段:insecure与ca_certificate

在 Harbor 的注册表(Registry)端点模型中,与 TLS 校验相关的两个核心字段定义在 src/pkg/reg/model/registry.go:

type Registry struct { ID int64 `json:"id"` Name string `json:"name"` Description string `json:"description"` Type string `json:"type"` URL string `json:"url"` // TokenServiceURL is only used for local harbor instance to // avoid the requests passing through the external proxy for now TokenServiceURL string `json:"token_service_url"` Credential *Credential `json:"credential"` Insecure bool `json:"insecure"` CACertificate string `json:"ca_certificate,omitempty"` Status string `json:"status"` CreationTime time.Time `json:"creation_time"` UpdateTime time.Time `json:"update_time"` }

两个字段的语义:

字段类型含义对应 UI 控件
Insecurebool是否跳过对远端证书的校验(即 UI 上的Verify Remote Cert复选框,勾选=校验=true)Verify Remote Cert 复选框
CACertificatestringPEM 编码的 CA 证书内容,用于校验该端点证书的替代信任源CA Certificate 文本框

注意 UI 上Verify Remote Cert勾选时对应Insecure=false;该复选框取消勾选时Insecure=true(跳过校验)。两者配合关系在 OpenAPI 规范中有明确描述,见 api/v2.0/swagger.yaml:

  • insecure:Whether or not the certificate will be verified when Harbor tries to access the server.
  • ca_certificate:The PEM-encoded CA certificate for this registry endpoint. If provided, this CA will be used to verify the registry's certificateinstead of the system CA pool.

后者的关键点是:一旦填写了自定义 CA,Harbor 将优先使用该 CA 替代系统 CA 池来校验该端点的服务端证书。

底层实现:TLS Transport 的选择优先级

Harbor 的所有 Registry 适配器在构建 HTTP 客户端时,都会把端点的Insecure与CACertificate透传给统一的传输层构造函数GetHTTPTransport,例如:

  • 原生 Docker Registry 适配器 src/pkg/reg/adapter/native/adapter.go:
adapter.Client = registry.NewClientWithCACert(reg.URL, username, password, reg.Insecure, reg.CACertificate)
  • Harbor 对 Harbor 适配器 src/pkg/reg/adapter/harbor/base/adapter.go 同样透传两个配置项。

传输层的核心判定逻辑位于 src/common/http/transport.go:

func GetHTTPTransport(opts ...TransportOption) http.RoundTripper { cfg := &TransportConfig{} for _, opt := range opts { opt(cfg) } if cfg.CACertificate != "" { return NewTransport( WithCustomCACert(cfg.CACertificate), ) } if cfg.Insecure { return insecureHTTPTransport } return secureHTTPTransport }

由此可以归纳出三档优先级(源码注释中亦明确列出):

  1. 自定义 CA 证书优先:只要CACertificate非空,就基于该证书新建 TLS Transport(WithCustomCACert),使用自定义 CA 验证远端证书;
  2. Insecure 模式:未填 CA 但Insecure=true时,使用全局共享的跳过校验 Transport(insecureHTTPTransport);
  3. 默认模式:两者皆空时,使用系统 CA 池的共享 Transport(secureHTTPTransport)。

这正是测试用例所验证行为的代码级证据:在「填写匹配的 CA 且Verify Remote Cert保持开启」的情况下,请求走的是第 1 档——自定义 CA 校验,而不是被降级为跳过校验。

对应地,TransportOption的两个构造函数定义在同文件 src/common/http/transport.go:

// WithInsecure returns a TransportOption that configures the transport to skip verification of the server's certificate func WithInsecure(skipVerify bool) TransportOption { return func(cfg *TransportConfig) { cfg.Insecure = skipVerify } } // WithCACert returns a TransportOption that configures custom CA certificate func WithCACert(caCert string) TransportOption { return func(cfg *TransportConfig) { cfg.CACertificate = caCert } }

该逻辑还配套了针对性的单元测试,覆盖有效 CA、无效 CA、空 CA、Insecure 与 CA 组合等场景,见 src/common/http/transport_test.go,可作为理解传输层行为的参考。

连接测试(Test Connection)如何判定成功

测试用例中的关键步骤是「点击 Test Connection」。该动作在源码层面最终调用的是原生适配器的HealthCheck(或Ping)方法:

  • src/pkg/reg/adapter/native/adapter.go:HealthCheck依据端点是否配置了凭据,分别走PingSimple(无凭据,仅校验连通性与证书)或Ping(带凭据);
  • src/pkg/reg/adapter/native/adapter.go:PingSimple只关心连通性与 TLS 证书校验是否通过,401/403 等鉴权错误不算失败。

因此,连接测试成功与否直接取决于 TLS 握手阶段的证书校验结果:

  • 当粘贴的 CA 与远端端点证书匹配时,TLS 校验通过 →HealthCheck返回Healthy→ UI 显示连接成功、可保存端点;
  • 当粘贴的 CA 与远端端点证书不匹配(或用错 CA)时,TLS 握手在证书校验处失败(典型错误如x509: certificate signed by unknown authority)→ 测试失败 → 端点无法保存。

这与测试用例的 Expected Outcome 完全一致:

  • Step 2:提供匹配的 CA,Test Connection 成功,端点保存;
  • Step 3:替换为不匹配的 CA,Test Connection 失败。

完整操作步骤(UI 实操)

以下操作路径对应测试用例 7-16,适用于至少两台 Harbor 实例、远端为 HTTPS 自签名证书的环境:

Step 1:准备远端 CA 证书

在运行远端 Harbor 的机器上导出其 HTTPS 证书签发者(自签名证书则导出其自身)的 PEM 内容。如果远端证书由内部 CA 签发,则需要该 CA 的根证书;证书链中间证书可一并放入同一字段(Go 的x509会按 PEM 块依次解析,支持多证书链)。

Step 2:新增端点并配置 CA(用例 Step 2)

  1. 使用 admin 账号登录 Harbor UI;
  2. 进入Administration -> Registries页面;
  3. 点击New Endpoint,填写:
    • 端点 URL:远端 Harbor 的 HTTPS 地址(如https://remote-harbor.example.com);
    • 访问凭证:用户名 / 密码;
    • 保持Verify Remote Cert复选框为勾选状态(即不关闭证书校验);
    • 在CA Certificate文本框中粘贴与远端证书匹配的 PEM 格式 CA 证书;
  4. 点击Test Connection,预期结果为连接成功;
  5. 保存端点。

Step 3:验证不匹配 CA 的拦截(用例 Step 3)

  1. 在Administration -> Registries中编辑刚保存的端点;
  2. 将CA Certificate替换为一张与远端端点证书不匹配的 CA 证书;
  3. 保持Verify Remote Cert勾选;
  4. 再次点击Test Connection,预期结果为连接失败——这正是自定义 CA 生效、证书校验未被绕过的直接证明。

可选:结合 API 验证

Endpoint 创建/更新对应的 REST API 也暴露了insecure与ca_certificate字段(见 api/v2.0/swagger.yaml 的RegistryUpdate定义),可通过 Harbor API 以 JSON 形式设置与查询这两个字段,方便在自动化脚本中复现上述步骤。

常见问题与避坑指南

  • CA 与 Insecure 的优先级:一旦填写了CA Certificate,即使Insecure被置为 false(校验开启),传输层也会优先使用自定义 CA(见上文GetHTTPTransport的分支顺序)。反之,若只勾选不校验而不填 CA,则完全跳过证书校验,安全性最弱。
  • 自签名证书与 IP SAN:在 Harbor 内部(CORE_URL与本机一致)的本地端点场景,源码注释提到会遇到x509: cannot validate certificate for 127.0.0.1 because it doesn't contain any IP SANs类问题,因此本地端点会被强制使用 insecure transport 并忽略 CA 证书,参见 src/pkg/reg/adapter/harbor/base/adapter.go。该行为仅适用于「本 Harbor 检测到目标 URL 与自身一致」的特殊情形,普通远端端点不受影响。
  • 多证书链:CA 字段支持粘贴完整 PEM 链(根 CA + 中间 CA),测试GetHTTPTransport的多证书场景可见 src/common/http/transport_test.go。
  • 证书更换后重新测试:编辑端点替换 CA 后务必重新点击 Test Connection,Harbor 会在保存前用新的传输配置发起一次真实 TLS 握手,不匹配的 CA 会在该阶段即被拒绝。

小结

Harbor 的 per-endpoint CA 证书能力,让复制端点在「保持证书校验开启」的前提下,通过自定义 CA 信任自签名/私有 CA 的远端 Registry,避免了为兼容自签名证书而整体关闭校验的安全妥协。从源码看,其实现机制是传输层GetHTTPTransport对「自定义 CA > Insecure > 系统 CA 池」的三级优先级选择,连接测试则通过适配器HealthCheck/Ping完成真实 TLS 握手验证。参考 测试用例 与 传输层实现,你可以在自己的多 Harbor 复制环境中安全地启用该配置。

【免费下载链接】harborAn open source trusted cloud native registry project that stores, signs, and scans content.项目地址: https://gitcode.com/GitHub_Trending/ha/harbor

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询