Amazon GuardDuty에서 심각도에 따라 SNS 알림 자동화하기

Amazon GuardDuty에서 심각도에 따라 SNS 알림 자동화하기

Amazon GuardDuty에서 심각도에 따라 SNS 알림을 자동화하는 방법에 대해서 정리해 봤습니다.
Clock Icon2025.04.17

안녕하세요 클래스메소드 김재욱(Kim Jaewook) 입니다. 이번에는 Amazon GuardDuty에서 심각도에 따라 SNS 알림을 자동화하는 방법에 대해서 정리해 봤습니다.

통지 받을 이메일(SNS) 준비

먼저 사전 준비로는 SNS 알림을 설정할 필요가 있습니다. 이 SNS 알림의 경우 Amazon GuardDuty의 경보를 받을 이메일을 의미합니다.

SNS 설정에 대해서는 아래 블로그를 참고해 주세요.

https://dev.classmethod.jp/articles/get-ec2-instance-cpu-utilization-in-slack/#toc-sns-

Lambda 함수 생성 및 코드 작성

먼저 Lamda 함수를 생성하기에 앞서 IAM 역할을 생성해야 합니다.

이번에 생성할 IAM 역할의 경우 Lamda에서 SNS를 통해 이메일을 통지하기 때문에 Lambda에서 SNS를 제어할 권한이 필요합니다.

먼저 IAM 정책을 생성합니다. Resource에는 SNS의 Arn을 입력합시다.

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "AllowSNSPublish",
            "Effect": "Allow",
            "Action": "sns:Publish",
            "Resource": "arn:aws:sns:ap-northeast-1:xxxxxxx:test-sns"
        }
    ]
}

마지막으로 IAM 역할에는 조금 전 생성한 정책을 추가하기만 하면 됩니다.

jw-blgguardtest-1

이제 Lambda 함수를 생성합시다.

Lambda 함수의 런타임은 [Python 3.13]으로, 역할은 조금 전 생성한 IAM 역할을 선택합니다.

jw-blgguardtest-2

Lambda 함수 생성이 끝났다면, 코드를 작성합시다. 코드는 3단계의 경보 [LOW], [MEDIUM], [HIGH]로 나누어서 통지를 실시하며, 알아보기 쉽게 유형, 심각도, 리소스, 설명을 덧붙여서 통지합니다.

import json
import boto3

sns = boto3.client('sns')
TOPIC_ARN = "arn:aws:sns:ap-northeast-1:xxxxxxxx:test-sns"  # 여기에 SNS ARN 입력

def lambda_handler(event, context):
    detail = event.get("detail", {})

    finding_type = detail.get("type", "N/A")
    severity = detail.get("severity", 0)
    description = detail.get("description", "N/A")
    instance_id = detail.get("resource", {}).get("instanceDetails", {}).get("instanceId", "N/A")

    if severity >= 7:
        severity_label = "HIGH"
    elif severity >= 4:
        severity_label = "MEDIUM"
    else:
        severity_label = "LOW"

    message = f"""🚨 GuardDuty 알림
유형: {finding_type}
심각도: {severity_label} ({severity})
리소스: {instance_id}
설명: {description}
"""

    sns.publish(
        TopicArn=TOPIC_ARN,
        Subject="GuardDuty Alert",
        Message=message
    )

    return {
        "statusCode": 200,
        "body": "SNS sent"
    }

Amazon GuardDuty의 심각도는 1.0~10.0으로 나누어져 있으며, 수치에 따라 [LOW], [MEDIUM], [HIGH]이 결정됩니다.

자세한 내용은 아래 AWS 공식 문서를 확인해 주세요.

https://docs.aws.amazon.com/ko_kr/guardduty/latest/ug/guardduty_findings-severity.html

EventBridge 설정

이제 Lambda 코드 작성이 끝났다면, EventBridge를 통해 GuardDuty에서 이벤트가 발생했을 시 Lambda 함수를 실행시켜 통지를 날리도록 설정합시다.

EventBridge에서 규칙을 생성하는데, 규칙은 GuardDuty에서 검출결과가 나왔을 시 이벤트가 발생한다는 조건입니다.

{
  "source": ["aws.guardduty"],
  "detail-type": ["GuardDuty Finding"]
}

[GuardDuty Finding] 즉 결과 유형에 대한 보다 상세한 내용은 AWS 공식 문서를 확인해 주세요.

https://docs.aws.amazon.com/ko_kr/guardduty/latest/ug/guardduty_finding-types-active.html

이제 마지막으로 이벤트가 발생했을 시 실행시킬 대상을 선택합니다. 대상은 조금 전 생성한 Lambda 함수입니다.

jw-blgguardtest-3

테스트

이제 제대로 통지가 날아오는지 테스트를 실시해 봅시다.

Amazon GuardDuty에서는 심각도 테스트를 위해 샘플 결과 유형을 제공합니다.

[설정]→[샘플 결과 작성]을 통해서 샘플 결과를 만들어낼 수 있습니다.

jw-blgguardtest-4

샘플 결과 작성을 클릭했다면, 결과 화면에서 다양한 낮음, 중간 높음 등 다양한 결과가 검출된 것을 확인할 수 있습니다.

jw-blgguardtest-5

이제 이메일을 확인해 보면, 성공적으로 GuardDuty 심각도에 따른 통지가 도착한 것을 확인할 수 있습니다.
※ 샘플의 경우 많은 결과가 검출되기 때문에 통지 또한 제법 많은 양의 이메일이 도착합니다.

jw-blgguardtest-6

본 블로그 게시글을 읽고 궁금한 사항이 있으신 분들은 jaewookkim533@yahoo.com로 보내주시면 감사하겠습니다.

Share this article

facebook logohatena logotwitter logo

© Classmethod, Inc. All rights reserved.