☰
eksctl 0.166.0 实战:使用 `utils migrate-to-pod-identity` 将 IRSA 一键迁移到 EKS Pod Identity
2026/10/13 2:12:55 网站建设 项目流程
  • 云原生
  • 容器编排
  • DevOps

【免费下载链接】eksctl

The official CLI for Amazon EKS

项目地址:https://gitcode.com/gh_mirrors/ek/eksctl
点击查看免费下载

导读

eksctlv0.166.0(发布说明)为utils命令族新增了migrate-to-pod-identity子命令(PR #7343),用于把集群中所有基于 IRSAv1(即 iamserviceaccounts + IAM OIDC Provider)的配置自动转换为等价的 Pod Identity Associations 配置。本文将围绕该命令展开:先梳理 IRSA 与 EKS Pod Identity 的差异与迁移动机,再给出命令用法、关键参数与安全前提,然后深入pkg/actions/podidentityassociation源码逐层拆解迁移器生成的每个任务,最后结合测试用例给出验证与回退建议,帮助你在真实集群上安全、可控地完成这一迁移。

为什么需要迁移:IRSA 与 EKS Pod Identity 的本质差异

EKS Pod Identity Associations 是 AWS 推出的增强机制,用于让集群管理员为 Kubernetes 应用配置访问 AWS 服务的 IAM 权限。它与 IRSA(IAM Roles for Service Accounts)共享同一套"用 ServiceAccount 绑定 IAM 角色"的思路,但关键区别在于配置入口从 IAM API 转移到了 EKS API(见 userdocs/src/usage/pod-identity-associations.md):

  • IRSA(IRSAv1):IAM 角色的信任策略必须引用集群的 OIDC Provider(FederatedPrincipal +oidc.eks.<region>.amazonaws.com/id/<id>:sub条件),角色与单个集群强绑定;ServiceAccount 上需要eks.amazonaws.com/role-arn注解(常量定义见 pkg/apis/eksctl.io/v1alpha5/iam.go)。
  • Pod Identity:角色信任pods.eks.amazonaws.com这一 EKS 服务主体(见 pkg/apis/eksctl.io/v1alpha5/iam.go),不再依赖 OIDC Provider,因此同一个 IAM 角色可以跨多个 EKS 集群复用,免去角色重复创建和每建一个新集群都要改写信任策略的负担,也简化了 IRSA 的自动化流程。

迁移的收益即来源于此:把绑定单集群的 OIDC 信任关系替换为跨集群通用的 EKS 服务主体信任,同时把 ServiceAccount 的"注解式"授权改为 EKS API 原生管理的 Pod Identity Association。

前置条件

在运行迁移命令前,需要确认:

  1. Pod Identity Agent 已就绪:Pod Identity 在 worker 节点上以 DaemonSet 形式运行 agent,对应的官方 addon 是eks-pod-identity-agent。若集群已启用 EKS Auto Mode,该 agent 会随集群预装,无需额外操作;否则可先用以下命令安装(usage 文档):
eksctl create addon --cluster my-cluster --name eks-pod-identity-agent
  1. 预先存在的 IAM 角色需要信任 EKS 服务主体:如果 Pod Identity Association 使用的是已有的 IAM 角色,该角色的信任策略必须允许pods.eks.amazonaws.com执行sts:AssumeRole与sts:TagSession。示例信任策略(来自 usage 文档):
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Service": "pods.eks.amazonaws.com" }, "Action": [ "sts:AssumeRole", "sts:TagSession" ] } ] }

如果不在配置中提供既有角色的 ARN,eksctl会在创建 Pod Identity Association 时自动创建角色并配置上述信任策略。好消息是:migrate-to-pod-identity命令会自动完成信任策略改写(详见下文"迁移任务拆解"),无需手工处理。

命令用法与参数

命令通过utils子命令注册(注册点见 pkg/ctl/utils/utils.go):

eksctl utils migrate-to-pod-identity --cluster <cluster-name> [--region <region>] [--approve] [--remove-oidc-provider-trust-relationship] [--timeout <duration>]

命令描述(源码见 pkg/ctl/utils/migrate_to_pod_identity.go):

Migrates all IRSA related config for a cluster to an equivalent pod identity associations config

参数说明:

参数默认值作用
--cluster必填集群名称,缺失时命令会报ErrMustBeSet错误(见 migrate_to_pod_identity.go)
--region默认区域集群所在区域
--approvefalse是否真正执行变更。默认false时以Plan 模式运行,仅打印将要执行的任务清单(PlanMode: !options.Approve,见 migrator.go)
--remove-oidc-provider-trust-relationshipfalse是否同时移除现有 IRSA 角色信任策略中的 OIDC Provider 实体,并删除 ServiceAccount 上的eks.amazonaws.com/role-arn注解;不指定则保留原信任关系(双轨并存,风险更小)
--timeout由 cmdutils 提供默认值安装 addon 等任务的等待超时时间

命令的完整调用链(migrate_to_pod_identity.go)依次执行:

  1. 校验集群名称;创建 AWS Provider 并验证集群可操作(ctl.CanOperate);
  2. 通过NewOpenIDConnectManager检查集群是否关联了 IAM OIDC Provider——如果集群没有 OIDC Provider,说明没有 iamserviceaccount 需要迁移,命令直接告警并退出(logger.Warning("no IAM OIDC provider associated with cluster..."));
  3. 建立 Kubernetes 客户端(NewStdClientSet)读取 ServiceAccount;
  4. 初始化 addon 管理器(addon.New)与 CloudFormation Stack 管理器(NewStackManager);
  5. 组装podidentityassociation.NewMigrator(...)并调用MigrateToPodIdentity(ctx, options)。

迁移任务拆解:源码视角的完整流程

Migrator.MigrateToPodIdentity(pkg/actions/podidentityassociation/migrator.go)把所有操作组织成一颗串行任务树(Parallel: false),每个迁移对象内部再并行执行子任务。整体分四个阶段:

阶段一:确保 Pod Identity Agent 已安装

IsPodIdentityAgentInstalled(migrator.go)先检查集群是否处于 Auto Mode(IsAutoModeEnabled,通过DescribeCluster读取ComputeConfig.Enabled);若不是 Auto Mode,则调用DescribeAddon查询eks-pod-identity-agent(常量见 pkg/apis/eksctl.io/v1alpha5/addon.go)。若 addon 不存在,任务树会追加一个任务:install eks-pod-identity-agent addon,通过addonCreator.Create完成安装。

阶段二:扫描 IRSA 配置(iamserviceaccount + ServiceAccount)

  1. IRSAv1StackNameResolver.Populate(migrator.go)通过stackUpdater.GetIAMServiceAccounts(ctx, "", "")拉取所有由 eksctl CloudFormation 管理的 iamserviceaccount 及其 RoleARN、StackName、Tags、Capabilities,构建"RoleARN → IRSAv1StackSummary"映射;
  2. 遍历 Kubernetes 集群中的全部 ServiceAccount,找出带eks.amazonaws.com/role-arn注解的对象(migrator.go):
    • 通过CreateAddonServiceAccountRoleMapper(addon_role_mapper.go)分页列出全部 EKS addon,将 addon 的ServiceAccountRoleArn映射到 addon 本身;若某 ServiceAccount 的角色 ARN 已被某个 addon 使用,则该角色不按普通 iamserviceaccount 处理,改由 AddonMigrator 专门迁移;
    • 其余角色被收集进toBeCreated(待创建的PodIdentityAssociation列表),并从 ARN 推断角色名(api.RoleNameFromARN);
    • 按角色是否由 eksctl Stack 管理(resolver.GetStack(roleARN)),分别生成"owned role"或"unowned role"的信任策略更新任务。

阶段三:迁移 EKS 托管 Addon(AddonMigrator)

AddonMigrator.Migrate(addon_migrator.go)对每个"使用 IRSAv1 角色"的 addon 执行migrateAddon:

  1. 若 addon 已配置PodIdentityAssociations,直接跳过;
  2. 调用DescribeAddonConfiguration检查该 addon 版本是否支持 Pod Identity(len(addonConfig.PodIdentityConfiguration) == 0则跳过);
  3. 解析角色的信任策略(getRoleServiceAccount,addon_migrator.go),从StringEquals条件中提取形如system:serviceaccount:<ns>:<name>的 ServiceAccount 主体;若提取失败且 addon 只支持一个 ServiceAccount,则使用 addon 配置中声明的默认 ServiceAccount;
  4. 生成两个串行子任务:
    • 更新该角色的信任策略(owned 角色走 CloudFormation Stack 更新,unowned 角色走UpdateAssumeRolePolicy,此处固定传入removeOIDCProviderTrustRelationship=true);
    • updateAddonToUsePodIdentity(addon_migrator.go):调用UpdateAddon,在PodIdentityAssociations字段中填入原ServiceAccountRoleArn与解析出的 ServiceAccount。

阶段四:迁移 iamserviceaccount(并行任务组)

每个待迁移的 ServiceAccount 生成一个独立子任务组(Parallel: true,见 migrator.go),按序执行:

  1. 更新信任策略:trustPolicyUpdater.UpdateTrustPolicyForOwnedRoleTask/UpdateTrustPolicyForUnownedRoleTask(tasks.go)——先GetRole读取现有 AssumeRolePolicyDocument,updateTrustStatements(tasks.go)做两件事:若指定了--remove-oidc-provider-trust-relationship,则删除 Principal 为Federated且指向oidc-provider的语句;随后追加api.EKSServicePrincipalTrustStatement(Service: pods.eks.amazonaws.com+sts:AssumeRole/sts:TagSession)。
    • owned 角色:更新 CloudFormation 模板中AWS::IAM::Role的 AssumeRolePolicyDocument,同时更新 Stack Tags——移除eksctl-iamserviceaccount-name标签(若指定移除信任关系),并打上alpha.eksctl.io/podidentityassociation-name标签(标签常量见 pkg/apis/eksctl.io/v1alpha5/types.go),保留原 Capabilities(如CAPABILITY_IAM)后通过MustUpdateStack应用变更;
    • unowned 角色:直接调用 IAMUpdateAssumeRolePolicy写入新的信任策略文档。
  2. 移除注解(仅当--remove-oidc-provider-trust-relationship为 true):删除 ServiceAccount 上的eks.amazonaws.com/role-arn注解并Update回 Kubernetes。
  3. 创建 Pod Identity Association:NewCreator(...).CreateTasks(ctx, toBeCreated, true),内部调用 EKSCreatePodIdentityAssociation,传入Namespace、RoleARN、ServiceAccount、Tags 以及可选的DisableSessionTags、Policy、TargetRoleArn(跨账户角色链,见 tasks.go);若ignorePodIdentityExistsErr且目标已存在(ResourceInUseException),则跳过并提示。

全部任务执行前,命令会通过cmdutils.LogIntendedAction打印摘要:

migrate N iamserviceaccount(s) and M addon(s) to pod identity by executing the following tasks

若没有任何 iamserviceaccount 或 addon 可迁移,则打印no iamserviceaccounts or addons found to migrate to pod identity并直接返回(migrator.go)。

关键参数详解与推荐迁移策略

关于--remove-oidc-provider-trust-relationship

该参数控制迁移的彻底程度:

  • 不指定(推荐首轮执行):只做"加法"——为角色追加pods.eks.amazonaws.com信任语句、创建 Pod Identity Association、安装 agent。OIDC 信任关系与 ServiceAccount 注解原样保留,IRSAv1 与 Pod Identity 双轨并存。此时 Pod 若通过注解注入凭证仍可工作,适合灰度验证。
  • 指定该参数:在上一基础上执行"减法"——删除角色信任策略中的 OIDC Provider Federated 语句、删除 ServiceAccount 注解,并更新 Stack 标签以反映 IRSAv2 化。迁移完成后集群将不再依赖 IAM OIDC Provider 提供 pod 凭证。

建议流程:先用默认(Plan 模式)查看任务清单 → 不加该参数--approve执行,验证应用正常 → 确认无误后再加--remove-oidc-provider-trust-relationship --approve完成收尾清理。

关于--approve

迁移器把任务树置于PlanMode(PlanMode: !options.Approve),未指定--approve时任务只做规划与打印,不触发任何实际变更(cmdutils.LogPlanModeWarning会输出 Plan 模式提示)。这与 eksctl 一贯的--dry-run心智一致,务必先预览再批准。

迁移后的验证

迁移完成后,可用以下命令确认 Pod Identity Association 已生效(命令及输出格式见 usage 文档):

# 查看全部关联 eksctl get podidentityassociation --cluster my-cluster # 按命名空间过滤 eksctl get podidentityassociation --cluster my-cluster --namespace dev

同时可检查对应 ServiceAccount 上是否已无eks.amazonaws.com/role-arn注解,以及 IAM 角色信任策略是否已包含pods.eks.amazonaws.com主体。

测试与可靠性保障

该功能的测试覆盖在 pkg/actions/podidentityassociation/migrator_test.go 中,使用 Ginkgo 表格驱动 + mockprovider + fake Clientset 验证了多个关键分支:

  • API 错误路径:DescribeAddon失败、GetIAMServiceAccounts失败均返回明确错误(migrator_test.go);
  • agent 安装任务:addon 未安装时任务树包含install eks-pod-identity-agent addon;Auto Mode 下(ComputeConfig.Enabled=true)或ComputeConfig为 nil 时行为正确(migrator_test.go);
  • 注解移除任务:指定RemoveOIDCProviderTrustRelationship时输出remove iamserviceaccount EKS role annotation for "default/service-account-1"(migrator_test.go);
  • owned / unowned 角色分支:owned 角色生成update trust policy for owned role,unowned 角色生成update trust policy for unowned role,两者均生成create pod identity association任务(migrator_test.go);
  • 端到端成功:验证最终信任策略只包含Service: pods.eks.amazonaws.com主体、Stack 标签仅保留alpha.eksctl.io/podidentityassociation-name、模板不再包含oidc(migrator_test.go)。

此外 0.166.0 还修复了build-integration-test for pod_identity_associations(PR #7336)与STS interface(PR #7345),保证迁移链路依赖的接口定义正确。

补充:以配置文件方式管理 Pod Identity

migrate-to-pod-identity是一次性的存量迁移工具;日常的声明式管理仍通过集群配置文件中的iam.podIdentityAssociations字段完成(字段定义见 pkg/apis/eksctl.io/v1alpha5/iam.go,完整示例见 examples/39-pod-identity-association.yaml):

iam: podIdentityAssociations: - namespace: default serviceAccountName: s3-reader createServiceAccount: true # 可选,默认 false roleARN: arn:aws:iam::111122223333:role/role-1 # 提供 roleARN 时仅创建关联 - namespace: dev serviceAccountName: app-cache-access roleName: pod-identity-role-app-cache # 不提供 roleARN 时由 eksctl 创建角色 permissionPolicyARNs: ["arn:aws:iam::111122223333:policy/permission-policy-1"] wellKnownPolicies: autoScaler: true permissionsBoundaryARN: arn:aws:iam::111122223333:policy/permission-boundary

配套命令:

# 创建(集群创建时在 config.yaml 声明后直接生效,或对已有集群) eksctl create podidentityassociation --cluster my-cluster -f config.yaml # 更新 / 删除 eksctl update podidentityassociation --cluster my-cluster -f config.yaml eksctl delete podidentityassociation --cluster my-cluster -f config.yaml

注意:eksctl create cluster -f config.yaml使用iam.podIdentityAssociations时,校验逻辑要求集群同时安装eks-pod-identity-agentaddon(见 pkg/apis/eksctl.io/v1alpha5/validation.go 与 validation.go)。

总结

eksctl utils migrate-to-pod-identity把"IRSA 迁移到 Pod Identity"这一原本需要手工修改角色信任策略、逐个创建 EKS API 关联、清理注解的复杂过程,收敛为一条可预览、可灰度、可回滚(默认保留 OIDC 信任关系)的命令。其底层由一颗结构化的任务树驱动,覆盖 agent 安装、iamserviceaccount 扫描、addon 专用迁移、owned/unowned 角色信任策略差异化处理与 Pod Identity Association 创建,并通过 migrator_test.go 对关键分支做了充分验证。对正在批量使用 iamserviceaccount 的集群而言,这是向 EKS 官方推荐的 Pod Identity 机制平滑演进的最佳起点。

  • 云原生
  • 容器编排
  • DevOps

【免费下载链接】eksctl

The official CLI for Amazon EKS

项目地址:https://gitcode.com/gh_mirrors/ek/eksctl
点击查看免费下载
上一篇:Squire富文本编辑器:与ProtonMail、Tutanota等顶级邮件服务的集成完整指南 🚀
下一篇:osquery预测分析:基于历史数据的智能预测完全指南

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

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

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

立即咨询