PHP工房「PHPメールフォーム(無料版)」は、PHPでフォーム制作をしたことがある人なら使わずとも見かけたことは1度はあるだろう。CMSも入れるほどではない小規模のサイトやページでは無料で使えるこのフォームは重宝する。実際に今まで何度かお世話になってきた。ありがとう!PHP工房さん!
で、クライアントから
「Gmailで管理者宛のメールが受け取れないのよ」
と連絡が入り、私はすぐさま
「ああ~、それねえ、Gmailはセキュリティたーかいから、簡単にメールってのは受け取れないのよ、うーん、でも私なら直せると思いますのでちょっと待っとってください」
と返したのだった。だがその後、3日間ものあいだ返信をすることができず、問題解消はできないかと思われた…修正してはフォームを送信。試すこと100回以上。ぜんぜん届かん!なぜだ、なぜだ、なぜだーー!と悶々とした日々を過ごした。だが明けない夜はないとか言うように、一つずつ問題を解決していき、ついにGmailへ管理者メールが届くようになった!なのでそのやり方を残しとくね。
結果から言うと、原因は複合的に絡んでいて、大きく分けて2つ。「SPF,DKIM,DMARC」と「Return-Path,From」が原因だ。わけがわからないかもしれないが、わかってしまうとなんつうことはないので臆することはない。順を追って見ていこう。
SPF,DKIM,DMARC
SPF(Sender Policy Framework)、DKIM (DomainKeys Identified Mail)、DMARC (Domain-based Message Authentication Reporting and Conformance)は平たく言えば「メールの送信元を確認する仕組み」という意味だ。
確認の流れとしては、
Gmailにどっかからメールが届けられる
→Googleが「届ける前にこのメールの身元確認をしとこう」
→ドメインにアクセス
→DNSに書かれたなんじゃかんじゃを確認
→身元が確認取れた!
→よし、届けよう
みたいなことだ。簡単に言えばね。詳しいことはここでは知らなくてOK。
昨今のサーバーではこれらの設定が簡単にできるようになっているはずだ。さくらサーバーなんかはここ数年前に機能を設置してくれたが、その操作は簡単すぎるくらい簡単だ。自分の使用しているサーバーでは備わっているか調べてみよう。もし備わっていなければ、DNSに自力で設定する方法もある。こちらの記事も参照してみてくれ。
SPF設定(Postfix)Gmailで警告と鍵マーク。asahiネットのrelayhost使用時にはちょっと注意。
まあまあ大変かもしれないが、やるしかない。今の時代では、SPFだのが設定されていないと信用されないのだから。
設定してから最大で48時間かかる場合がある。DNSに設定することなのでしかたがないのだが、大概は1時間もしないうちに反映されている。5分くらいのときもある。だが焦らず気長にいこう。
SPF,DKIM,DMARCの設定が済んだら、今度はReturn-Path,Fromだ。ここからはPHPを触るので、「PHPメールフォーム(無料版)」のmail.phpを開いてみよう。
Return-Path,From
ここでは以下の条件で改修をしていく。
●mail.phpは「最終更新日2014/12/12」というかなり古いバージョンを使用。(最新版ではないので、最新版を使用すればもっと簡単に済むかもしれない。)
●デフォルトは送信元(From)を「送ってくれた人のメアド」になっていて、GmailはそれをNGとするので「管理者のメアド」に変更する
●「管理者のメアド」を使用すると、誰から来たのかわからなくなるので、メールタイトルを変更する
以上が変更点になる。メールタイトルを変更しなくてもいい、という人はそこは飛ばしてもらっても構わない。その場合はReturn-PathとFromにかかわるところだけを改修しよう。
よし、いってみよっか。
メールタイトルを変更するために$dsp_nameを使用
//メールタイトルを変更するためなので、飛ばしてもとりあえずOK。ここではフォームに設定する入力項目のうちの「名前」を設定した。
$dsp_name = '名前';
次に、メールを送る部分。ここがこのプログラムの出口なわけだな。だがプログラム内の中盤よりちょっと前のほうにあるかな。検索して探してみよう。
太字の部分を追加している。
//管理者宛に届くメールをセット
$adminBody = mailToAdmin($_POST,$subject,$mailFooterDsp,$mailSignature,$encode,$confirmDsp);
$header = adminHeader($userMail,$post_mail,$BccMail,$to);
if(isset($_POST) && isset($_POST[$dsp_name])) {
$subject = h($_POST[$dsp_name]). "様より ".$subject;
//タイトルに送り主の名前を入れるため。不要な人は飛ばしてOK。h()はサニタイズなので絶対に外さないように。
}
$subject = "=?iso-2022-jp?B?".base64_encode(mb_convert_encoding($subject,"JIS",$encode))."?=";$add_params = '-f'. $to;//mail関数の第5パラメータに「fオプション」を設定するため。
mail($to,$subject,$adminBody,$header,$add_params);
//管理者宛のmail関数の第5パラメータに設定
if($remail == 1) mail($post_mail,$re_subject,$userBody,$reheader,$add_params);
//自動返信にもmail関数の第5パラメータに設定
次は管理者宛送信メールヘッダだ。けっこう下の方にある。太字の部分を追加。Return-PathとFromの設定だね。
//管理者宛送信メールヘッダ
function adminHeader($userMail,$post_mail,$BccMail,$to){
$header = '';
if($userMail == 1 && !empty($post_mail)) {
$header="From: $to\n";
//デフォルトでは、$header="From: $post_mail\n"; というように送信者のメアドを設定してくれているが、これだとGmailが迷惑メールフォルダに振り分けてしまう。なので必ず設定しよう
if($BccMail != '') {
$header.="Bcc: $BccMail\n";
}
$header.="Reply-To: ".$post_mail."\n";
}else {
if($BccMail != '') {
$header="Bcc: $BccMail\n";
}
$header.="Reply-To: ".$to."\n";
}
$header.="Return-Path: ".$to."\n";
$header.="Content-Type:text/plain;charset=iso-2022-jp\nX-Mailer: PHP/".phpversion();
return $header;
}
次はユーザ宛送信メールヘッダだ。これも下の方にある。太字の部分を追加。Return-Pathの設定。
※管理者宛のものをコピペしてはダメだ。作者が書き方を変えているので、それに合わせよう。
//ユーザ宛送信メールヘッダ
function userHeader($refrom_name,$to,$encode){
$reheader = "From: ";
if(!empty($refrom_name)){
$default_internal_encode = mb_internal_encoding();
if($default_internal_encode != $encode){
mb_internal_encoding($encode);
}
$reheader .= mb_encode_mimeheader($refrom_name)." <".$to.">\nReply-To: ".$to;
}else{
$reheader .= "$to\nReply-To: ".$to;
}
$reheader .= "\n"."Return-Path: ".$to;
$reheader .= "\nContent-Type: text/plain;charset=iso-2022-jp\nX-Mailer: PHP/".phpversion();
return $reheader;
}
という感じで、数カ所の修正だが、慣れないと難しいだろう。そしてこれらの設定のどれもが欠けると届かないとか迷惑メールに入る、とかが起こる。Hotmailでは違った判定になるなどもあるので、いろいろなメールで試してみると、今後の勘も働いていくようになると思う。
わからないことがあったらコメントで質問してくれ。気が付かないときもあるかもだけれど、出来る限りお答えしよう。(そもそも難しすぎて答えられないかもだけれど)