Kubernetes v1.33:从 Secret 到 Service Account:Kubernetes 镜像拉取的演进

Kubernetes 稳步发展,以减少对存储在 API 中的长期凭据的依赖。这一转变的一个典型例子是 Kubernetes Service Account (KSA) 令牌从长期、静态的令牌过渡到具有 OpenID Connect (OIDC) 兼容语义的临时、自动轮换的令牌。这一进步使得工作负载能够安全地向外部服务进行身份验证,而无需持久性 Secret。

然而,仍然存在一个主要差距:镜像拉取身份验证。如今,Kubernetes 集群依赖于存储在 API 中的镜像拉取 Secret,这些 Secret 是长期存在的且难以轮换;或者依赖于节点级别的 kubelet 凭据提供程序,这允许在节点上运行的任何 Pod 访问相同的凭据。这带来了安全和运营方面的挑战。

为了解决这个问题,Kubernetes 正在引入针对 Kubelet 凭据提供程序的 Service Account 令牌集成,该功能目前处于 Alpha 阶段。这一增强功能允许凭据提供程序使用特定于 Pod 的 Service Account 令牌来获取镜像仓库凭据,然后 kubelet 可以使用这些凭据进行镜像拉取——从而消除了对长期镜像拉取 Secret 的需求。

镜像拉取 Secret 的问题

目前,Kubernetes 管理员在处理私有容器镜像拉取方面主要有两种选择:

  1. 存储在 Kubernetes API 中的镜像拉取 Secret

    • 这些 Secret 通常是长期有效的,因为它们难以轮换。
    • 它们必须显式附加到 Service Account 或 Pod 上。
    • 拉取 Secret 的泄露可能导致未经授权的镜像访问。
  2. Kubelet 凭据提供程序

    • 这些提供程序在节点级别动态获取凭据。
    • 在同一节点上运行的任何 Pod 都可以访问相同的凭据。
    • 没有按工作负载进行隔离,增加了安全风险。

这两种方法都不符合最小权限临时身份验证的原则,给 Kubernetes 留下了安全隐患。

解决方案:针对 Kubelet 凭据提供程序的 Service Account 令牌集成

这项新增强功能使得 Kubelet 凭据提供程序能够在获取镜像仓库凭据时使用工作负载身份。凭据提供程序不再依赖于长期有效的 Secret,而是可以使用 Service Account 令牌来请求与特定 Pod 身份绑定的短期凭据。

这种方法提供了:

  • 特定于工作负载的身份验证:镜像拉取凭据的作用域限定于特定的工作负载。
  • 临时凭据:令牌会自动轮换,消除了长期 Secret 带来的风险。
  • 无缝集成:与现有的 Kubernetes 身份验证机制配合工作,符合云原生安全最佳实践。

工作原理

1. 用于凭据提供程序的 Service Account 令牌

如果 kubelet 通信的凭据提供程序已选择接收用于镜像拉取的 Service Account 令牌,那么 kubelet 会为 Service Account 生成短期的、自动轮换的令牌。这些令牌符合 OIDC ID 令牌语义,并作为 CredentialProviderRequest 的一部分提供给凭据提供程序。然后,凭据提供程序可以使用此令牌向外部服务进行身份验证。

2. 镜像仓库身份验证流程

  • 当一个 Pod 启动时,kubelet 会向一个凭据提供程序请求凭据。
  • 如果凭据提供程序已选择接收令牌,kubelet 会为该 Pod 生成一个 Service Account 令牌
  • Service Account 令牌包含在 CredentialProviderRequest,允许凭据提供程序进行身份验证,并将其换取来自镜像仓库(例如 AWS ECR、GCP Artifact Registry、Azure ACR)的临时镜像拉取凭据
  • 然后,kubelet 使用这些凭据代表 Pod 拉取镜像。

这种方法的优点

  • 安全性:消除了长期有效的镜像拉取 Secret,减少了攻击面。
  • 精细的访问控制:凭据与单个工作负载绑定,而不是整个节点或集群。
  • 操作简便性:管理员无需手动管理和轮换镜像拉取 Secret。
  • 提高合规性:帮助组织满足禁止在集群中使用持久性凭据的安全策略。

接下来是什么?

对于 Kubernetes v1.34,我们预计将该功能以 Beta 版本发布,同时继续收集用户的反馈。

在接下来的版本中,我们将重点关注:

  • 实现缓存机制,以提高令牌生成的性能。
  • 凭据提供程序提供更多灵活性,使其能够决定如何缓存返回给 kubelet 的镜像仓库凭据。
  • 使该功能与“确保镜像是通过 Secret 拉取的”协同工作,以确保在使用 Service Account 令牌进行身份验证时,使用某个镜像的 Pod 都有权访问该镜像。

你可以在 Kubernetes 文档的用于镜像拉取的 Service Account 令牌页面上了解更多关于此功能的信息。

你也可以关注 KEP-4412 来跟踪未来 Kubernetes 版本中的进展。

立即试用

要试用此功能:

  1. 确保你正在运行 Kubernetes v1.33 或更高版本。.
  2. 在 kubelet 上启用 ServiceAccountTokenForKubeletCredentialProviders 特性门控
  3. 确保凭据提供程序支持:修改或更新你的凭据提供程序,以使用 Service Account 令牌进行身份验证。
  4. 更新凭据提供程序配置,通过配置 tokenAttributes 字段来选择为凭据提供程序接收 Service Account 令牌。
  5. 部署一个 Pod,该 Pod 使用凭据提供程序从私有镜像仓库拉取镜像。

我们非常希望听到你对这个功能的反馈。请通过 Kubernetes Slack 上的 #sig-auth-authenticators-dev 频道与我们联系(如需邀请,请访问 https://slack.k8s.io/)。

如何参与

如果你有兴趣参与此功能的开发、分享反馈或参与任何其他正在进行的 SIG Auth 项目,请在 Kubernetes Slack 上的 #sig-auth 频道与我们联系。

我们也欢迎你参加每两周举行一次的 SIG Auth 会议,会议在每隔一个星期三举行。