[アップデート]SQSのサーバサイド暗号化キーにSSE-SQSが追加されました

SQSのメッセージ保存時の暗号化を無料で実施できようになりました!
2021.11.26

こんにちは!コンサル部のinomaso(@inomasosan)です。

今回はSQSのサーバサイド暗号化キーにSSE-SQSが追加されたので、内容を紹介していきます。

概要

2021/11/23に、SQSサービスが所有する暗号化キー(SSE-SQS)を使用してメッセージ保存時の暗号化ができるようになりました。

従来はCMKであるSSE-KMSのサポートのみだったので、暗号化キーの選択の幅が広がりました。

尚、SSE-SQSの暗号化方式はAES-256となります。

何が嬉しいの?

SSE-SQSのメリットは以下の通りです。

  • SQSサービスが所有する暗号化キーを使用するため、暗号化キーを新規作成する必要はありません
  • SSE-SQSを使用した保存時の暗号化は、追加料金なしで利用可能です
  • EC2やLambda等から利用する際のIAMポリシーに暗号化キー関連のアクセス許可設定は不要です
    • ちなみにSSE-KMSのデフォルトマスターキー(AWS管理CMK)も同様にIAMポリシー設定不要です

全リージョンで使用可能?

中国リージョンを除く全てのAWSリージョンとAWS GovCloud(US)リージョンで利用できます。

やってみた

構成図

今回はSQSのメッセージ保存時の暗号化にSSE-SQSを使用し、EC2からメッセージ送受信できるか検証してみます。

SQS作成

AWSマネージメントコンソールからSQSサービスを開きキューを作成をチェックします。

詳細で任意のキュー名を入力します。

暗号化サーバー側の暗号化有効と、Encryption key typeAmazon SQS キー (SSE-SQS)にチェックを入れます。

それ以外の項目はデフォルトのまま、キューを作成をクリックします。

EC2とIAMロール作成

EC2はAmazonLinux2の最新AMI(ami-0404778e217f54308)で構築しました。

EC2からSQSへメッセージ送受信するためにIAMロールを作成します。
IAMロールにアタッチするIAMポリシーは、最低限のActionのみ許可し、Resourceは先ほど作成したSQSのみに制限するようにしました。

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "sqs:SendMessage",
                "sqs:ReceiveMessage",
                "sqs:DeleteMessage"
            ],
            "Resource": "arn:aws:sqs:ap-northeast-1:<AWS Account ID>:inomaso-dev-sqs"
        }
    ]
}

IAMロールとIAMポリシを作成したら、EC2にIAMロールをアタッチします。

SQSメッセージ送受信

SSE-SQSを使用してメッセージ保存時に暗号化した場合に、透過的にメッセージ送受信可能か検証していきます。 今回は、弊社の以下ブログにあったサンプルコードを検証で使用したかったので、EC2にNode.jsSDK for JavaScriptをセットアップします。

 セットアップは以下ドキュメントを参考に実施しました。

EC2にsqs_send_message.jssqs_receive_message.jsいうファイル名でNode.jsモジュールを作成します。

sqs_send_message.js

const AWS = require("aws-sdk")
const SQS = new AWS.SQS({ region: "ap-northeast-1" })

const QueueUrl = "https://sqs.ap-northeast-1.amazonaws.com/<AWS Account ID>/inomaso-dev-sqs"

async function sendMessage(message) {
  try {
    const MessageBody = JSON.stringify({ message })
    const result = await SQS.sendMessage({ MessageBody, QueueUrl }).promise()
    console.log(result)
  } catch (e) {
    console.error(e)
  }
}

sqs_receive_message.js

const AWS = require("aws-sdk")
const SQS = new AWS.SQS({ region: "ap-northeast-1" })

const QueueUrl = "https://sqs.ap-northeast-1.amazonaws.com/<AWS Account ID>/inomaso-dev-sqs"

async function processingMessage() {
  try {
    const params = {
      QueueUrl,
      MaxNumberOfMessages: 10, // 最大取得メッセージ
      WaitTimeSeconds: 20 // ロングポーリング
    }
    const messages = await SQS.receiveMessage(params).promise() // メッセージを取得
    for (message of messages.Messages) {
      //const body = JSON.parse(message.Body)
      console.log(message)
      //console.log(body.message) //メッセージの実態
      //重い処理
      await new Promise((resolve, reject) => {
        setTimeout(resolve, 1000)
      })
      const params =  {
        QueueUrl,
        ReceiptHandle: message.ReceiptHandle
      }
      const deleteResult = await SQS.deleteMessage(params).promise()
      console.log(deleteResult)
    }

  } catch (e) {
    console.error(e)
  }
}

processingMessage()


Node.jsモジュールを作成したら、メッセージ送受信できるか確認していきます。
それぞれの実行結果は以下の通りです。

SQSへメッセージ送信
# node sqs_send_message.js
{
  ResponseMetadata: { RequestId: '0c1a1186-c2bd-5f88-a50c-4b9c5dfca4ab' },
  MD5OfMessageBody: '04366f504cabfb9b64545bd8f0a6012b',
  MessageId: '16828cb4-b276-4ff3-836a-704e494c8e69'
}
SQSからメッセージ受信および削除
# node sqs_receive_message.js
{
  MessageId: '16828cb4-b276-4ff3-836a-704e494c8e69',
  ReceiptHandle: 'AQEBr5cbzG1MqxeQwKSJs/QE3eG9pJ2QqZiIIQx61d+U0bOdHkqFILn4KYBnmnIcSHRkYNi/fGQMwT+AsGt9PEnMCtTJJXmoBEV3cH7tCC+fWQXObSDwlhV2lAEUrZCnWvYycQAey6TM/97u8pM3SFOSwNEhMPFww38XCyX4ZvHWcbuOKqiHqYDuuhNBRxKs+pGLoyj63tJbjXVqaWl//H1W8/RjVXDNFVidxesltVwVDQjRkBDqrPNBF69M++MwXac84XnkSyj8/wE/swclSbQvrYovY8QzoNMVdS3OcV+3BEkVyDP6NB3SSvnbWIEil1PH6Ed5sViOkXjU+0nqNnsZQkG+CbdmNZTiyhJeKLRheCbr6kMUD3TsgMLvzrm7+nxNyGEEbCGp5u9te6QMeSQZ6w==',
  MD5OfBody: '04366f504cabfb9b64545bd8f0a6012b',
  Body: '{"message":"こんにちは"}'
}
{
  ResponseMetadata: { RequestId: '1bad37eb-5f14-5329-ae1e-6df1c043864b' }
}

SSE-KMSを選んだ方が良いケースは?

暗号化キーに対するリクエストの監査証跡(CloudTrail)が必要な場合、SSE-SQSだと対応しておりません。
それ以外にも、セキュリティやコンプライアンスが詳細に求められている場合等は、SSE-KMSを検討して頂くのが良いかと思います。

DevelopersIOに同じアップデート記事があるんだけど?

AWSアップデートブログ競争に敗北し、2番手となってしまいました。 ただ、最初のアップデート記事はクロスアカウントにフォーカスした内容ですので、本記事と合わせ1粒で2度美味しいアップデートブログとなります。

あわせて読みたいURL

まとめ

SSE-SQSを利用すると、無料でメッセージ保存時の暗号化が可能になりましたので、コストや設計・実装のハードルが下がったのではないでしょうか。 ざっと調べた&検証してみた限りは、SSE-S3と同様な扱い方ができるがと思います。

この記事が、どなたかのお役に立てば幸いです。それでは!