3. OCI Registry 基础:OCI 标准、Helm 与 OCI 的集成方式、推送与拉取流程

3.1 OCI 标准与 Helm Chart 的容器化

OCI(Open Container Initiative)标准最初用于定义容器镜像的格式与运行时规范。Helm v3.8+ 将 Chart 打包为符合 OCI 标准的制品(Artifact),使 Helm Chart 能够像容器镜像一样被存储、版本化、分发和签名。

维度 传统 Helm Chart 仓库 OCI Registry 方式
存储格式 tgz + index.yaml OCI Manifest + Layer Blob
版本控制 依赖 index.yaml 手动管理 Registry 原生 tag/digest
访问控制 HTTP Basic / 自定义 Bearer / OIDC
签名与验证 无标准机制 Notation / Cosign 集成
多架构支持 不适用 OCI Index 原生支持
关键概念:OCI 将 Helm Chart 视为一个“层”(Layer),Chart 的 metadata 和 values 被序列化为 JSON 并打包成 OCI 层。Registry 通过 application/vnd.cncf.helm.chart.content.v1.tar+gzip 等媒体类型识别 Chart 制品。

3.2 Helm 与 OCI Registry 的集成方式

Helm 通过内置的 registry 子命令与 OCI Registry 交互,无需额外插件。集成方式分为以下三种场景:

  • 直接推送/拉取:使用 helm push 和 helm pull 命令,指定 OCI 格式的引用地址(oci://registry.example.com/namespace/chartname)。
  • Chart 依赖引用:在 Chart.yaml 的 dependencies 中直接使用 repository: oci://... 声明依赖。
  • Helm OCI 登录:通过 helm registry login 完成身份认证,支持用户名/密码、 或 OIDC 流程。
最佳实践:生产环境中建议为每个 Helm Chart 使用独立的 OCI Repository,并启用镜像不可变标签(immutable tag)策略,防止意外覆盖已发布的 Chart 版本。

3.3 推送与拉取流程详解

3.3.1 推送流程(Push)

  1. 打包 Chart:helm package ./mychart 生成 mychart-1.0.0.tgz。
  2. 登录 Registry:helm registry login myregistry.io 获取访问凭证。
  3. 推送 Chart:helm push mychart-1.0.0.tgz oci://myregistry.io/helm-charts。
  4. Registry 处理:Registry 解析 Chart 层,生成 OCI Manifest 并返回 digest。

3.3.2 拉取流程(Pull)

  1. 拉取 Chart:helm pull oci://myregistry.io/helm-charts/mychart --version 1.0.0。
  2. 下载 Manifest:Helm 客户端请求 OCI Manifest,获取层列表。
  3. 解压层:下载 Chart 层(tgz),Helm 自动解压到本地目录。
  4. 验证完整性:Helm 校验 digest 是否与 Manifest 一致,防止篡改。
Helm Chart OCI 推送与拉取流程 推送流程(Push) ① helm package ./mychart ② helm registry login myregistry.io ③ helm push chart.tgz oci://... 拉取流程(Pull) ① helm pull oci://... --version 1.0.0 ② 下载 OCI Manifest ③ 解压 Chart 层并校验 digest OCI Registry Manifest + Layer Blob 一致性复核关键点 推送时记录 Chart digest → 拉取时校验 digest 一致性 确保故障域切换后拉取的 Chart 与原始推送完全一致

3.4 OCI 引用格式与版本标识

Helm 使用 OCI 引用(Reference)定位 Chart,格式如下:

oci://registry.example.com/namespace/chartname:version
# 示例
oci://myregistry.io/helm-charts/nginx-ingress:4.0.13
引用组件 说明 示例值
Scheme 固定为 oci:// oci://
Registry 地址 Registry 的 FQDN 或 IP myregistry.io
Repository Chart 所在的命名空间/仓库 helm-charts/nginx-ingress
Tag Chart 版本号,对应 Chart.yaml 中的 version 4.0.13
注意:OCI Registry 中的 tag 是可变的。在故障域一致性复核场景中,应优先使用 digest(@sha256:...)而非 tag 进行引用,确保每次拉取的 Chart 内容与原始推送完全一致。

3.5 故障域一致性复核中的 OCI 关键属性

在跨故障域同步 Helm Chart 时,以下 OCI 属性是一致性复核的核心依据:

  • Manifest Digest:Chart 内容的唯一指纹,任何层变更都会导致 digest 变化。
  • Layer Digest:每个 Chart 层(tgz)的 SHA256 校验值。
  • Media Type:标识 Chart 格式版本,如 application/vnd.cncf.helm.chart.content.v1.tar+gzip。
  • Annotations:可携带 Chart 元数据(如 Chart.yaml 中的 description、appVersion),用于辅助验证。
# 查看 OCI Manifest 示例(精简)
{
  "schemaVersion": 2,
  "mediaType": "application/vnd.oci.image.manifest.v1+json",
  "config": {
    "mediaType": "application/vnd.cncf.helm.chart.config.v1+json",
    "digest": "sha256:abc123...",
    "size": 1024
  },
  "layers": [
    {
      "mediaType": "application/vnd.cncf.helm.chart.content.v1.tar+gzip",
      "digest": "sha256:def456...",
      "size": 20480
    }
  ],
  "annotations": {
    "org.opencontainers.image.version": "1.0.0",
    "org.opencontainers.image.title": "mychart"
  }
}
一致性复核要点:在故障域 A 推送 Chart 后,记录其 Manifest Digest(如 sha256:abc123...)。在故障域 B 拉取时,使用 helm pull oci://...@sha256:abc123... 强制拉取指定 digest,然后对比本地解压后的 Chart.yaml 与原始推送版本是否一致。任何 digest 不匹配都表明 Chart 内容已被篡改或同步失败。