だ。ログ。

開発とかスノボとかやきうとか。

SESからSNSを経由したバウンスメールの通知のjsonが上手くパース出来ない件

SESの大原則、メールのバウンス率が5%を越える事なかれ。
商用環境だろうとなんだろうと無慈悲なサービス停止を回避する為にはメールの送信失敗率を極力抑える必要性がある。
送る事は前提として、どうやって抑えるか。
多分、厳密には送る前にアドレスの正当性とかを判断するのが必要なのだろうが、そこまでの資金力も開発力もない。

となると、送って良いメールかバウンスで戻った事があるメールか。の判断しリスト化する事が必要になる。
リストと一致したデータがある場合は送信しない。と言う事になる。

SES → SNSのリレーションの設定に関しては
http://program-memo.com/archives/599
プログラムメモ様を見ると、詳細な設定が図解されているので参照。

さて、ここまでの設定が終わった段階でエンドポイントに仕込むプログラムで1日以上苦労したのでそのメモ。
結論から言うと、SNSから送られてくるjsonに不要な中括弧がある。

{
  "Message" : "{"notificationType":"Bounce","bounce":{"bounceType":"Permanent","bounceSubType":"General","bouncedRecipients":[{"emailAddress":"bounce@simulator.amazonses.com".........}}",
}

Message項のnotificationの前にダブルクォーテーションで囲まれた中括弧が入っているのである。
なので、これを

include_once dirname(__FILE__).'/autoload.php';
use GuzzleHttp\Client;

$json = file_get_contents("php://input");
$arr = json_decode($json,true);
echo $arr['Message'];

とした際に出てくる結果は「{」中括弧になってしまっている。
なので、Messageの中を一度パースする。

今回は失敗したメールアドレスを取得する。

$json = file_get_contents("php://input");
$arr = json_decode($json,true);
$arr2 = json_decode($arr['Message'],true);
$email = $arr2['bounce']['bouncedRecipients']['0']['emailAddress'];

要は送信されたjsonのMessageをもう一回json_decodeする。と言う事が大切になる。
それと、上記のソースコードの$arr2を

error_log($arr2);

で出力すると

error_log() expects parameter 1 to be string

とエラーを吐いてしまう。
$arr2の内容を見る際には

error_log(print_r($arr2,true));

とする。
$emailのboucedRecipientsに添え字で0が入っている事が分からず数時間詰まった。
http://butterbull.hatenablog.com/entry/2014/06/11/215653
様に感謝。