基于OIDC的Github Action跨AWS账户部署Terraform并访问远端状态
解决方案:跨AWS账户通过OIDC访问Terraform远端State
步骤1:在账户A创建支持GitHub OIDC的IAM角色
要让GitHub Action访问账户A的S3 State桶,需先在账户A配置OIDC信任并创建对应角色:
- 添加GitHub OIDC身份提供商:
在账户A的IAM控制台,创建OIDC提供商,URL填https://token.actions.githubusercontent.com,受众填sts.amazonaws.com。 - 创建信任策略:
新建IAM角色,信任策略允许你的GitHub仓库主体扮演该角色,示例:{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Federated": "arn:aws:iam::[账户A ID]:oidc-provider/token.actions.githubusercontent.com" }, "Action": "sts:AssumeRoleWithWebIdentity", "Condition": { "StringEquals": { "token.actions.githubusercontent.com:aud": "sts.amazonaws.com", "token.actions.githubusercontent.com:sub": "repo:[你的GitHub用户名/仓库名]:ref:refs/heads/[部署分支名]" } } } ] } - 添加S3权限策略:
给该角色附加权限,允许读写账户A的State桶:{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": ["s3:GetObject", "s3:PutObject", "s3:ListBucket"], "Resource": [ "arn:aws:s3:::[账户A State桶名]", "arn:aws:s3:::[账户A State桶名]/*" ] } ] }
步骤2:配置Terraform后端使用账户A角色
修改Terraform后端块,指定要Assume的账户A角色ARN,让Terraform自动切换权限访问远端State:
terraform { backend "s3" { bucket = "[账户A State桶名]" key = "terraform/state/你的项目名称.tfstate" region = "us-east-1" # 替换为桶所在区域 role_arn = "arn:aws:iam::[账户A ID]:role/[账户A创建的OIDC角色名]" # 若启用DynamoDB锁,添加以下配置 # dynamodb_table = "terraform-state-lock-table" } }
步骤3:给账户B的部署角色添加Assume权限
回到账户B,找到你之前创建的部署用OIDC角色,附加权限允许它Assume账户A的角色:
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": "sts:AssumeRole", "Resource": "arn:aws:iam::[账户A ID]:role/[账户A创建的OIDC角色名]" } ] }
步骤4:调整GitHub Action工作流
保持原有获取账户B凭据的步骤不变,Terraform会自动用账户B的权限Assume账户A角色访问State,再用账户B权限部署资源。示例工作流:
name: Terraform Cross-Account Deploy on: push: branches: [ main ] jobs: deploy: runs-on: ubuntu-latest permissions: id-token: write contents: read steps: - name: 拉取代码 uses: actions/checkout@v4 - name: 配置账户B AWS凭据 uses: aws-actions/configure-aws-credentials@v4 with: role-to-assume: arn:aws:iam::[账户B ID]:role/[账户B部署角色名] aws-region: us-east-1 - name: 安装Terraform uses: hashicorp/setup-terraform@v3 - name: Terraform初始化 run: terraform init - name: Terraform计划 run: terraform plan - name: Terraform部署 run: terraform apply -auto-approve
排查要点
- 确认账户A的OIDC提供商URL和受众配置正确
- 检查信任策略的
sub字段是否匹配你的仓库和分支 - 测试账户B角色能否Assume账户A角色:在工作流中添加命令
aws sts assume-role --role-arn "[账户A角色ARN]" --role-session-name "test-session",验证是否返回有效凭据
内容的提问来源于stack exchange,提问作者saturn876e
相关产品推荐
相关产品推荐

