はじめに
みなさんこんにちは。AWSも好きなSalesforceエンジニアの吉澤です。
今日はSalesforceとAmazon SESを使ったメール配信システムについてお話したいと思います。
メール送信におけるSalesforceの制限
1組織あたり1日に最大5000個の外部メールアドレスに対し一括メール送信ができる。
Salesforceの一括メール送信は取引先責任者、個人取引先、リード、および内部ユーザにのみ。
(内部ユーザへのメール送信は制限はありません。)
※Salesforceヘルプより引用
今回の仮想シナリオ
今回は、以下のような場合に、どうやったら簡単にメール配信ができるかを考えてみました。
1.Salesforceの外部ユーザ(5000人以上)に対し、ダイレクトメールを送付したい。
2.迷惑メール業者に認定されたくないので、不達管理は行う!
メール配信ができそうなツールを考えてみた。
メール配信を考えたときにまずはじめに思いついたのが、Amazon SESです。
Amazon SESはAmazon Web ServicesのEメールプラットフォームです。
メールの送信機能には以下のような特徴があります。
・SPFやDKIMなどの認証に対応している。
・メールが不達だった場合、Amazon SNSを使って結果を返してくれる。
・弊社連携ツールである、SkyOnDemandのメールアダプタを使うと簡単に送信できる。
こうした特長から、Amazon SES&SkyOnDemandであれば、今回の条件でも簡単にメール配信&不達管理ができそうです。
全体の構成
1.配信者はメール対象オブジェクトに対象となるメールアドレスを登録します。
2.配信者がメール配信処理を行うと、SkyOnDemandがメール配信対象から対象メールアドレスを抽出し、Amazon SESを使ってメール配信される
3.不達のメールはAmazon SNSを使ってSalesforceに返され、Salesforceの処理で不達フラグを立てる。
メール送信設定
メール配信の事前準備として、メール送信サーバーのグローバルリソースの設定を行います。
こちらはリージョンごとに固定です。
メール配信スクリプトはメールデータ取得→送信対象→宛先セット→メール送付と、これだけです。
メール送信アイコンでは認証キーが必要ですので、以下のように設定します。
必須設定タブ
送信元メールアドレス:AWS側で認証済のメールアドレス
認証タブ
ユーザ名 :AWSで発行したメールユーザのアクセスキー
パスワード:AWSで発行したメールユーザのシークレットキー
メール送信はたったこれだけの作業でできました!
不達管理設定
不達になったメールはAmazon SNSで通知されます。
まずはAmazon SNSの仕様を調べてみました。
Amazon SNS
Amazon SNSの通知方法は6種類があります。
・HTTPS(JSON)
・HTTP(JSON)
・SQS
・Email
・Email-JSON
・Application
今回はSalesforceのメールサービスを使い、不達メールアドレスを受け取るようにしました。
メールサービス設定
メールサービス設定はこのような形で設定します。
MailServiceClass
このメールサービスで呼び出すクラスでは、メール本文の解析、バウンスメールレコードを作成、メール本文内からステータス、メールアドレスを抽出し、メール配信対象オブジェクトを検索。該当するメールアドレスのメール配信対象に対し、不達のチェックフラグを立てる。
といった処理を行います。
global class BounceMailHandler implements Messaging.InboundEmailHandler { global Messaging.InboundEmailResult handleInboundEmail(Messaging.InboundEmail email, Messaging.InboundEnvelope envelope) { Messaging.InboundEmailResult result = new Messaging.InboundEmailresult(); try { // バウンスメールを作成 Bouncemail__c bmail = new Bouncemail__c(); bmail.Detail__c = email.plainTextBody; // ステータス検索 String statuscode = getObjectFromBody(bmail.Detail__c,'status\\\\":\\\\"','\\\\','"Message" : ','status'); bmail.Status__c = statusCode; // メールアドレス検索 String bounceMailAdderess = getObjectFromBody(bmail.Detail__c,'destination\\\\":\\[\\\\"','\\\\','"Message" : ','destination'); bmail.Email__c = bounceMailAdderess; // タイムスタンプ検索 Datetime bounceDatetime; String bounceTimeStamp = getObjectFromBody(bmail.Detail__c,'Timestamp" : "','"','"Timestamp" : ','Timestamp'); if(!String.isEmpty(bounceTimeStamp)){ System.debug(bounceTimeStamp); // 年取得 Integer bYear = Integer.valueOf(bounceTimeStamp.subString(0,4)); // 月取得 Integer bMonth = Integer.valueOf(bounceTimeStamp.subString(5,7)); // 日取得 Integer bDay = Integer.valueOf(bounceTimeStamp.subString(8,10)); // 時取得 Integer bHour = Integer.valueOf(bounceTimeStamp.subString(11,13)); // 分取得 Integer bMin = Integer.valueOf(bounceTimeStamp.subString(14,16)); // 秒取得 Integer bSec = Integer.valueOf(bounceTimeStamp.subString(17,19)); System.debug(bYear); System.debug(bMonth); System.debug(bDay); System.debug(bHour); System.debug(bMin); System.debug(bSec); // 日時型へ変換 Datetime tmpDate = datetime.newInstance(bYear,bMonth,bDay,bHour,bMin,bSec); // 9時間加算 Datetime bDate = tmpDate.addHours(9); // 項目セット bmail.SendDateTime__c = bDate; } if((statuscode=='5.1.1' || statuscode=='5.3.0') && !String.isEmpty(bounceMailAdderess)){ // 該当メールアドレスが設定されている取引先を検索 List<SendMailTo__C> bounceMailToList = getMailToFromEmail(bounceMailAdderess); // メール配信対象更新 if(bounceMailToList != null && bounceMailToList.size() > 0){ for(SendMailTo__C cont : bounceMailToList){ cont.MailBounceFlg__c = true; cont.MailBounceDate__c = SYstem.now(); } update bounceMailToList; // メール配信対象と紐づけ bmail.mailToUpdateFlg__c = true; } } Insert bmail; }catch(Exception e){ String errMsg = '◆◆◆バウンスメール処理エラー:' + e.getMessage(); system.debug(errMsg); // 本文のみセットし登録 Bouncemail__c errorMail = new Bouncemail__c(); errorMail.Detail__c = email.plainTextBody; Insert errorMail; // throw new EstimateWSMailHandlerException(errMsg); } return result; } }
※処理の基幹部分のみを抜粋
これで不達となった対象ユーザを把握できるようになりました。
まとめ
より充実した機能を求めるとApp Exchangeでメール配信サービスなどの利用を考えますが、今回は単純なメール配信サービスであれば、Salesforceと他のサービスをつなぐ事で比較的簡単にできました。
SalesforceやAWSはどんどんと新しいサービスが発表されておりますので、より新しいサービスを触ってみたいと思います。