Skip to content

Route security findings to dedicated Slack channel#122

Merged
Alexanderamiri merged 1 commit intomainfrom
feat/security-alerts-channel
Apr 14, 2026
Merged

Route security findings to dedicated Slack channel#122
Alexanderamiri merged 1 commit intomainfrom
feat/security-alerts-channel

Conversation

@Alexanderamiri
Copy link
Copy Markdown
Member

Summary

  • Routes Security Hub and GuardDuty findings to new #platform-security-alerts Slack channel (webhook stored in SSM as SecureString)
  • Adds Workflow.Status = NEW filter to EventBridge rule so suppressed findings no longer trigger Lambda invocations on re-import
  • Deduplicates GuardDuty root credential usage alerts (one per hour instead of one per API call)
  • 50 known/accepted findings suppressed directly in Security Hub (S3 public access for website buckets, Elastic Beanstalk legacy apps, default VPC security groups, SSM public sharing) — active count reduced from 80 to 29

Changes

  • handler.py — read new SECURITY_WEBHOOK_PARAM, route security findings to it, hourly dedup for root credential GuardDuty findings
  • lambdas/main.tf — add SECURITY_WEBHOOK_PARAM env var to slack-alert and securityhub-summary Lambdas
  • monitoring/main.tf — add Workflow.Status = ["NEW"] to Security Hub EventBridge rule pattern
  • CLAUDE.md — document new SSM parameter and updated alert routing

Test plan

  • Verify terraform plan shows only expected changes (Lambda env vars + EventBridge rule pattern)
  • After apply, confirm Security Hub findings post to #platform-security-alerts
  • Confirm IAM/resource/login events still post to #javabin-infra-alerts
  • Confirm suppressed findings do not trigger new alerts on next Security Hub re-evaluation cycle

- New SSM param /javabin/slack/platform-security-alerts-webhook
- Lambda routes Security Hub and GuardDuty findings to dedicated channel
- Weekly summary also posts to security channel
- EventBridge rule filters on Workflow.Status=NEW (suppressed findings silent)
- GuardDuty root credential usage deduped per hour (one alert per session)
- 50 known/accepted findings suppressed in Security Hub (80→29 active)
@Alexanderamiri Alexanderamiri requested a review from a team as a code owner April 14, 2026 18:54
@github-actions
Copy link
Copy Markdown

Terraform Plan

🚧 Changes detected — Plan: 0 to add, 3 to change, 0 to destroy.

Plan output
Acquiring state lock. This may take a few moments...

Terraform used the selected providers to generate the following execution
plan. Resource actions are indicated with the following symbols:
  ~ update in-place

Terraform will perform the following actions:

  # module.lambdas.aws_lambda_function.securityhub_summary will be updated in-place
  ~ resource "aws_lambda_function" "securityhub_summary" {
        id                             = "javabin-securityhub-summary"
      ~ last_modified                  = "2026-03-31T10:13:42.000+0000" -> (known after apply)
      ~ source_code_hash               = "Qe3B8I3nLK88y9g2hWSlTCmA2ioOWPS1kp7hSB7/kSg=" -> "0Du88FWS1mMhV3/DDcnnVGTyLcxgRawJyEP9D0B5IGA="
        tags                           = {}
        # (21 unchanged attributes hidden)

      ~ environment {
          ~ variables = {
              + "SECURITY_WEBHOOK_PARAM" = "/javabin/slack/platform-security-alerts-webhook"
                # (7 unchanged elements hidden)
            }
        }

        # (3 unchanged blocks hidden)
    }

  # module.lambdas.aws_lambda_function.slack_alert will be updated in-place
  ~ resource "aws_lambda_function" "slack_alert" {
        id                             = "javabin-slack-alert"
      ~ last_modified                  = "2026-03-31T10:13:36.000+0000" -> (known after apply)
      ~ source_code_hash               = "Qe3B8I3nLK88y9g2hWSlTCmA2ioOWPS1kp7hSB7/kSg=" -> "0Du88FWS1mMhV3/DDcnnVGTyLcxgRawJyEP9D0B5IGA="
        tags                           = {}
        # (21 unchanged attributes hidden)

      ~ environment {
          ~ variables = {
              + "SECURITY_WEBHOOK_PARAM" = "/javabin/slack/platform-security-alerts-webhook"
                # (7 unchanged elements hidden)
            }
        }

        # (3 unchanged blocks hidden)
    }

  # module.monitoring.aws_cloudwatch_event_rule.securityhub_findings will be updated in-place
  ~ resource "aws_cloudwatch_event_rule" "securityhub_findings" {
      ~ event_pattern  = jsonencode(
          ~ {
              ~ detail      = {
                  ~ findings = {
                      + Workflow = {
                          + Status = [
                              + "NEW",
                            ]
                        }
                        # (1 unchanged attribute hidden)
                    }
                }
                # (2 unchanged attributes hidden)
            }
        )
        id             = "javabin-securityhub-findings"
        name           = "javabin-securityhub-findings"
        tags           = {}
        # (7 unchanged attributes hidden)
    }

