AWS SES メール送信環境のセキュリティ


はじめに

Amazon SES (以下SES) を使えば、Linuxを立ててPostfixを入れて設定して・・・などという面倒なことをしなくても、サーバレスで簡単にメール送信環境 (メールサーバのサーバレス版) を構築できます。
SESを使ってメールを送るには、AWS側で以下の3ステップを踏む必要があります。

  1. サンドボックスの解除
  2. SMTP Credentialの発行
  3. セキュリティ (認証・アクセス許可等) の設定

今回、以下の「目指したい姿」を満たすため、セキュリティの設定をどうすれば良いのか、検証によって導いてみました。

目指したい姿

今回、SESでやりたかったことは以下です。

  • メール送信用途で使う。
  • 送信を許可する唯一のドメインを「test1.com」とすること。
    • 「test1.com」以外のドメインは全て拒否されること。
  • Eメールアドレスは、個人につき1つ割り当てられ、個人は自分のメールアドレスだけを使用できること。
  • 全ての利用者は、管理者が払い出したEメールアドレス以外を名乗って使用できないこと。
  • SESから送信されていることを隠蔽すること。

SESのセキュリティ

SESのマネジメントコンソールを開くと「Identity Management」という項目があります。
この項目で、SESのセキュリティ (アクセス許可) を設定できます。

設定できるアクセス許可項目

「Domains」と「Email Addresses」の2項目を設定できます。
後述の検証結果でも分かりますが、これらはホワイトリスト形式です。

Domains

ここに登録したドメインをFromとするメールの送信を許可します。
ドメインは、DNSのゾーンに所定のTXTレコードを追加し、SESで承認される必要があります。
このため、他人が持っているドメインを勝手に登録してFromに使うことはできません。

Email Addresses

ここに登録したメールアドレスをFromとするメールの送信を許可します。
メールアドレスは、SESから送信される確認メールのリンクを押すことで、SESで承認される必要があります。
このため、他人が持っているメールアドレスを勝手に登録してFromに使うことはできません。

デフォルトの状態

まずはデフォルトの状態を見てみました。
サンドボックスを解除し、SMTP Credentialを発行しただけの状態では、DomainsとEmail Addressには何も登録されていません。

「Domains」

「Email Addresses」

この状態でSESのSMTP Endpointに対してメールを送信しても、以下のようなエラーが返り、送信に失敗します。

Message rejected: Email address is not verified. The following identities failed the check in region US-EAST-1: [email protected], Taro Yamada <[email protected]>

つまり「Domains」と「Email Addresses」に何も入っていない状態では、SMTP Endpoint宛にメールを送信してもRejectされますので、何も送信できないと言えます。

この検証から、SESのセキュリティはホワイトリスト方式であり、Fromのドメインやメールアドレスは必要なものだけを許可するというポリシーであることが分かります。

検証パターン

「目指したい姿」を実現するにはどう設定を投入すれば良いのかを、検証によって導くことを考えました。
今回、SESのセキュリティの設定の入れ方のパターンを全9パターン定義し、検証しました。

検証表と、検証の結果は以下の通りとなりました。
検証により、以下のCase 7の組み合わせで各設定を投入すれば、「目指したい姿」が満たせると分かりました。

No. D DKIM EAs IAM P1 P2 P3 P4
1 - - - - F F F F
2 F - - T T F F
3 T - - T T F F
4 F - T T F F
5 T - T T F F
6 F - T F F F
7 T - T F F F
8 F T F F F
9 T T F F F

表の各項目については、以下の通りです。

  • D (Domains) : Domainsにおける、唯一の許可ドメイン名 「test1.com」 (From) の登録有無 (○/-)
  • DKIM : 上記の許可ドメイン名において、DKIMを有効にしたかどうか (T/F)
  • EAs (Email Addresses) : Email Addressesにおける、許可メールアドレス 「[email protected]」 (From) の登録有無 (○/-)
  • IAM (ses:FromAddress) : SMTP Credentialに紐づいているIAMポリシーのses:FromAddressにおいて、許可メールアドレス 「[email protected]」 (From) の登録有無 (○/-)
    • ses:FromAddressではFromのメールアドレスを制限可能。ses:FromAddressに書かれているメールアドレス以外がFromに指定されている場合、メールを送信できなくなります。
  • P1~P4 : 以下P1~P4のメール送信成否 (T/F)

