From 08c584b2dd1e0aef65c85f74fcb83ce75d4e937d Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 03:39:24 -0700 Subject: [PATCH 01/13] yaml changes --- .github/workflows/deploy.yml | 2 -- 1 file changed, 2 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 1aca6c1..9621ae6 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -66,8 +66,6 @@ jobs: env: IMAGE_URI: ${{ needs.build.outputs.image_uri }} run: | - set -euo pipefail - echo "Deploying image ${IMAGE_URI} to instance" test -n "${IMAGE_URI}" From beb3693db9e7d5eba26e42e155703257aec307b2 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 03:43:15 -0700 Subject: [PATCH 02/13] yaml changes --- .github/workflows/deploy.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 9621ae6..10cb13b 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -19,7 +19,7 @@ jobs: contents: read outputs: - image_uri: ${{ steps.build.outputs.image_uri }} + IMAGE_URI: ${{ steps.build.outputs.IMAGE_URI }} steps: - name: Checkout @@ -64,7 +64,7 @@ jobs: - name: Deploy to EC2 via SSM env: - IMAGE_URI: ${{ needs.build.outputs.image_uri }} + IMAGE_URI: ${{ needs.build.outputs.IMAGE_URI }} run: | echo "Deploying image ${IMAGE_URI} to instance" test -n "${IMAGE_URI}" From 04b66342fcff5cc4a3099d6213b39f92c4a06d9a Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 03:46:40 -0700 Subject: [PATCH 03/13] added debugging statement to deploy.yaml --- .github/workflows/deploy.yml | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 10cb13b..3c4222f 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -106,6 +106,18 @@ jobs: --query 'Command.CommandId' \ --output text) + aws ssm get-command-invocation \ + --region "${AWS_REGION}" \ + --command-id "${COMMAND_ID}" \ + --instance-id "${EC2_INSTANCE_ID}" \ + --query '{ + Status: Status, + ExitCode: ResponseCode, + Stdout: StandardOutputContent, + Stderr: StandardErrorContent + }' \ + --output json + sleep 2 aws ssm get-command-invocation \ --region "${AWS_REGION}" \ From eb08c372574177bb3ea5b77e554d49162ec15a6b Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 03:53:21 -0700 Subject: [PATCH 04/13] yaml changes --- .github/workflows/deploy.yml | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 3c4222f..2935ee8 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -45,7 +45,10 @@ jobs: docker build -f Dockerfile.prod -t "${IMAGE_URI}" . docker push "${IMAGE_URI}" - echo "IMAGE_URI=${IMAGE_URI}" >> $GITHUB_OUTPUT + echo "IMAGE_URI=${IMAGE_URI}" >> "$GITHUB_OUTPUT" + + - name: Print build output + run: echo "build produced image_uri='${{ steps.build.outputs.image_uri }}'" deploy: runs-on: ubuntu-latest @@ -102,7 +105,7 @@ jobs: "# Smoke check", "sleep 2", "curl -fsS http://localhost:8080/health" - ]"" \ + ]" \ --query 'Command.CommandId' \ --output text) From a1dcb8a0d9b7532dd876a26fb2008c8617393232 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 03:59:26 -0700 Subject: [PATCH 05/13] yml changes --- .github/workflows/deploy.yml | 70 ++++++++++-------------------- infra/env/prod/.terraform.lock.hcl | 55 ++++++++++++++++++----- 2 files changed, 68 insertions(+), 57 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 2935ee8..b117e2f 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -48,7 +48,7 @@ jobs: echo "IMAGE_URI=${IMAGE_URI}" >> "$GITHUB_OUTPUT" - name: Print build output - run: echo "build produced image_uri='${{ steps.build.outputs.image_uri }}'" + run: echo "build produced IMAGE_URI='${{ steps.build.outputs.IMAGE_URI }}'" deploy: runs-on: ubuntu-latest @@ -69,43 +69,34 @@ jobs: env: IMAGE_URI: ${{ needs.build.outputs.IMAGE_URI }} run: | + set -euo pipefail echo "Deploying image ${IMAGE_URI} to instance" test -n "${IMAGE_URI}" + COMMANDS=$(cat </dev/null 2>&1; then sudo dnf -y install docker; sudo systemctl enable --now docker; fi", + "sudo usermod -aG docker ec2-user || true", + "ECR_REGISTRY=\${IMAGE_URI%%/*}", + "aws ecr get-login-password --region $AWS_REGION | sudo docker login --username AWS --password-stdin \$ECR_REGISTRY", + "DBURL=\$(aws ssm get-parameter --region $AWS_REGION --with-decryption --name /cgc-2026-prod/api/database_url --query Parameter.Value --output text)", + "CLERK_SECRET=\$(aws ssm get-parameter --region $AWS_REGION --with-decryption --name /cgc-2026-prod/api/clerk_secret_key --query Parameter.Value --output text)", + "sudo docker pull $IMAGE_URI", + "sudo docker rm -f $CONTAINER_NAME || true", + "sudo docker run -d --restart unless-stopped --name $CONTAINER_NAME -p 8080:8080 -e PORT=8080 -e DATABASE_URL=\"\$DBURL\" -e CLERK_SECRET_KEY=\"\$CLERK_SECRET\" $IMAGE_URI", + "sleep 2", + "curl -fsS http://localhost:8080/health" + ] + JSON + ) + COMMAND_ID=$(aws ssm send-command \ --region "${AWS_REGION}" \ --instance-ids "${EC2_INSTANCE_ID}" \ --document-name "AWS-RunShellScript" \ - --parameters commands="[ - "set -e", - "AWS_REGION='${AWS_REGION}'", - "IMAGE_URI='${IMAGE_URI}'", - "CONTAINER_NAME='${CONTAINER_NAME}'", - "", - "if ! command -v docker >/dev/null 2>&1; then sudo dnf -y install docker; sudo systemctl enable --now docker; fi", - "", - "sudo usermod -aG docker ec2-user || true", - "", - "# Login to ECR", - "aws ecr get-login-password --region ${AWS_REGION} | sudo docker login --username AWS --password-stdin $(echo ${IMAGE_URI} | cut -d/ -f1)", - "", - "# Fetch runtime secrets from SSM", - "DBURL=$(aws ssm get-parameter --region ${AWS_REGION} --with-decryption --name /cgc-2026-prod/api/database_url --query Parameter.Value --output text)", - "CLERK_SECRET=$(aws ssm get-parameter --region ${AWS_REGION} --with-decryption --name /cgc-2026-prod/api/clerk_secret_key --query Parameter.Value --output text)", - "", - "# Pull new image", - "", - "sudo docker pull ${IMAGE_URI}", - "# Stop existing container (if any)", - "sudo docker rm -f ${CONTAINER_NAME} || true", - "", - "# Run container", - "sudo docker run -d --restart unless-stopped --name \"${CONTAINER_NAME}\" -p 8080:8080 -e PORT=8080 -e DATABASE_URL=\"${DBURL}\" -e CLERK_SECRET_KEY=\"${CLERK_SECRET}\" \"${IMAGE_URI}\"", - "", - "# Smoke check", - "sleep 2", - "curl -fsS http://localhost:8080/health" - ]" \ + --parameters "commands=${COMMANDS}" \ --query 'Command.CommandId' \ --output text) @@ -113,18 +104,5 @@ jobs: --region "${AWS_REGION}" \ --command-id "${COMMAND_ID}" \ --instance-id "${EC2_INSTANCE_ID}" \ - --query '{ - Status: Status, - ExitCode: ResponseCode, - Stdout: StandardOutputContent, - Stderr: StandardErrorContent - }' \ - --output json - - sleep 2 - aws ssm get-command-invocation \ - --region "${AWS_REGION}" \ - --command-id "${COMMAND_ID}" \ - --instance-id "${EC2_INSTANCE_ID}" \ - --query 'StandardErrorContent' \ - --output text \ No newline at end of file + --query '{Status:Status,ExitCode:ResponseCode,Stdout:StandardOutputContent,Stderr:StandardErrorContent}' \ + --output json \ No newline at end of file diff --git a/infra/env/prod/.terraform.lock.hcl b/infra/env/prod/.terraform.lock.hcl index b98b2f2..79adc07 100644 --- a/infra/env/prod/.terraform.lock.hcl +++ b/infra/env/prod/.terraform.lock.hcl @@ -19,19 +19,52 @@ provider "registry.opentofu.org/hashicorp/aws" { ] } +provider "registry.opentofu.org/hashicorp/local" { + version = "2.6.1" + hashes = [ + "h1:Dd5MP04TnE9qaFD8BQkJYkluiJCOsL7fwUTJx26KIP0=", + "zh:0416d7bf0b459a995cf48f202af7b7ffa252def7d23386fc05b34f67347a22ba", + "zh:24743d559026b59610eb3d9fa9ec7fbeb06399c0ef01272e46fe5c313eb5c6ff", + "zh:2561cdfbc90090fee7f844a5cb5cbed8472ce264f5d505acb18326650a5b563f", + "zh:3ebc3f2dc7a099bd83e5c4c2b6918e5b56ec746766c58a31a3f5d189cb837db5", + "zh:490e0ce925fc3848027e10017f960e9e19e7f9c3b620524f67ce54217d1c6390", + "zh:bf08934295877f831f2e5f17a0b3ebb51dd608b2509077f7b22afa7722e28950", + "zh:c298c0f72e1485588a73768cb90163863b6c3d4c71982908c219e9b87904f376", + "zh:cedbaed4967818903ef378675211ed541c8243c4597304161363e828c7dc3d36", + "zh:edda76726d7874128cf1e182640c332c5a5e6a66a053c0aa97e2a0e4267b3b92", + ] +} + provider "registry.opentofu.org/hashicorp/random" { - version = "3.8.0" + version = "3.8.1" constraints = "~> 3.6" hashes = [ - "h1:nRPdhXsZpGPMppuUgBe/ZcAtD73NaCLGROYHXv41qz8=", - "zh:2d5e0bbfac7f15595739fe54a9ab8b8eea92fd6d879706139dad7ecaa5c01c19", - "zh:349e637066625d97aaa84db1b1418c86d6457cf9c5a62f6dcc3f55cbd535112c", - "zh:5f4456d53f5256ccfdb87dd35d3bf34578d01bd9b71cffaf507f0692805eac8a", - "zh:6c1ecfacc5f7079a068d7f8eb8924485d4ec8183f36e6318a6e748d35921ddac", - "zh:6d86641edeb8c394f121f7b0a691d72f89cf9b938b987a01fc32aad396a50555", - "zh:76947bd7bc7033b33980538da149c94e386f9b0abb2ce63733f25a57517e4742", - "zh:79c07f4c8b3a63d9f89e25e4348b462c57e179bca66ba533710851c485e282db", - "zh:ac1c2b941d994728a3a93aba093fd2202f9311d099ff85f66678897c792161ba", - "zh:cbb2aa867fd828fcb4125239e00862b9a3bc2f280e945c760224276b476f4c49", + "h1:K/OIbLGX0YNiuoDXlpkerSWyv+bjS97Z6YGUCGePPAw=", + "zh:25c458c7c676f15705e872202dad7dcd0982e4a48e7ea1800afa5fc64e77f4c8", + "zh:2edeaf6f1b20435b2f81855ad98a2e70956d473be9e52a5fdf57ccd0098ba476", + "zh:44becb9d5f75d55e36dfed0c5beabaf4c92e0a2bc61a3814d698271c646d48e7", + "zh:7699032612c3b16cc69928add8973de47b10ce81b1141f30644a0e8a895b5cd3", + "zh:86d07aa98d17703de9fbf402c89590dc1e01dbe5671dd6bc5e487eb8fe87eee0", + "zh:8c411c77b8390a49a8a1bc9f176529e6b32369dd33a723606c8533e5ca4d68c1", + "zh:a5ecc8255a612652a56b28149994985e2c4dc046e5d34d416d47fa7767f5c28f", + "zh:aea3fe1a5669b932eda9c5c72e5f327db8da707fe514aaca0d0ef60cb24892f9", + "zh:f56e26e6977f755d7ae56fa6320af96ecf4bb09580d47cb481efbf27f1c5afff", + ] +} + +provider "registry.opentofu.org/hashicorp/tls" { + version = "4.1.0" + hashes = [ + "h1:RBhHxjVu41XdAnM4WxxGTz2nYaccHNLalqx4031L8rE=", + "zh:187a99f0d236fd92da224e2f026c4ca8f1dcbf2b5cddc8e6896801bacfab0d73", + "zh:61a32a01cc46f382014dcf7aff5bcac61fe97bd69d3ccb51c801e9437ecdb9ce", + "zh:683ba18baa2cc336ff83f061b5e4569e2cd7c4a097b53a2d80bb0a26be2fc59a", + "zh:85c7640ea13dcf5ae5f7f3abbf2f21e4b93ce7f333ffee5b4a6acd6b5fe71223", + "zh:882f2c5214fd6d280a500acfd560925a71030ef70e10d11fa2b94815b58ae9b6", + "zh:97cb5e0b81b8687870a6b8a16e9a9cfe546e2fdb7534bdd8302eda0d66393f78", + "zh:c0a0110b15ce45140036fe5bf5a44cb822c2f55b30ff2770faf37d7c3cae3b5e", + "zh:d98c1c63fd0c76704fd7be38c316c305a2c95f3215330f2fb1e6b0b7081bf8e9", + "zh:e703a7adf220ac436f8ebfd06529de865b965fcfc461c7ef7b71afa0de04c8e9", + "zh:e93e241150cd438a0708679cb4aa7976742fde02f4c1725cfdefc405c4eeca1a", ] } From 449d1b55db41001a2922ed377dab298dbac22d69 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:03:54 -0700 Subject: [PATCH 06/13] deploy.yml changes --- .github/workflows/deploy.yml | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index b117e2f..2f52698 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -18,9 +18,6 @@ jobs: id-token: write contents: read - outputs: - IMAGE_URI: ${{ steps.build.outputs.IMAGE_URI }} - steps: - name: Checkout uses: actions/checkout@v4 @@ -35,7 +32,6 @@ jobs: uses: aws-actions/amazon-ecr-login@v2 - name: Build & push image - id: build env: IMAGE_TAG: ${{ github.sha }} run: | @@ -45,8 +41,6 @@ jobs: docker build -f Dockerfile.prod -t "${IMAGE_URI}" . docker push "${IMAGE_URI}" - echo "IMAGE_URI=${IMAGE_URI}" >> "$GITHUB_OUTPUT" - - name: Print build output run: echo "build produced IMAGE_URI='${{ steps.build.outputs.IMAGE_URI }}'" @@ -65,9 +59,15 @@ jobs: role-to-assume: ${{ secrets.AWS_DEPLOY_ROLE_ARN }} aws-region: ${{ env.AWS_REGION }} + - name: Compute IMAGE_URI + run: | + set -euo pipefail + ECR_REGISTRY="$(aws sts get-caller-identity --query Account --output text).dkr.ecr.${AWS_REGION}.amazonaws.com" + IMAGE_URI="${ECR_REGISTRY}/${ECR_REPO}:${GITHUB_SHA}" + echo "IMAGE_URI=${IMAGE_URI}" >> "$GITHUB_ENV" + echo "Computed IMAGE_URI=${IMAGE_URI}" + - name: Deploy to EC2 via SSM - env: - IMAGE_URI: ${{ needs.build.outputs.IMAGE_URI }} run: | set -euo pipefail echo "Deploying image ${IMAGE_URI} to instance" From 6c8880965397d13211797a375bcfefd6a44075b6 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:10:08 -0700 Subject: [PATCH 07/13] yml changes --- .github/workflows/deploy.yml | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 2f52698..c26fe7f 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -59,17 +59,12 @@ jobs: role-to-assume: ${{ secrets.AWS_DEPLOY_ROLE_ARN }} aws-region: ${{ env.AWS_REGION }} - - name: Compute IMAGE_URI + - name: Deploy to EC2 via SSM run: | set -euo pipefail + ECR_REGISTRY="$(aws sts get-caller-identity --query Account --output text).dkr.ecr.${AWS_REGION}.amazonaws.com" IMAGE_URI="${ECR_REGISTRY}/${ECR_REPO}:${GITHUB_SHA}" - echo "IMAGE_URI=${IMAGE_URI}" >> "$GITHUB_ENV" - echo "Computed IMAGE_URI=${IMAGE_URI}" - - - name: Deploy to EC2 via SSM - run: | - set -euo pipefail echo "Deploying image ${IMAGE_URI} to instance" test -n "${IMAGE_URI}" From 29220a1272dfeb4289e7b4a447f05482799c8109 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:15:00 -0700 Subject: [PATCH 08/13] yml changes --- .github/workflows/deploy.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index c26fe7f..3e83590 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -71,6 +71,9 @@ jobs: COMMANDS=$(cat </dev/null 2>&1; then sudo dnf -y install docker; sudo systemctl enable --now docker; fi", "sudo usermod -aG docker ec2-user || true", From 2c55645ff295b4b63ba998511224089d4bdea08b Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:20:01 -0700 Subject: [PATCH 09/13] yml changes --- .github/workflows/deploy.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 3e83590..6af02fb 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -73,7 +73,7 @@ jobs: "set -euo pipefail", "AWS_REGION=${AWS_REGION}", "IMAGE_URI=${IMAGE_URI}", - "CONTAINER_NAME=${CONTAINER_NAME} + "CONTAINER_NAME=${CONTAINER_NAME}", "echo IMAGE_URI=$IMAGE_URI", "if ! command -v docker >/dev/null 2>&1; then sudo dnf -y install docker; sudo systemctl enable --now docker; fi", "sudo usermod -aG docker ec2-user || true", From dd3edae7bc08c4c9950af7e0ae5a3c539854d4ee Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:35:28 -0700 Subject: [PATCH 10/13] yml changes --- .github/workflows/deploy.yml | 72 +++++++++++++++++++++++++++++++++--- 1 file changed, 67 insertions(+), 5 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 6af02fb..fc29f35 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -98,9 +98,71 @@ jobs: --query 'Command.CommandId' \ --output text) - aws ssm get-command-invocation \ + - name: Wait for SSM command to finish + run: | + set -euo pipefail + + COMMAND_ID='${{ steps.ssm_send.outputs.command_id }}' + echo "Waiting on SSM CommandId: ${COMMAND_ID}" + + for i in {1..80}; do + STATUS=$(aws ssm get-command-invocation \ + --region "${AWS_REGION}" \ + --command-id "${COMMAND_ID}" \ + --instance-id "${EC2_INSTANCE_ID}" \ + --query 'Status' \ + --output text) + + echo "SSM status: ${STATUS}" + + case "$STATUS" in + Pending|InProgress|Delayed) + sleep 3 + ;; + Success) + aws ssm get-command-invocation \ + --region "${AWS_REGION}" \ + --command-id "${COMMAND_ID}" \ + --instance-id "${EC2_INSTANCE_ID}" \ + --query '{Status:Status,ExitCode:ResponseCode,Stdout:StandardOutputContent,Stderr:StandardErrorContent}' \ + --output json + exit 0 + ;; + *) + aws ssm get-command-invocation \ + --region "${AWS_REGION}" \ + --command-id "${COMMAND_ID}" \ + --instance-id "${EC2_INSTANCE_ID}" \ + --query '{Status:Status,ExitCode:ResponseCode,Stdout:StandardOutputContent,Stderr:StandardErrorContent}' \ + --output json + echo "SSM command failed with status: ${STATUS}" >&2 + exit 1 + ;; + esac + done + + echo "SSM command did not finish in time" >&2 + exit 1 + + - name: Verify health + run: | + set -euo pipefail + + PUBLIC_IP=$(aws ec2 describe-instances \ --region "${AWS_REGION}" \ - --command-id "${COMMAND_ID}" \ - --instance-id "${EC2_INSTANCE_ID}" \ - --query '{Status:Status,ExitCode:ResponseCode,Stdout:StandardOutputContent,Stderr:StandardErrorContent}' \ - --output json \ No newline at end of file + --instance-ids "${EC2_INSTANCE_ID}" \ + --query 'Reservations[0].Instances[0].PublicIpAddress' \ + --output text) + + test "${PUBLIC_IP}" != "None" + + for i in {1..20}; do + if curl -fsS "${URL}" >/dev/null; then + echo "Health check passed" + exit 0 + fi + echo "Health not ready yet (attempt $i/20) — retrying..." + sleep 3 + done + + echo "Health check failed" \ No newline at end of file From dc98e6f437970310b3d6d039d097748447085fd8 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:37:59 -0700 Subject: [PATCH 11/13] yml changes --- .github/workflows/deploy.yml | 46 ------------------------------------ 1 file changed, 46 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index fc29f35..5984952 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -98,52 +98,6 @@ jobs: --query 'Command.CommandId' \ --output text) - - name: Wait for SSM command to finish - run: | - set -euo pipefail - - COMMAND_ID='${{ steps.ssm_send.outputs.command_id }}' - echo "Waiting on SSM CommandId: ${COMMAND_ID}" - - for i in {1..80}; do - STATUS=$(aws ssm get-command-invocation \ - --region "${AWS_REGION}" \ - --command-id "${COMMAND_ID}" \ - --instance-id "${EC2_INSTANCE_ID}" \ - --query 'Status' \ - --output text) - - echo "SSM status: ${STATUS}" - - case "$STATUS" in - Pending|InProgress|Delayed) - sleep 3 - ;; - Success) - aws ssm get-command-invocation \ - --region "${AWS_REGION}" \ - --command-id "${COMMAND_ID}" \ - --instance-id "${EC2_INSTANCE_ID}" \ - --query '{Status:Status,ExitCode:ResponseCode,Stdout:StandardOutputContent,Stderr:StandardErrorContent}' \ - --output json - exit 0 - ;; - *) - aws ssm get-command-invocation \ - --region "${AWS_REGION}" \ - --command-id "${COMMAND_ID}" \ - --instance-id "${EC2_INSTANCE_ID}" \ - --query '{Status:Status,ExitCode:ResponseCode,Stdout:StandardOutputContent,Stderr:StandardErrorContent}' \ - --output json - echo "SSM command failed with status: ${STATUS}" >&2 - exit 1 - ;; - esac - done - - echo "SSM command did not finish in time" >&2 - exit 1 - - name: Verify health run: | set -euo pipefail From ec24cbff033fa67fc329dd450ef55add3cfa11b7 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 04:40:52 -0700 Subject: [PATCH 12/13] yml changes --- .github/workflows/deploy.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 5984952..d63dcab 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -41,9 +41,6 @@ jobs: docker build -f Dockerfile.prod -t "${IMAGE_URI}" . docker push "${IMAGE_URI}" - - name: Print build output - run: echo "build produced IMAGE_URI='${{ steps.build.outputs.IMAGE_URI }}'" - deploy: runs-on: ubuntu-latest needs: build @@ -110,6 +107,9 @@ jobs: test "${PUBLIC_IP}" != "None" + URL="http://${PUBLIC_IP}:8080/health" + echo "Checking ${URL}" + for i in {1..20}; do if curl -fsS "${URL}" >/dev/null; then echo "Health check passed" From 2e75de5c4b35d60ae899cd53fdd976c5a475a8f7 Mon Sep 17 00:00:00 2001 From: NicolaSavino Date: Fri, 30 Jan 2026 18:57:52 -0700 Subject: [PATCH 13/13] yml changes --- .github/workflows/deploy.yml | 34 +++++++++++++++++++++++++++++++++- 1 file changed, 33 insertions(+), 1 deletion(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index d63dcab..a5a6fbf 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -95,6 +95,37 @@ jobs: --query 'Command.CommandId' \ --output text) + echo "Waiting for SSM command ${COMMAND_ID} to complete..." + for i in {1..60}; do + STATUS=$(aws ssm get-command-invocation \ + --region "${AWS_REGION}" \ + --command-id "${COMMAND_ID}" \ + --instance-id "${EC2_INSTANCE_ID}" \ + --query 'Status' \ + --output text 2>/dev/null || echo "Pending") + + case "${STATUS}" in + Success) + echo "SSM command succeeded" + break + ;; + Failed|Cancelled|TimedOut) + echo "SSM command failed with status: ${STATUS}" + aws ssm get-command-invocation \ + --region "${AWS_REGION}" \ + --command-id "${COMMAND_ID}" \ + --instance-id "${EC2_INSTANCE_ID}" \ + --query 'StandardErrorContent' \ + --output text + exit 1 + ;; + *) + echo "Status: ${STATUS} (attempt $i/60)" + sleep 5 + ;; + esac + done + - name: Verify health run: | set -euo pipefail @@ -119,4 +150,5 @@ jobs: sleep 3 done - echo "Health check failed" \ No newline at end of file + echo "Health check failed" + exit 1 \ No newline at end of file