暗号化されていないSNSトピックの暗号化設定手順

このブログシリーズ 「クラウドセキュリティ 実践集」 では、一般的なセキュリティ課題を取り上げ、「なぜ危険なのか?」 というリスクの解説から、「どうやって直すのか?」 という具体的な修復手順(コンソール、AWS CLI、Terraformなど)まで、分かりやすく解説します。

この記事では、Security Hubで検出された「[SNS.1] SNS トピックは、AWS KMS を使用して保管時に暗号化する必要があります」というセキュリティ課題の修正方法について解説します。

ポリシーの説明

[SNS.1] SNS トピックは、保管時にAWS KMSを使用して暗号化する必要があります

Amazon SNS の Security Hub コントロール – AWS Security Hub

このコントロールは、Amazon SNS トピックが AWS Key Management Service (AWS KMS) に管理されているキーを使用して保管中に暗号化されているかどうかをチェックします。SNS トピックがサーバー側の暗号化 (SSE) に KMS キーを使用しない場合、コントロールは失敗します。デフォルトでは、SNS はディスク暗号化を使用してメッセージとファイルを保存します。このコントロールに合格するには、代わりに暗号化に KMS キーを使用する必要があります。これにより、セキュリティレイヤーが追加され、アクセスコントロールの柔軟性が向上します。

Amazon SNSは、アプリケーションやユーザー間でメッセージを配信するためのスケーラブルなメッセージングサービスです。SNSトピックに保管されるメッセージには、機密情報が含まれる可能性があります。AWS KMS (Key Management Service) を使用して保管時の暗号化を有効にすることで、これらのメッセージは保存時に暗号化され、不正なアクセスから保護されます。

修復方法

AWSコンソールでの修正手順

  1. Amazon SNS > トピックに移動します
  2. 「編集」を選択後、暗号化-オプションを有効化します。
  3. 設定後、必要項目を入力し「トピックの作成」を行う。

Terraformでの修復手順

#-------------------------------
# 変数
#-------------------------------
variable "topic_name"    { type = string }
variable "environment"   { type = string }
variable "tags"          { type = map(string) default = {} }

#-------------------------------
# KMS (カスタム CMK)
#-------------------------------
resource "aws_kms_key" "sns" {
  description         = "KMS key for SNS encryption"
  enable_key_rotation = true

  policy = jsonencode({
    Version   = "2012-10-17",
    Statement = [
      # ① 口座ルートに全権
      {
        Sid      = "RootAccess",
        Effect   = "Allow",
        Principal= { AWS = "arn:aws:iam::${data.aws_caller_identity.current.account_id}:root" },
        Action   = "kms:*",
        Resource = "*"
      },
      # ② SNS サービスプリンシパルに最小権限
      {
        Sid      = "AllowSNS",
        Effect   = "Allow",
        Principal= { Service = "sns.amazonaws.com" },
        Action   = [
          "kms:Encrypt","kms:Decrypt",
          "kms:GenerateDataKey*","kms:DescribeKey"
        ],
        Resource = "*"
      }
    ]
  })
}

resource "aws_kms_alias" "sns" {
  name          = "alias/sns-${var.environment}"
  target_key_id = aws_kms_key.sns.key_id
}

#-------------------------------
# SNS トピック (暗号化あり)
#-------------------------------
resource "aws_sns_topic" "encrypted" {
  name              = var.topic_name
  kms_master_key_id = aws_kms_key.sns.arn

  tags = merge(var.tags, {
    Environment = var.environment
  })
}

output "sns_topic_arn" { value = aws_sns_topic.encrypted.arn }

AWS CLI

REGION="ap-northeast-1"
TOPIC_ARN="arn:aws:sns:${REGION}:123456789012:myTopic"
KEY_ALIAS="alias/sns-encryption-key"

# 1) カスタム CMK 作成
KEY_ID=$(aws kms create-key \\
           --description "CMK for SNS encryption" \\
           --region $REGION \\
           --output text --query 'KeyMetadata.KeyId')

aws kms create-alias \\
  --alias-name ${KEY_ALIAS} \\
  --target-key-id $KEY_ID \\
  --region $REGION

aws kms enable-key-rotation --key-id $KEY_ID --region $REGION

# 2) トピックに割当
aws sns set-topic-attributes \\
  --topic-arn $TOPIC_ARN \\
  --attribute-name KmsMasterKeyId \\
  --attribute-value $KEY_ID \\
  --region $REGION

ベストプラクティス & 運用注意点

項目推奨
キーの種類通常の機密度なら AWS 管理キー (alias/aws/sns) で SNS.1 は合格。より厳格な管理・クロスアカウント共有が必要なら カスタム CMK を使用。
課金CMK 使用 10,000 リクエストごとに課金が発生。メッセージ量が多いワークロードではコストを試算してください。AWS ドキュメント
クロスアカウント配信サブスクライバー (SQS / Lambda 他) が別アカウントの場合、そのアカウントにも CMK 参照権限を付与する。
継続監査AWS Config ルール sns-encrypted-kms を有効化し、逸脱を自動検知。
Key policy の最小化kms:* ワイルドカードは避け、SNS に必要な 4 アクションのみ許可。

最後に

今回は、SNSトピックをAWS KMSを使用して保管時に暗号化する方法についてご紹介しました。SNSトピックに機密性の高いメッセージを扱う場合は、保管時の暗号化を有効にすることで、データのセキュリティを確保することが重要です。カスタマー管理のKMSキー (CMK) を使用することで、より詳細なアクセス制御と監査が可能になります。

この問題の検出は弊社が提供するSecurifyのCSPM機能で簡単に検出及び管理する事が可能です。

運用が非常に楽に出来る製品になっていますので、ぜひ興味がある方はお問い合わせお待ちしております。

最後までお読みいただきありがとうございました。この記事が皆さんの役に立てば幸いです

この記事をシェアする

クラウドセキュリティ対策実践集一覧へ戻る

貴社の利用状況に合わせた見積もりを作成します。

料金プランを詳しく見る