2. 核心概念:Kubernetes Secret 类型详解

Kubernetes Secret 是集群中存储敏感信息的标准对象,其核心价值在于将敏感数据与 Pod 定义解耦。Secret 的类型(type 字段)决定了数据的编码方式、校验逻辑以及 Kubelet 在拉取镜像时的处理行为。本章重点剖析与镜像拉取认证直接相关的 docker-registry 类型,并对比其他常见类型。

2.1 Secret 类型总览与分类

Kubernetes 原生支持多种 Secret 类型,每种类型对应特定的使用场景。下表列出了最常用的几种类型及其核心差异:

Secret 类型 用途 数据键(data 字段) 编码方式
Opaque 通用型,存储任意键值对(密码、 等) 用户自定义 Base64
kubernetes.io/dockerconfigjson 镜像仓库认证(推荐方式) .dockerconfigjson Base64 编码的 Docker config.json
kubernetes.io/dockercfg 镜像仓库认证(旧版格式) .dockercfg Base64 编码的 Docker config
kubernetes.io/basic-auth HTTP 基本认证(用户名+密码) username, password Base64
kubernetes.io/tls TLS 证书与私钥 tls.crt, tls.key Base64
kubernetes.io/ssh-auth SSH 认证私钥 ssh-privatekey Base64
关键提示: 在镜像拉取场景中,dockerconfigjson 是唯一被 Kubelet 原生支持的 Secret 类型。使用 Opaque 类型存储 Docker 认证信息虽然技术上可行,但 Kubelet 不会自动解析,必须通过 imagePullSecrets 字段显式引用,且格式必须符合 Docker 规范。

2.2 重点详解:docker-registry 类型(dockerconfigjson)

kubernetes.io/dockerconfigjson 是 Kubernetes 为镜像仓库认证专门设计的 Secret 类型。它的核心数据是一个符合 Docker 客户端规范的 config.json 文件,经过 Base64 编码后存储在 .dockerconfigjson 键中。

2.2.1 数据结构与格式

一个典型的 dockerconfigjson Secret 的 YAML 定义如下:

apiVersion: v1
kind: Secret
metadata:
  name: my-registry-secret
  namespace: default
type: kubernetes.io/dockerconfigjson
data:
  .dockerconfigjson: eyJhdXRocyI6eyJodHRwczovL2luZGV4LmRvY2tlci5pby92MS8iOnsiYXV0aCI6ImJtVjRZVzF3YjI1bGJtOXlJR1ZzYVhOcGJtYz0ifX19

解码后的 .dockerconfigjson 内容(Base64 解码后)是一个 JSON 对象:

{
  "auths": {
    "https://index.docker.io/v1/": {
      "auth": "base64_encoded_username:password"
    }
  }
}

其中 auth 字段的值是 username:password 的 Base64 编码字符串。Kubelet 在拉取镜像时,会读取该 Secret,解码 .dockerconfigjson,提取对应仓库地址的认证信息,并注入到容器运行时的拉取请求中。

2.2.2 创建方式对比

Kubernetes 提供了两种创建 dockerconfigjson Secret 的方式:

创建方式 命令/方法 适用场景 优点
命令行(推荐) kubectl create secret docker-registry 交互式创建,适合手动操作 自动生成 .dockerconfigjson 格式,无需手动 Base64 编码
YAML 文件 手动编写 YAML 并 kubectl apply GitOps、CI/CD 流水线 可版本控制,适合自动化部署

命令行创建示例:

kubectl create secret docker-registry my-registry-secret \
  --docker-server=https://index.docker.io/v1/ \
  --docker-username=myuser \
  --docker-password=mypassword \
  --docker-email=myuser@example.com \
  --namespace=default
注意: --docker-email 字段在 Docker Hub 的旧版 API 中是必填项,但对于其他兼容 OCI 的镜像仓库(如 Harbor、GitLab Container Registry),该字段通常可选。Kubernetes 1.24+ 版本中,该字段已标记为可选。

2.2.3 与旧版 dockercfg 的对比

Kubernetes 早期版本支持 kubernetes.io/dockercfg 类型,其数据格式为 .dockercfg(Docker 1.x 时代的配置文件格式)。两者对比如下:

特性 dockerconfigjson dockercfg
数据键 .dockerconfigjson .dockercfg
内部格式 Docker 1.13+ 的 config.json Docker 1.12 及更早的 config
推荐状态 当前推荐 已弃用(但兼容)
Kubelet 支持 完全支持 兼容支持

2.3 其他相关 Secret 类型

2.3.1 basic-auth 类型

kubernetes.io/basic-auth 用于存储 HTTP 基本认证凭据。虽然它不直接用于镜像拉取,但在某些场景下(如通过 Ingress 访问私有镜像仓库的 Web UI)会用到。

apiVersion: v1
kind: Secret
metadata:
  name: my-basic-auth
type: kubernetes.io/basic-auth
data:
  username: bXl1c2Vy
  password: bXlwYXNzd29yZA==

2.3.2 tls 类型

kubernetes.io/tls 用于存储 TLS 证书和私钥,通常用于 Ingress 的 HTTPS 终止。在镜像拉取场景中,如果仓库启用了双向 TLS(mTLS),则需要将客户端证书和私钥以 tls 类型 Secret 挂载到 Pod 中,但这不是 Kubelet 原生支持的镜像拉取认证方式。

2.4 Secret 类型选择与镜像拉取的关系

下图展示了 Kubelet 在拉取镜像时如何根据 Pod 的 imagePullSecrets 字段选择并解析 Secret:

Kubelet 镜像拉取认证流程(Secret 类型解析) Pod 创建/调度 检查 imagePullSecrets 读取 Secret 对象 判断 Secret.type dockerconfigjson 解析 .dockerconfigjson dockercfg(旧版) 解析 .dockercfg 其他类型(Opaque 等) 需手动处理格式 说明:Kubelet 仅对 dockerconfigjson 和 dockercfg 类型自动解析认证信息;其他类型需用户确保格式正确。

2.5 最佳实践与常见误区

  • 始终使用 dockerconfigjson 类型: 对于镜像拉取认证,优先使用 kubernetes.io/dockerconfigjson,避免使用 Opaque 类型手动构造认证数据。
  • 避免在 Secret 中存储明文密码: 即使 Base64 编码不是加密,也应结合 RBAC 限制 Secret 的访问权限,并启用 etcd 加密。
  • 注意命名空间隔离: imagePullSecrets 必须与 Pod 位于同一命名空间,或通过 ServiceAccount 的 secrets 字段全局注入。
  • 不要混淆 basic-auth 与 dockerconfigjson: basic-auth 不包含仓库地址信息,Kubelet 无法将其用于镜像拉取。
故障排查要点: 当镜像拉取失败时,首先检查 imagePullSecrets 引用的 Secret 类型是否为 dockerconfigjson,然后验证 .dockerconfigjson 中的仓库地址是否与镜像地址的 registry 部分完全匹配(包括端口号)。