Plan: 0 to add, 3 to change, 0 to destroy.

─────────────────────────────────────────────────────────────────────────────

Saved the plan to: tfplan

To perform exactly these actions, run the following command to apply:
    terraform apply "tfplan"

LLM Review

Risk: 🟢 LOW

Routine Lambda function updates with new environment variable and EventBridge rule refinement for security monitoring.

  • [routine] Two Lambda functions (securityhub_summary and slack_alert) being updated with new source code hash and environment variable SECURITY_WEBHOOK_PARAM added. These are standard application updates.
  • [routine] EventBridge rule for SecurityHub findings being refined to filter on Workflow Status = NEW. This improves event filtering without changing security posture.
  • [routine] No resources being created or destroyed. All changes are in-place updates to existing Lambda functions and event rules.
  • 🔒 [security] New environment variable SECURITY_WEBHOOK_PARAM references SSM parameter for Slack webhook. Ensure this parameter exists and contains valid webhook URL with appropriate access controls.
  • [routine] Lambda source code hash changes indicate code updates. Verify code changes in version control before applying.

@Alexanderamiri Alexanderamiri merged commit a13fe23 into main Apr 14, 2026
3 checks passed
@Alexanderamiri Alexanderamiri deleted the feat/security-alerts-channel branch April 14, 2026 18:56
Alexanderamiri added a commit that referenced this pull request May 9, 2026
## Summary
- Routes Security Hub and GuardDuty findings to new
`#platform-security-alerts` Slack channel (webhook stored in SSM as
SecureString)
- Adds `Workflow.Status = NEW` filter to EventBridge rule so suppressed
findings no longer trigger Lambda invocations on re-import
- Deduplicates GuardDuty root credential usage alerts (one per hour
instead of one per API call)
- 50 known/accepted findings suppressed directly in Security Hub (S3
public access for website buckets, Elastic Beanstalk legacy apps,
default VPC security groups, SSM public sharing) — active count reduced
from 80 to 29

## Changes
- `handler.py` — read new `SECURITY_WEBHOOK_PARAM`, route security
findings to it, hourly dedup for root credential GuardDuty findings
- `lambdas/main.tf` — add `SECURITY_WEBHOOK_PARAM` env var to
`slack-alert` and `securityhub-summary` Lambdas
- `monitoring/main.tf` — add `Workflow.Status = ["NEW"]` to Security Hub
EventBridge rule pattern
- `CLAUDE.md` — document new SSM parameter and updated alert routing

## Test plan
- [ ] Verify `terraform plan` shows only expected changes (Lambda env
vars + EventBridge rule pattern)
- [ ] After apply, confirm Security Hub findings post to
`#platform-security-alerts`
- [ ] Confirm IAM/resource/login events still post to
`#javabin-infra-alerts`
- [ ] Confirm suppressed findings do not trigger new alerts on next
Security Hub re-evaluation cycle
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant