JavaMail:メール送信でOP25B対応
【概要】
昨今のスパムメール対策により,Javaプログラムからのメール送信が困難な場合がでてきています。送信先がLAN内だったり,LAN内のメールサーバ(MTA)をリレーしたり,ISPが提供するメールサーバをリレーしてメール送信するなら問題ありませんが,JavaプログラムからISPのユーザ回線を経由してインターネットの向こう側に設置しているメールサーバでメールをリレーしようとすると,最近各ISPが導入を進めているOutbound Port 25 Blocking(OP25B)によりメール送信が阻止されてしまうことがあります。
Outbound Port 25 Blockingとは,一般ユーザのパソコンから送信用メールサーバをリレーせずに直接送信先のメールサーバへメールを送りつけるのを禁止するもので,ISPのユーザ回線から外部の25番ポート(SMTP)へ接続するのを阻止することで実現しています。これにより25番ポートからインターネットへメール送信できるのはISPのメールサーバや固定IPを取得したホストに限られますが,メールをリレーする送信用メールサーバがISPの外側にいる場合にも接続が阻止される弊害が出ています。
この対策としては,ISPの外側にいるメールサーバがメール送信のリレーを受け付けるときは25番以外のポート番号を使用すればよいということになります。この代替ポートとして「サブミッションポート」と呼ばれる587番ポートを使うようメールサーバを設定することができます。このとき587番ポートが正規のアカウントによるメール送信のみに使われるように,587番ポートはSASL認証必須に設定します。メールサーバ側のサブミッションポート対応についてはこちらの記事の後半にて,Mac OS X Serverで稼動するPostfixの設定方法を解説しています。
【JavaMailによる実装例】
この記事では,JavaプログラムからJavaMailを使ってメール送信するときに,メールサーバに25番ではなく587番ポートに接続して,SASL認証を行った上でメール送信するコードを例示します。なお,JavaMailを使用するには,事前にJavaMailとJAFをダウンロードして,クラスパスで指定されているディレクトリにJavaMailの「mail.jar」とJAFの「activation.jar」をインストールしておく必要があります。(JAFはJava SE 6に含まれるようになったので,Java SE 6ではJAFのインストールは不要です。)
JavaMailダウンロード:[JavaMail][JAF]
クラスパスの設定:[概要][Windows][Solaris][Mac OS X]
下記のコードではSASLの認証方法として「AUTH LOGIN」で認証できることを確認しています。認証方法「CRAM-MD5」については,JavaMailではSMTPで未サポートのようです(出典)。
下記のコードは25番ポートへ認証なしにメールを送信する場合と以下の点が異なります。
1)接続先SMTPサーバのポート番号を587番に指定:
→プロパティ「mail.smtp.port」を「587」に設定。
2)SASL認証(SMTP Auth)を試みるよう指定:
→プロパティ「mail.smtp.auth」を「true」に設定。
3)SASL認証で使用する認証情報クラスを用意する:
→Authenticatorクラスを継承し,getPasswordAuthenticationメソッドを実装したクラス(PassAuther)を用意する。
4)Session取得時に認証情報クラスインスタンスで初期化:
→Session.getDefaultInstance()メソッドの第二引数にPassAutherのインスタンスを渡す。
【WebObjectsでJavaMailを使う場合の注意】
WebObjectsアプリケーションではデフォルトで「Session」というクラスが作られるため,JavaMailのSessionクラスとクラス名のバッティングが起こります。そのためJavaMailのSessionクラスを指定する場合に「javax.mail.Session」とフルパスでクラス名を指定するなどの対応が必要です。
JavaMailを使って587番ポートからSASL認証してメール送信を行う実装例:
import java.util.*; import javax.mail.*; import javax.mail.internet.*; /** * SendSASLMail:メール送信クラス. */ public class SendSASLMail { /** * PassAuther:認証情報クラス. */ private class PassAuther extends Authenticator { private String mUserName; private String mPassword; //------------------------------------------------------------------ /** * PassAutherクラスのコンストラクタ. * @param userName SASL認証で使うユーザ名. * @param passwd 同パスワード. */ public PassAuther ( String userName, String passwd) { super(); mUserName = userName; mPassword = passwd; } //------------------------------------------------------------------ /** * Authenticatorの派生クラスで必須のメソッド. */ public PasswordAuthentication getPasswordAuthentication () { return new PasswordAuthentication(mUserName, mPassword); } } private String mHostName; private String mUserName; private String mPassword; //------------------------------------------------------------------ Authenticator auther = new PassAuther(mUserName, mPassword); // session.setDebug(true); // デバッグ情報を表示する. mmsg.setFrom(from); Transport.send(mmsg); String subject = "テストメール"; |
【著作権表記】上記コードを含む本ブログのプログラムコードは,私的利用可,商用利用可,改変しての利用可です。利用の際に作者に許諾を得る必要はありません。
■関連情報
ISPによるOP25B 実施状況((財)日本データ通信協会・迷惑メール相談センター)
メール送信サンプル:[JavaMail(SMTP)編(JavaでHelloWorld)][JavaMailでメール送信アプリを作る(@IT Java Tips)]
JavaMail完全解説
Sun:[JavaMail]
API Reference(javadoc):[JavaMail][J2EE 1.3.1]
ダウンロード:[JavaMail][JAF]
WebObjects:WOMailDeliveryで日本語メール送信
■関連書籍をAmazonで検索:[JavaMail][Java]
●独習Java サーバサイド編 第2版 (kindle版)
←この記事が役に立ったという方はクリックお願いします。
| 固定リンク
「プログラミング」カテゴリの記事
- シェルスクリプト:「.svn」ディレクトリを一括削除する(2015.03.23)
- JavaScript:excanvasを使ってWebページに画像を表示する(2012.05.07)
- C言語:TRUEとFALSEの値(2012.05.06)
- Java:CSVパーサを作る(その3) - RFC4180対応 後編(2008.06.13)
- Java:CSVパーサを作る(その2) - RFC4180対応 前編(2008.06.12)
「Java」カテゴリの記事
- Java:Reader/Writerにおけるclose()メソッド呼び出しの流儀(2015.06.29)
- Java:例外が起こったときに実行されるコードとされないコード(2015.03.31)
- Java:前回作成したコードの処理速度を比較する(2015.03.15)
- Java:数値を3桁ごとのカンマ区切りの文字列にする(2015.03.02)
- Java:全角の数値文字列を数値として受け付ける(2015.01.19)