おもしろwebサービス開発日記

Ruby や Rails を中心に、web技術について書いています

Action MailboxをAWS SESで利用する

「メール受信をトリガーにしてなにかする機能」であるAction MailboxはRails6.0からRailsに追加された機能です。なかなか実際に使うことがなかったのですが、最近機会に恵まれてAction Mailboxを導入したので簡単に概要を書き残しておきます。ingress*1にはAWS SESを利用しました。

そもそもAction MailboxはAWS SESを公式サポートしてないんですよ

まず、Action Mailboxが公式にサポートしているingressにAWS SESはありません。Action Mailboxのリリース前にはサポートされる予定があったのですが、AWS SESはSendgridなどの他のメールサービスと比べてAction Mailbox側で考慮すべき点が多く、他のサービスと同一の実装だといろいろ問題があったため最終的に公式サポートがない状態でリリースされました。

その後、有志がAWS SESサポートを入れようと頑張るのですが、Railsコアチームの中にSESを使っている人がいなくてメンテナンスの継続に問題があるということでRejectされます。

しかし最終的にここでの成果物がAWS公式のgemとして採用される、という結果になりました。

aws/aws-actionmailbox-ses-ruby

というわけでAWS SESでAction Mailboxしたい場合はAWS公式である上記gemを使うのが良さそうです。

actionmailbox-ses-rubyを使う時の設定の仕方

actionmailbox-ses-ruby gemのREADMEに設定方法は書かれています。なので単にその通りにやれば良いのですが、僕のようにAWSに詳しくない人間だといくつかハマる可能性があるので個人的なメモとしての設定の流れを箇条書きしておきます。

  • Route53(もしくは他のDNSサーバ)に、メールを受け取りたいSESリージョンに対応したMXレコードを登録する(例: 10 inbound-smtp.us-east-1.amazonaws.com)
  • メール受信用のS3バケットを作成しておく
  • Route53に設定したMXレコードのリージョンで、SESのEmail receiving設定を追加する
    • Recipient conditionsで、Railsに通知したいメールアドレスの条件を設定する
    • Actionsを設定してS3バケットにメールの内容を保存するようにする
      • S3に保存するのはactionmailbox-ses-ruby gem的にはOptionalのようだけど、S3に保存しないと150KBまでのメールしか扱えないようなので実質必須(参考: Publish to Amazon SNS topic action - Amazon Simple Email Service )
      • Action中のSNS topicにSNSトピックを設定する
        • SESではなくS3バケットのプロパティとしてSNSトピックを紐づけることもできるけど、そこからのHTTPSリクエストはaws-actionmailbox-ses-ruby側は考慮していないので注意
  • SNSトピックでは https://example.com/rails/action_mailbox/ses/inbound_emails のようにSubscriptionのEndpointを指定する
    • これを登録するとすぐに正しいEndpointなのか実際にリクエストを投げて確認が行われる
    • actionmailbox-ses-rubyはこの確認をうまく取り扱ってくれるが、うまく取り扱うためにはactionmailbox-ses-rubyを含んだRailsアプリケーションを先にデプロイしておかないといけない
    • さらにSNSのSubscription Endpointが正しいものと確認されていないと、それをSESと紐づけられない模様
    • なのでできる範囲でSESを設定しておき、 actionmailbox-ses-rubyが含まれているRailsアプリケーションをデプロイ→SNSを設定→SESの設定にSNSを追加、という流れになる
  • S3に保存したメールをAction Mailboxから取得する権限設定が必要。actionmailbox-ses-ruby gemのREADME中に記載された設定例ではconfig.action_mailbox.ses.s3_client_options = { region: 'us-east-1' }のようにs3_client_optionsにregionのみ書かれているけどこれはS3を扱えるIAMロールがEC2インスタンスにアタッチされている前提なので、普通にアクセスキーを使いたい場合は次のようにする。
config.action_mailbox.ses.s3_client_options = {
  region: 'us-east-1'
  access_key_id: 'YOUR_ACCESS_KEY_ID',
  secret_access_key: 'YOUR_SECRET_ACCESS_KEY'
}

雑感

上記のポイントを抑えつつ設定すればあとはAction Mailboxのレールに乗るだけです。

AWS SES経由でS3に保存したメールデータをAciton Mailboxで扱う際に、同じデータをActive Storage経由でまたS3にアップロードすることになるのが非効率だなという気もしますがまあこれは仕方がないですね…。

aws-actionmailbox-ses-rubyのスター数は執筆時点で5しかないのでみんなこのgem知らないんじゃないかな、と思い紹介を兼ねて書いてみました。誰かの役に立てば幸いです。

*1:Action Mailboxがメール受信に使う外部サービス