CI CD & infrastructure - mzogheib/quoll GitHub Wiki
- GitHub Actions for CI/CD
- Terraform for deploying AWS resources
- Terraform Cloud for the backend
- Source is in another private repo
- Avoid long lived AWS keys stored in Terraform Cloud or GitHub
- Instead, authenticate via an OIDC provider
- Basic steps:
- Create the OIDC provider in IAM
- Create the role in IAM
- Add permission policies to the role, e.g. permission to create ECR repositories
- Add a trust policy to the role that allows the provider to assume the role
- Add the role's ARN to your provider, e.g. as an env variable or workflow input
- Given that this is a one time setup it can be done via the AWS and Terraform UIs
- Guides
- Replace all the
<...>
with your values - The condition values can be wildcards
*
to allow all, e.g.run_phase:*
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Federated": "arn:aws:iam::<ACCOUNT-ID>:oidc-provider/app.terraform.io"
},
"Action": "sts:AssumeRoleWithWebIdentity",
"Condition": {
"StringEquals": {
"app.terraform.io:aud": "aws.workload.identity"
},
"StringLike": {
"app.terraform.io:sub": "organization:<ORGANIZATION>:project:<PROJECT>:workspace:<WORKSPACE>:run_phase:<RUN-PHASE>"
}
}
}
]
}
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Federated": "arn:aws:iam::<ACCOUNT-ID>:oidc-provider/token.actions.githubusercontent.com"
},
"Action": "sts:AssumeRoleWithWebIdentity",
"Condition": {
"StringEquals": {
"token.actions.githubusercontent.com:aud": "sts.amazonaws.com"
},
"StringLike": {
"token.actions.githubusercontent.com:sub": "repo:<ORGANIZATION>/<REPO>:<BRANCH>"
}
}
}
]
}
- Push to
master
- Workflow runs to raise a release PR
- Workflow runs to run all tests
- If tests pass, can merge the release PR
- Workflow runs to create new application and packages and publish applicable packages
- If new application tags created, workflow runs to build and push Docker images
- If new images created, workflow runs to deploy to cloud
Tag trigger: @quoll/api@*
- Build Docker image
- Push to Docker repository
- https://github.com/docker/build-push-action
- See example workflow and specify the input
file: packages/api/Dockerfile
- Use the workflow reference for the image tag https://github.com/orgs/community/discussions/26686
- Parse the git tag from
@quoll/api/0.0.0
to0.0.0
. Image tags have a strict syntax.
- Log in to EC2 instance via EC2 Instance Connect
- Create/update the
.env
,docker-compose.yaml
files - Get the ECR credentials (it has an IAM role that has the permission to do this)
aws ecr get-login-password --region <REGION> | sudo docker login --username AWS --password-stdin <AWS_ACCOUNT_ID>.dkr.ecr.<REGION>.amazonaws.com
- Stop the existing image if running
sudo docker-compose down
- Run the latest image
sudo docker-compose up -d
- Can't use the default
GITHUB_TOKEN
if the intention is to trigger one workflow as a side effect of another, e.g. workflow A creates a git tag then workflow B is triggered on the creation of that tag.- See here. It's intentional.
- Workaround is to use a personal access token.