Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 47 additions & 0 deletions .github/actions/setup-opentofu/action.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
name: Setup OpenTofu
description: Sets up OpenTofu and related environment variables
inputs:
config:
description: OpenTofu configuration to initialize.
required: true
default: service
runs:
using: composite
steps:
- name: Cache OpenTofu
uses: actions/cache@v4
with:
path: ./tofu/config/${{ inputs.config }}/.terraform
key: ${{ runner.os }}-tofu-${{ hashFiles('./tofu/config/${{ inputs.config }}/.terraform.lock.hcl') }}
restore-keys: |
${{ runner.os }}-tofu-
- name: Setup OpenTofu
uses: opentofu/setup-opentofu@v1
with:
tofu_wrapper: false
- name: Display OpenTofu version
shell: bash
run: tofu version
- name: Set optional variables
shell: bash
run: |
variables=(
"apply_database_updates_immediately" "consumer_container_count"
"consumer_cpu" "consumer_memory" "database_instance_count"
"database_skip_final_snapshot" "deletion_protection"
"deployment_environments" "environment" "export_expiration"
"image_tags_mutable" "key_recovery_period" "program" "project" "repository"
)
for var in ${variables[@]}; do
name="TF_VAR_$(echo $var | tr '[:lower:]' '[:upper:]')"
if [ -n "${!name}" ]; then
echo "Setting TF_VAR_$var"
echo "TF_VAR_$var=${!name}" >> $GITHUB_ENV
else
echo "$name is not set"
fi
done
- name: Initialize OpenTofu
shell: bash
working-directory: ./tofu/config/${{ inputs.config }}
run: tofu init
68 changes: 24 additions & 44 deletions .github/workflows/deploy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -80,55 +80,35 @@ jobs:
aws-region: ${{ secrets.AWS_REGION || 'us-west-1' }}
role-to-assume: ${{ secrets.AWS_ROLE_ARN }}
role-session-name: GitHub_to_AWS_via_FederatedOIDC
- name: Setup OpenTofu
uses: opentofu/setup-opentofu@v1
with:
tofu_wrapper: false
- name: Display OpenTofu version
run: tofu version
- name: Set optional variables
env:
# For any of these that have a value, the corresponding TF_VAR_*
# environment variable will be set.
APPLY_DATABASE_UPDATES_IMMEDIATELY: ${{ secrets.TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY }}
TF_VAR_CONSUMER_CONTAINER_COUNT: ${{ secrets.TF_VAR_CONSUMER_CONTAINER_COUNT }}
CONSUMER_CPU: ${{ secrets.TF_VAR_CONSUMER_CPU }}
CONSUMER_MEMORY: ${{ secrets.TF_VAR_CONSUMER_MEMORY }}
DATABASE_SKIP_FINAL_SNAPSHOT: ${{ secrets.TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT }}
DELETION_PROTECTION: ${{ secrets.TF_VAR_DELETION_PROTECTION }}
DEPLOYMENT_ENVIRONMENTS: ${{ secrets.TF_VAR_DEPLOYMENT_ENVIRONMENTS }}
ENVIRONMENT: ${{ secrets.TF_VAR_ENVIRONMENT }}
EXPORT_EXPIRATION: ${{ secrets.TF_VAR_EXPORT_EXPIRATION }}
IMAGE_TAGS_MUTABLE: ${{ secrets.TF_VAR_IMAGE_TAGS_MUTABLE }}
KEY_RECOVERY_PERIOD: ${{ secrets.TF_VAR_KEY_RECOVERY_PERIOD }}
PROGRAM: ${{ secrets.TF_VAR_PROGRAM }}
PROJECT: ${{ secrets.TF_VAR_PROJECT }}
REPOSITORY: ${{ secrets.TF_VAR_REPOSITORY }}
run: |
variables=(
"apply_database_updates_immediately" "consumer_container_count"
"consumer_cpu" "consumer_memory" "database_skip_final_snapshot"
"deletion_protection" "deployment_environments" "environment"
"export_expiration" "image_tags_mutable" "key_recovery_period"
"program" "project" "repository"
)
for var in ${variables[@]}; do
name="$(echo $var | tr '[:lower:]' '[:upper:]')"
if [ -n "${!name}" ]; then
echo "Setting TF_VAR_$var"
echo "TF_VAR_$var=${!name}" >> $GITHUB_ENV
else
echo "$name is not set"
fi
done
- name: Download plan file
uses: actions/download-artifact@v4
with:
name: ${{ inputs.config }}-tfplan
path: ./tofu/config/${{ inputs.config }}
- name: Initialize OpenTofu
working-directory: ./tofu/config/${{ inputs.config }}
run: tofu init
- name: Setup OpenTofu
uses: ./.github/actions/setup-opentofu
env:
TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY: ${{ secrets.TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY }}
TF_VAR_CONSUMER_CONTAINER_COUNT: ${{ secrets.TF_VAR_CONSUMER_CONTAINER_COUNT }}
TF_VAR_CONSUMER_CPU: ${{ secrets.TF_VAR_CONSUMER_CPU }}
TF_VAR_CONSUMER_MEMORY: ${{ secrets.TF_VAR_CONSUMER_MEMORY }}
TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT: ${{ secrets.TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT }}
TF_VAR_DATABASE_INSTANCE_COUNT: ${{ secrets.TF_VAR_DATABASE_INSTANCE_COUNT }}
TF_VAR_DELETION_PROTECTION: ${{ secrets.TF_VAR_DELETION_PROTECTION }}
TF_VAR_DEPLOYMENT_ENVIRONMENTS: ${{ secrets.TF_VAR_DEPLOYMENT_ENVIRONMENTS }}
TF_VAR_ENVIRONMENT: ${{ inputs.environment }}
TF_VAR_EXPORT_EXPIRATION: ${{ secrets.TF_VAR_EXPORT_EXPIRATION }}
TF_VAR_IMAGE_TAGS_MUTABLE: ${{ secrets.TF_VAR_IMAGE_TAGS_MUTABLE }}
TF_VAR_KEY_RECOVERY_PERIOD: ${{ secrets.TF_VAR_KEY_RECOVERY_PERIOD }}
TF_VAR_PROJECT: ${{ secrets.TF_VAR_PROJECT }}
TF_VAR_PROGRAM: ${{ secrets.TF_VAR_PROGRAM }}
TF_VAR_REPO_OIDC_ARN: ${{ secrets.TF_VAR_REPO_OIDC_ARN }}
TF_VAR_REPOSITORY: ${{ secrets.TF_VAR_REPOSITORY }}
TF_VAR_VPC_CIDR: ${{ secrets.TF_VAR_VPC_CIDR }}
TF_VAR_VPC_PRIVATE_SUBNET_CIDRS: ${{ secrets.TF_VAR_VPC_PRIVATE_SUBNET_CIDRS }}
TF_VAR_VPC_PUBLIC_SUBNET_CIDRS: ${{ secrets.TF_VAR_VPC_PUBLIC_SUBNET_CIDRS }}
with:
config: ${{ inputs.config }}
- name: Deploy changes
working-directory: ./tofu/config/${{ inputs.config }}
run: tofu apply tfplan
110 changes: 110 additions & 0 deletions .github/workflows/launch-tools.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,110 @@
name: Launch tools container