上の表では、上記の7パターンにおいて、Fromを次の順で変更してメールを送信 (P1~P4) し、成否を確認し、結果を記入しました。

No. From Email Address
P1 [email protected]
P2 [email protected]
P3 [email protected]
P4 [email protected]

また、DKIMがTの場合のみ、amazonses.com経由であることを隠蔽できる結果が得られています。

検証結果から分かること

以下に、各設定について分かったことをまとめました。

1. DomainsはEmail Addressesよりも強い

Case 2とCase 4の結果から分かるように、Domainsで許可したドメインの具体的なFromメールアドレスをEmail Addressesに書いたとしても、許可はDomainsの範囲のままで、Email Addressesの範囲に絞られません。
これらの比較から、Domainsの設定はEmail Addressesの設定よりも強いことが分かります。
DomainsとEmail Addressesの和集合が、SESで送信を許可されるFromメールアドレスの範囲となります。

2. Domainsでドメインを許可すれば、Email Addressesのメールアドレス単位の許可は不要

1.で示したように、Domainsで許可したドメインのメールアドレスを、Email Addressesに書いたとしても、意味がありません。
例えば、Email Addressesの有無でケースが分かれるCase 7とCase 9は、結果が同じです。

Domainsでドメインを許可した場合は、Email Addressesでそのドメインのメールアドレスを改めて許可する必要がないと言えます。

3. Domainsはホワイトリストであり、ここに書かれたドメイン以外は通らない

Fromにtest2.comを指定し、ローカル部を変えて送信を検証 (P3とP4) しましたが、Domainsでtest1.comしか許可していない状況では、どちらも送信できません。
つまりDomainsでドメインを絞った時点で、他のドメインからの送信は全て遮断できると言えます。

4. amazonses.com経由を隠蔽するにはDKIMを設定する

検証結果から分かるように、DKIMのT/Fによってamazonses.com経由の表示の有無が変わりました。
amazonses.com経由であることを隠すために、DKIMを入れるべきだと言えます。

5. 「1人あたり1メールアドレス」にはses:FromAddressが必須

SMTP CredentialのIAMポリシーで「ses:FromAddress」を設定すると、Domainsで許可したドメインの中で、Fromのメールアドレスを限定できます。
この仕様を利用し、個人ごとにSMTP Credentialを与え、各SMTP CredentialのIAMポリシーでメールアドレスを限定すれば、「1人あたり1メールアドレス」を配って利用してもらうことができます。

設定例は以下となります。

policy
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": "ses:SendRawEmail",
            "Resource": "*",
            "Condition": {
                "ForAnyValue:StringLike": {
                    "ses:FromAddress": [
                        "[email protected]"
                    ]
                }
            }
        }
    ]
}

SESを使う時に押さえておきたい特徴や対策

分析結果から総合すると、以下のようにまとまりそうです。

  • ドメイン、メールアドレスのなりすましは基本的にできない
    • SESでホワイトリストに追加する時に必ず所有を確認されるため
    • ただしドメインやメールアドレスそのものが乗っ取られないように注意
      • DNSのセキュリティ、メールの認証情報 (SMTP Credential含む) の管理は厳重に
  • SESのアクセス許可はホワイトリスト
    • Fromのドメインやメールアドレスを追加しない限りは、何もできない
    • SMTP Credentialの発行も必要
  • 個人ごとにメールアドレスを発行するには、SMTP CredentialのIAMポリシーを設定
    • Credentialごとにses:FromAddressでメールアドレスを縛る
    • 個人ごとにSMTP Credentialを払い出して配布する
  • 個人の不正なメール利用を疑ったら、まずSMTP Credentialの無効化で対処
    • 個人ごとにSMTP Credentialを分けていれば、この対処が可能
    • 上記で止まらない場合にDomainsやEmail Addressesを無効化
    • SMTP Credentialの使用状況はIAM Access Analyzerで追跡
  • DKIMでSES経由を隠蔽する
    • 署名による信頼度アップ
    • DKIM自体がアクセス許可を左右するわけではない (検証結果からも分かる)

終わりに

ハードルが高そうなイメージがあるSESのセキュリティですが、それほど複雑なものではありません。
アクセス許可の観点でDomains/Email AddressesとSMTP CredentialのIAMポリシーを押さえ、メール送信の信頼度の観点でDKIMとSPF等を押さえれば、頭の中でも整理できると思います。
本記事が、SESを使ってメール送信環境を立てようと考えている皆様のお役に立てば幸いです。