我需要使用 CDK 创建一个管道,该管道将根据 CodeCommit 存储库中的分支触发 CloudFormation 中的部署。如果 CodeCommit 存储库与管道位于同一帐户中,我会使用类似以下内容的内容:
const codecommitRepo = codecommit.Repository.fromRepositoryName(
this,
'AppRepository',
'REPO_NAME'
);
pipeline.addStage({
stageName: 'Source',
actions: [
new codepipeline_actions.CodeCommitSourceAction({
actionName: 'Source',
repository: codecommitRepo,
branch: 'BRANCH_NAME',
output: sourceArtifact,
}),
],
});
但是,如果 CodeCommit 存储库位于不同的帐户中怎么办?
我尝试重新创建的架构类似于 this article 中所示的架构。 (下图),但使用 CDK 和 CloudFormation。
我怎样才能创建它?
最佳答案
如果有人遇到同样的问题,我设法使用 CDK 来解决此问题 this example 。它已经过时了,但我应用了相同的逻辑。由于最近的变化,这个答案中提到的一些步骤可能是不必要的。我找到了一个更新的例子here ,但我还没有尝试过。
重要提示:确保两个帐户中的资源位于同一区域。
让我们通过 CodeCommit 存储库调用 ID_ACC_WITH_REPO 到 AWS 账户 ID,并通过管道和我们想要部署架构的位置调用 ID_ACC_WITH_PIPELINE 到账户 ID。
管道的 CDK 代码
ACC_WITH_REPO
- 在 ID_ACC_WITH_REPO 中创建堆栈。 必须指定区域,因为跨账户管道需要它。
const repoAccStack = new cdk.Stack(app, 'RepoAccStack', {
env: {
account: ID_ACC_WITH_REPO,
region: REPO_REGION
}
});
- 在 ACC_WITH_REPO 中创建跨账户角色,并附加 S3(用于存储工件)、CodeCommit 和 KMS(加密)的完整访问策略。该角色将由 ACC_WITH_PIPELINE 中的管道和源阶段中的 CodeCommit 源操作使用。我想你可以对它们进行更多限制以更加安全。
// Create role
const crossAccRole = new iam.Role(repoAccStack, 'OtherAccRole', {
roleName: 'CrossAccountRole',
assumedBy: new iam.AccountPrincipal(pipelineAcc),
});
// Attach policies
const policy = new iam.PolicyStatement();
policy.addAllResources();
policy.addActions('s3:*', 'codecommit:*', 'kms:*');
crossAccRole.addToPolicy(policy);
- 导入存储库。
const repo = codecommit.Repository.fromRepositoryArn(
repoAccStack,
'AppRepository',
`arn:aws:codecommit:${REPO_REGION}:${ID_ACC_WITH_REPO}:${REPO_NAME}`
);
ACC_WITH_PIPELINE
- 在 ID_ACC_WITH_PIPELINE 中为管道创建堆栈。
const pipelineAccStack = new cdk.Stack(app, 'PipelineAccStack', {
env: {
account: ID_ACC_WITH_PIPELINE,
region: REGION_WITH_PIPELINE
}
});
- 创建 KMS key 。示例中使用的方法
EncryptionKey
已弃用,请改用Key
。
const key = new kms.Key(pipelineAccStack, 'CrossAccountKmsKey');
实际上,我在尝试创建 key 时遇到 kms.model.MalformedPolicyDocumentException
错误,因此我从 AWS 控制台手动执行此操作,然后使用 kms.Key.fromKeyArn< 导入它
。我的帐户可能出了问题(在使用此解决方案之前我遇到了很多错误),但如果您遇到相同的错误,这是一个解决方法。只需确保为管道角色分配使用权限即可。
- 使用之前创建的 KMS 在 ACC_WITH_PIPELINE 中创建 S3 存储桶。需要存储桶名称。示例中使用的
HackyIdentity
不是必需的,类实现中使用的几个方法现已弃用。
const artifactsBucket = new s3.Bucket(pipelineAccStack, "ArtifactsBucket", {
bucketName: BUCKET_NAME,
encryptionKey: key,
encryption: s3.BucketEncryption.KMS
});
artifactsBucket.grantReadWrite(new iam.ArnPrincipal(crossAccRole.roleArn));
- 创建管道并添加第 5 步中创建的跨账户角色。
// Create pipeline
const pipeline = new codepipeline.Pipeline(pipelineAccStack, 'Pipeline', {
pipelineName: 'CrossAccountPipeline',
artifactBucket: artifactsBucket
});
// Add cross-account role
const policy = new iam.PolicyStatement();
policy.addResources(crossAccRole.roleArn)
policy.addActions('s3:*', 'codecommit:*', 'kms:*');
pipeline.addToRolePolicy(policy);
- 使用第 3 步中导入的 CodeCommit 存储库将源阶段添加到管道。
// Create artifact for source code
const sourceArtifact = new codepipeline.Artifact();
// Create source stage with role
pipeline.addStage({
stageName: 'Source',
actions: [
new codepipeline_actions.CodeCommitSourceAction({
actionName: 'CodeCommit_Source',
repository: repo,
output: sourceArtifact,
branch: 'dev',
role: crossAccRole
})
]
});
- 最后添加构建阶段
// Create CodeBuild project
const buildProject = new codebuild.PipelineProject(this, 'Build', {
environment: { buildImage: codebuild.LinuxBuildImage.AMAZON_LINUX_2_2 }
});
// Create artifact for build
const buildArtifact = new codepipeline.Artifact();
// Add build stage
pipeline.addStage({
stageName: 'Build',
actions: [
new codepipeline_actions.CodeBuildAction({
actionName: 'Build',
project: buildProject,
input: sourceArtifact,
outputs: [buildArtifact],
}),
],
});
部署
当 CDK 应用包含多个堆栈时,您不能仅cdk 部署
。 here对此进行了解释。 。但是,如果您尝试 cdk 部署“*”
,则会出现另一个错误:需要对账户 ACCOUNT_ID 执行 AWS 调用,但当前凭证适用于 ACCOUNT_ID
。
我设法使用 cdk deploy -e
部署堆栈,并使用 aws configure
切换帐户。
有三个堆栈,而不是两个。 CDK 自动生成 EventBusPolicy 堆栈来创建事件总线。另外两个事件由 CDK 添加(也是自动)到 PipelineAccStack 和 RepoAccStack 中。 Marcin 的回答解释了如何配置跨帐户事件。应在 ACC_WITH_PIPELINE 中创建 EventBusPolicy 堆栈。要获取堆栈的确切名称,请使用cdk list
。
考虑到所有这些,在本例中我将部署:
# with aws configure in ACC_WITH_PIPELINE
cdk deploy -e "PipelineAccStack"
cdk deploy -e "EventBusPolicy-$ID_ACC_WITH_REPO-$REGION-$ID_ACC_WITH_PIPELINE"
# switch aws configure to ACC_WITH_REPO
cdk deploy -e "RepoAccStack"
关于amazon-web-services - 以跨账户 CodeCommit 存储库作为源的 AWS 管道,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63602642/