From 1c66495f7ec7cc85e723c68c5d2d3bf7297ea6ba Mon Sep 17 00:00:00 2001 From: Alexander Amiri Date: Sat, 14 Mar 2026 00:15:08 +0100 Subject: [PATCH 1/2] Fix EventBridge rules: use prefix matching instead of hardcoded event names CloudTrail event names include version suffixes (e.g. CreateFunction20150331, DeleteFunction20150331) which didn't match the hardcoded names. Using prefix matching (Create*, Delete*, Modify*, etc.) scoped by source service catches all variants without maintaining explicit lists. Fixes missing Slack alerts for Lambda creation/deletion and other resources. --- terraform/platform/lambdas/main.tf | 6 ++---- terraform/platform/monitoring/main.tf | 23 ++++++++++++----------- 2 files changed, 14 insertions(+), 15 deletions(-) diff --git a/terraform/platform/lambdas/main.tf b/terraform/platform/lambdas/main.tf index 8354e39..1e1e86a 100644 --- a/terraform/platform/lambdas/main.tf +++ b/terraform/platform/lambdas/main.tf @@ -854,10 +854,8 @@ resource "aws_cloudwatch_event_rule" "compliance_reporter_trigger" { detail-type = ["AWS API Call via CloudTrail"] detail = { eventName = [ - "CreateBucket", "RunInstances", "CreateDBInstance", - "CreateService", "CreateFunction20150331", "CreateLoadBalancer", - "CreateSecurityGroup", "CreateNatGateway", "CreateVpc", "CreateSubnet", - "CreateTargetGroup", + { "prefix" : "Create" }, + { "prefix" : "Run" }, ] } }) diff --git a/terraform/platform/monitoring/main.tf b/terraform/platform/monitoring/main.tf index c5f461a..e041895 100644 --- a/terraform/platform/monitoring/main.tf +++ b/terraform/platform/monitoring/main.tf @@ -88,10 +88,11 @@ resource "aws_cloudwatch_event_rule" "iam_changes" { detail = { eventSource = ["iam.amazonaws.com"] eventName = [ - "CreateRole", "DeleteRole", - "PutRolePolicy", "AttachRolePolicy", - "DetachRolePolicy", "DeleteRolePolicy", - "CreatePolicy", "DeletePolicy", + { "prefix" : "Create" }, + { "prefix" : "Delete" }, + { "prefix" : "Put" }, + { "prefix" : "Attach" }, + { "prefix" : "Detach" }, ] } }) @@ -166,9 +167,8 @@ resource "aws_cloudwatch_event_rule" "resource_creation" { detail-type = ["AWS API Call via CloudTrail"] detail = { eventName = [ - "CreateBucket", "RunInstances", "CreateDBInstance", - "CreateService", "CreateFunction", "CreateQueue", - "CreateTable", "CreateLoadBalancer", + { "prefix" : "Create" }, + { "prefix" : "Run" }, ] } }) @@ -196,10 +196,11 @@ resource "aws_cloudwatch_event_rule" "resource_modification" { detail-type = ["AWS API Call via CloudTrail"] detail = { eventName = [ - "ModifyDBInstance", - "DeleteBucket", - "StopInstances", "TerminateInstances", - "DeleteService", "DeleteFunction", + { "prefix" : "Modify" }, + { "prefix" : "Update" }, + { "prefix" : "Delete" }, + { "prefix" : "Stop" }, + { "prefix" : "Terminate" }, ] } }) From 8573f8346480fa5b83d348d7238b26f81e97ede4 Mon Sep 17 00:00:00 2001 From: Alexander Amiri Date: Sat, 14 Mar 2026 01:00:31 +0100 Subject: [PATCH 2/2] Remove actor-based override gating, improve override UX - Remove override_approvers variable and actor condition from ci-override-approver trust policy. Access control is handled by GitHub (repo permissions + CODEOWNERS + environment protection rules), not by AWS IAM username matching. - Move job_workflow_ref to StringLike (consistent with other conditions) - HIGH risk Slack alert now includes a ready-to-copy gh CLI command with all override parameters pre-filled (plan_key, repo, run_id) --- scripts/notify-high-risk.sh | 10 +++++++--- terraform/platform/iam/main.tf | 14 ++++++-------- terraform/platform/iam/variables.tf | 6 ------ terraform/platform/main.tf | 1 - terraform/platform/variables.tf | 8 -------- 5 files changed, 13 insertions(+), 26 deletions(-) diff --git a/scripts/notify-high-risk.sh b/scripts/notify-high-risk.sh index f7faefc..ab33e38 100644 --- a/scripts/notify-high-risk.sh +++ b/scripts/notify-high-risk.sh @@ -48,6 +48,7 @@ REPO="${GITHUB_REPOSITORY:-unknown}" SHA=$(echo "${GITHUB_SHA:-unknown}" | cut -c1-8) ACTOR="${GITHUB_ACTOR:-unknown}" RUN_ID="${GITHUB_RUN_ID:-}" +PLAN_KEY="plans/${REPO}/${RUN_ID}/tfplan" # Build source line if [ -n "$RUN_ID" ] && [ "$REPO" != "unknown" ]; then @@ -57,16 +58,18 @@ else fi # Build the Block Kit payload -# Note: findings section only included if there are findings FINDINGS_BLOCK="" if [ -n "$FINDINGS_TEXT" ]; then - # Escape for JSON ESCAPED_FINDINGS=$(echo "$FINDINGS_TEXT" | python3 -c "import sys,json; print(json.dumps(sys.stdin.read())[1:-1])") FINDINGS_BLOCK=",{\"type\":\"section\",\"text\":{\"type\":\"mrkdwn\",\"text\":\"*Findings*\n${ESCAPED_FINDINGS}\"}}" fi +# Build override command — user can copy-paste this to approve +OVERRIDE_CMD="gh workflow run approve-override.yml --repo ${REPO} -f plan_key=${PLAN_KEY} -f repo=${REPO} -f run_id=${RUN_ID} -f reason=\\\"Override approved\\\"" + ESCAPED_SUMMARY=$(echo "$SUMMARY" | python3 -c "import sys,json; print(json.dumps(sys.stdin.read().strip())[1:-1])") ESCAPED_SOURCE=$(echo "$SOURCE_LINE" | python3 -c "import sys,json; print(json.dumps(sys.stdin.read().strip())[1:-1])") +ESCAPED_CMD=$(echo "$OVERRIDE_CMD" | python3 -c "import sys,json; print(json.dumps(sys.stdin.read().strip())[1:-1])") PAYLOAD=$(cat <