on:
workflow_dispatch:
inputs:
environment:
description: Environment to destroy.
default: development
required: true
type: environment
command:
description: |
Command to run in the tools container in the CMD format: executable,
param1, param2, ...
default: "echo,hello world"
required: true
type: string

permissions:
contents: read
id-token: write

jobs:
launch:
name: Launch tools container in ${{ inputs.environment }}
runs-on: ubuntu-latest
environment: ${{ inputs.environment }}
env:
# Set required variables.
TF_VAR_repo_oidc_arn: ${{ secrets.TF_VAR_REPO_OIDC_ARN }}
TF_VAR_vpc_cidr: ${{ secrets.TF_VAR_VPC_CIDR }}
TF_VAR_vpc_private_subnet_cidrs: ${{ secrets.TF_VAR_VPC_PRIVATE_SUBNET_CIDRS }}
TF_VAR_vpc_public_subnet_cidrs: ${{ secrets.TF_VAR_VPC_PUBLIC_SUBNET_CIDRS }}
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set up AWS credentials
uses: aws-actions/configure-aws-credentials@v4
with:
aws-region: ${{ secrets.AWS_REGION || 'us-west-1' }}
role-to-assume: ${{ secrets.AWS_ROLE_ARN }}
role-session-name: GitHub_to_AWS_via_FederatedOIDC
- name: Setup OpenTofu
uses: ./.github/actions/setup-opentofu
env:
TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY: ${{ secrets.TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY }}
TF_VAR_CONSUMER_CONTAINER_COUNT: ${{ secrets.TF_VAR_CONSUMER_CONTAINER_COUNT }}
TF_VAR_CONSUMER_CPU: ${{ secrets.TF_VAR_CONSUMER_CPU }}
TF_VAR_CONSUMER_MEMORY: ${{ secrets.TF_VAR_CONSUMER_MEMORY }}
TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT: ${{ secrets.TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT }}
TF_VAR_DATABASE_INSTANCE_COUNT: ${{ secrets.TF_VAR_DATABASE_INSTANCE_COUNT }}
TF_VAR_DELETION_PROTECTION: ${{ secrets.TF_VAR_DELETION_PROTECTION }}
TF_VAR_DEPLOYMENT_ENVIRONMENTS: ${{ secrets.TF_VAR_DEPLOYMENT_ENVIRONMENTS }}
TF_VAR_ENVIRONMENT: ${{ inputs.environment }}
TF_VAR_EXPORT_EXPIRATION: ${{ secrets.TF_VAR_EXPORT_EXPIRATION }}
TF_VAR_IMAGE_TAGS_MUTABLE: ${{ secrets.TF_VAR_IMAGE_TAGS_MUTABLE }}
TF_VAR_KEY_RECOVERY_PERIOD: ${{ secrets.TF_VAR_KEY_RECOVERY_PERIOD }}
TF_VAR_PROJECT: ${{ secrets.TF_VAR_PROJECT }}
TF_VAR_PROGRAM: ${{ secrets.TF_VAR_PROGRAM }}
TF_VAR_REPO_OIDC_ARN: ${{ secrets.TF_VAR_REPO_OIDC_ARN }}
TF_VAR_REPOSITORY: ${{ secrets.TF_VAR_REPOSITORY }}
TF_VAR_VPC_CIDR: ${{ secrets.TF_VAR_VPC_CIDR }}
TF_VAR_VPC_PRIVATE_SUBNET_CIDRS: ${{ secrets.TF_VAR_VPC_PRIVATE_SUBNET_CIDRS }}
TF_VAR_VPC_PUBLIC_SUBNET_CIDRS: ${{ secrets.TF_VAR_VPC_PUBLIC_SUBNET_CIDRS }}
with:
config: service
- name: Get OpenTofu outputs
id: outputs
working-directory: ./tofu/config/service
run: |
OUTPUTS=$(tofu output -json | jq -c)
echo "OUTPUTS=$OUTPUTS"
echo "outputs=$OUTPUTS" >> $GITHUB_OUTPUT
- name: Parse subnets
id: subnets
env:
SUBNETS: ${{ toJson(fromJson(steps.outputs.outputs.outputs).container_subnets.value) }}
run: |
SUBNET_STRING=$(echo "$SUBNETS" | jq -r '.[]')
echo "subnets<<EOF" >> $GITHUB_OUTPUT
echo "$SUBNET_STRING" >> $GITHUB_OUTPUT
echo "EOF" >> $GITHUB_OUTPUT
- name: Parse command
id: command
env:
COMMAND: ${{ inputs.command }}
run: |
IFS=',' read -ra parts <<< "$COMMAND"
COMMAND_STRING=$(printf "%s\n" "${parts[@]}")
echo "command<<EOF" >> $GITHUB_OUTPUT
echo "$COMMAND_STRING" >> $GITHUB_OUTPUT
echo "EOF" >> $GITHUB_OUTPUT
- name: Launch container
id: run-task
uses: geekcell/github-action-aws-ecs-run-task@v5
with:
cluster: ${{ secrets.TF_VAR_PROJECT }}-${{ secrets.TF_VAR_ENVIRONMENT }}
task-definition: ${{ secrets.TF_VAR_PROJECT }}-${{ secrets.TF_VAR_ENVIRONMENT }}-tools
override-container: ${{ secrets.TF_VAR_PROJECT }}-${{ secrets.TF_VAR_ENVIRONMENT }}-tools
assign-public-ip: DISABLED
tail-logs: true
task-wait-until-stopped: true
# The block style indicator (|) is necessary to tell YAML to preserve
# newlines.
override-container-command: |
${{ steps.command.outputs.command }}
subnet-ids: |
${{ steps.subnets.outputs.subnets }}
security-group-ids: |
${{ fromJson(steps.outputs.outputs.outputs).task_security_group_id.value }}
66 changes: 25 additions & 41 deletions .github/workflows/plan.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,10 @@ on:
default: development
required: true
type: environment
image_tag:
description: (Optional) Image tag to use for the OpenTofu containers. Defaults to latest SHA.
required: false
type: string

