export class FhrFlaskCodePipeline extends Stack {
constructor(scope: Construct, id: string, props?: StackProps) {
super(scope, id, props)
const repository = aws_codecommit.Repository.fromRepositoryName(
this,
'FhrFlaskCodeCommit',
'fhr-flask-api'
)
const codebuildRole = new aws_iam.Role(this, 'CodeBuildPushEcr', {
assumedBy: new aws_iam.ServicePrincipal('codebuild.amazonaws.com')
})
codebuildRole.attachInlinePolicy(
new aws_iam.Policy(this, 'CodeBuildInlinePolicy', {
statements: [
new aws_iam.PolicyStatement({
effect: aws_iam.Effect.ALLOW,
actions: ['ecr:*'],
resources: ['*']
}),
new aws_iam.PolicyStatement({
effect: aws_iam.Effect.ALLOW,
actions: ['ssm:*'],
resources: ['*']
})
]
})
)
const codebuild = new aws_codebuild.PipelineProject(
this,
'CodeBuildFhrFlaskEcrImage',
{
role: codebuildRole,
environment: {
buildImage: aws_codebuild.LinuxBuildImage.STANDARD_5_0,
computeType: aws_codebuild.ComputeType.MEDIUM,
privileged: true
},
buildSpec: aws_codebuild.BuildSpec.fromObject({
version: '0.2',
phases: {
install: {
commands: []
},
pre_build: {
commands: [
'aws ecr get-login-password --region ap-southeast-1 | docker login --username AWS --password-stdin 610770234379.dkr.ecr.ap-southeast-1.amazonaws.com'
]
},
build: {
commands: [
'docker build -t fhr-flask-api-image:${CODEBUILD_RESOLVED_SOURCE_VERSION} -f ./ecs-flask-api/lib/app/Dockerfile ./ecs-flask-api/lib/app/',
'docker tag fhr-flask-api-image:${CODEBUILD_RESOLVED_SOURCE_VERSION} 610770234379.dkr.ecr.ap-southeast-1.amazonaws.com/fhr-flask-api-image:${CODEBUILD_RESOLVED_SOURCE_VERSION}'
]
},
post_build: {
commands: [
'aws ssm put-parameter --name FhrEcrImageForFhrFlaskApi --type String --value ${CODEBUILD_RESOLVED_SOURCE_VERSION} --overwrite',
'docker push 610770234379.dkr.ecr.ap-southeast-1.amazonaws.com/fhr-flask-api-image:${CODEBUILD_RESOLVED_SOURCE_VERSION}'
]
}
}
})
}
)
const cdkbuild = new aws_codebuild.PipelineProject(this, 'CdkBuild', {
environment: {
buildImage: aws_codebuild.LinuxBuildImage.STANDARD_5_0,
computeType: aws_codebuild.ComputeType.MEDIUM,
privileged: true
},
buildSpec: aws_codebuild.BuildSpec.fromObject({
version: '0.2',
phases: {
install: {
commands: ['cd ecs-flask-api', 'npm install']
},
build: {
commands: ['npm run build', 'npm run cdk synth -- -o dist']
}
},
artifacts: {
'base-directory': 'ecs-flask-api/dist',
files: ['*.template.json']
}
})
})
const artifactBucket = aws_s3.Bucket.fromBucketName(
this,
'ArtifactBucket',
'fhr-codepipeline-artifact'
)
const sourceOutput = new aws_codepipeline.Artifact('SourceOutput')
const buildOutput = new aws_codepipeline.Artifact('BuildOutput')
const cdkBuildOutput = new aws_codepipeline.Artifact('CdkBuildOutput')
const codepipeline = new aws_codepipeline.Pipeline(
this,
'FhrFlaskCodePipeline',
{
pipelineName: 'FhrFlaskCodePipeline',
artifactBucket: artifactBucket,
stages: [
{
stageName: 'Source',
actions: [
new aws_codepipeline_actions.CodeCommitSourceAction({
actionName: 'Source',
repository: repository,
branch: 'master',
output: sourceOutput
})
]
},
{
stageName: 'CodeBuild',
actions: [
new aws_codepipeline_actions.CodeBuildAction({
actionName: 'BuildFhrFlaskEcrImage',
project: codebuild,
input: sourceOutput,
outputs: [buildOutput]
})
]
},
{
stageName: 'CdkBuild',
actions: [
new aws_codepipeline_actions.CodeBuildAction({
actionName: 'CdkBuild',
project: cdkbuild,
input: sourceOutput,
outputs: [cdkBuildOutput]
})
]
},
{
stageName: 'Deploy',
actions: [
new aws_codepipeline_actions.CloudFormationCreateUpdateStackAction(
{
actionName: 'Deploy',
templatePath: cdkBuildOutput.atPath(
'EcsFlaskApiStack.template.json'
),
stackName: 'EcsFlaskApiApplicationStack',
adminPermissions: true
}
)
]
}
]
}
)
}
}