permissions:
contents: read
Expand Down Expand Up @@ -95,49 +99,29 @@ jobs:
role-to-assume: ${{ secrets.AWS_ROLE_ARN }}
role-session-name: GitHub_to_AWS_via_FederatedOIDC
- name: Setup OpenTofu
uses: opentofu/setup-opentofu@v1
with:
tofu_wrapper: false
- name: Display OpenTofu version
run: tofu version
- name: Set optional variables
uses: ./.github/actions/setup-opentofu
env:
# For any of these that have a value, the corresponding TF_VAR_*
# environment variable will be set.
APPLY_DATABASE_UPDATES_IMMEDIATELY: ${{ secrets.TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY }}
TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY: ${{ secrets.TF_VAR_APPLY_DATABASE_UPDATES_IMMEDIATELY }}
TF_VAR_CONSUMER_CONTAINER_COUNT: ${{ secrets.TF_VAR_CONSUMER_CONTAINER_COUNT }}
CONSUMER_CPU: ${{ secrets.TF_VAR_CONSUMER_CPU }}
CONSUMER_MEMORY: ${{ secrets.TF_VAR_CONSUMER_MEMORY }}
DATABASE_SKIP_FINAL_SNAPSHOT: ${{ secrets.TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT }}
DELETION_PROTECTION: ${{ secrets.TF_VAR_DELETION_PROTECTION }}
DEPLOYMENT_ENVIRONMENTS: ${{ secrets.TF_VAR_DEPLOYMENT_ENVIRONMENTS }}
ENVIRONMENT: ${{ secrets.TF_VAR_ENVIRONMENT }}
EXPORT_EXPIRATION: ${{ secrets.TF_VAR_EXPORT_EXPIRATION }}
IMAGE_TAGS_MUTABLE: ${{ secrets.TF_VAR_IMAGE_TAGS_MUTABLE }}
KEY_RECOVERY_PERIOD: ${{ secrets.TF_VAR_KEY_RECOVERY_PERIOD }}
PROGRAM: ${{ secrets.TF_VAR_PROGRAM }}
PROJECT: ${{ secrets.TF_VAR_PROJECT }}
REPOSITORY: ${{ secrets.TF_VAR_REPOSITORY }}
run: |
variables=(
"apply_database_updates_immediately" "consumer_container_count"
"consumer_cpu" "consumer_memory" "database_skip_final_snapshot"
"deletion_protection" "deployment_environments" "environment"
"export_expiration" "image_tags_mutable" "key_recovery_period"
"program" "project" "repository"
)
for var in ${variables[@]}; do
name="$(echo $var | tr '[:lower:]' '[:upper:]')"
if [ -n "${!name}" ]; then
echo "Setting TF_VAR_$var"
echo "TF_VAR_$var=${!name}" >> $GITHUB_ENV
else
echo "$name is not set"
fi
done
- name: Initialize OpenTofu
working-directory: ./tofu/config/${{ inputs.config }}
run: tofu init
TF_VAR_CONSUMER_CPU: ${{ secrets.TF_VAR_CONSUMER_CPU }}
TF_VAR_CONSUMER_MEMORY: ${{ secrets.TF_VAR_CONSUMER_MEMORY }}
TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT: ${{ secrets.TF_VAR_DATABASE_SKIP_FINAL_SNAPSHOT }}
TF_VAR_DATABASE_INSTANCE_COUNT: ${{ secrets.TF_VAR_DATABASE_INSTANCE_COUNT }}
TF_VAR_DELETION_PROTECTION: ${{ secrets.TF_VAR_DELETION_PROTECTION }}
TF_VAR_DEPLOYMENT_ENVIRONMENTS: ${{ secrets.TF_VAR_DEPLOYMENT_ENVIRONMENTS }}
TF_VAR_ENVIRONMENT: ${{ inputs.environment }}
TF_VAR_EXPORT_EXPIRATION: ${{ secrets.TF_VAR_EXPORT_EXPIRATION }}
TF_VAR_IMAGE_TAGS_MUTABLE: ${{ secrets.TF_VAR_IMAGE_TAGS_MUTABLE }}
TF_VAR_KEY_RECOVERY_PERIOD: ${{ secrets.TF_VAR_KEY_RECOVERY_PERIOD }}
TF_VAR_PROJECT: ${{ secrets.TF_VAR_PROJECT }}
TF_VAR_PROGRAM: ${{ secrets.TF_VAR_PROGRAM }}
TF_VAR_REPO_OIDC_ARN: ${{ secrets.TF_VAR_REPO_OIDC_ARN }}
TF_VAR_REPOSITORY: ${{ secrets.TF_VAR_REPOSITORY }}
TF_VAR_VPC_CIDR: ${{ secrets.TF_VAR_VPC_CIDR }}
TF_VAR_VPC_PRIVATE_SUBNET_CIDRS: ${{ secrets.TF_VAR_VPC_PRIVATE_SUBNET_CIDRS }}
TF_VAR_VPC_PUBLIC_SUBNET_CIDRS: ${{ secrets.TF_VAR_VPC_PUBLIC_SUBNET_CIDRS }}
with:
config: ${{ inputs.config }}
- name: Plan changes
working-directory: ./tofu/config/${{ inputs.config }}
run: tofu plan -concise -no-color -out tfplan > plan.txt
Expand Down
32 changes: 16 additions & 16 deletions tofu/config/service/.terraform.lock.hcl

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 3 additions & 0 deletions tofu/config/service/locals.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
locals {
image_tag = var.image_tag != null ? var.image_tag : sha256(timestamp())
}
3 changes: 2 additions & 1 deletion tofu/config/service/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,10 @@ module "system" {
container_subnets = split(",", module.inputs.values["vpc/private_subnets"])

apply_database_updates_immediately = var.apply_database_updates_immediately
database_instance_count = var.database_instance_count
database_skip_final_snapshot = var.database_skip_final_snapshot
deletion_protection = var.deletion_protection
image_tag = var.image_tag != null ? var.image_tag : sha256(timestamp())
image_tag = local.image_tag
image_tags_mutable = var.image_tags_mutable

consumer_container_count = var.consumer_container_count
Expand Down
Loading
Loading