ポイント
- 送信アドレス誤りは同イントラ内限定で検出できた。別ドメインへのメール送信エラーは制御出来ない。
- 複数のアドレスに送信するときにアドレス誤りを検出するには、SmtpFailedRedipientsException と SmtpFailedRecipientException の両方でキャッチする必要がある。
- 1 つのアドレスにだけ送信する場合は、SmtpFailedRecipientException のみでよい。
- 送信できなかったメールアドレスは、SmtpFailedRecipientException.FailedRecipient に格納されている。
- Host、Port、userName、password に原因がある (つまりサーバに接続できない) 場合は SmtpException でキャッチできる。
他のポイント
- メールを送るには、MailMessage クラス、SmtpClient クラスの 2 つが必要
- MailMessage クラスはメール自体を扱うクラス
- From、To、CC、BCC、添付ファイル、件名、本文などを扱う。
- メールアドレスの追加は、MailAddress クラスにメールアドレス文字列を渡してインスタンス化したものを使う。
- SmtpClient クラスはメールを送るときの認証情報を扱うクラス。
- SMTP サーバ名、ポート番号、ユーザー名、パスワード、SSL の使用などを扱う。
- ユーザ名、パスワード の追加は、NetworkCredential クラスにユーザー名、パスワード文字列渡してインスタンス化したものを使う。
ソースコード
の環境、ファイルは同じです。リンク先の投稿のファイルを編集しました。
public ActionResult Index() { return View(); } [HttpPost, ActionName("Index")] [ValidateAntiForgeryToken] public ActionResult IndexExec() { //Hotmailでメールを送信する //MailMessageの作成 var from = "xxxxx@hotmail.co.jp"; var to = "yyyyy@gmail.com"; var to2 = "zzzzz@gmail.com"; var subject = "テスト"; var body = "このメールは、テストです。"; MailMessage msg = new MailMessage(); msg.From = new MailAddress(from); msg.To.Add(new MailAddress(to)); msg.To.Add(new MailAddress(to2)); msg.Subject = subject; msg.Body = body; SmtpClient sc = new SmtpClient(); //SMTPサーバーなどを設定する sc.Host = "smtp.live.com"; sc.Port = 587; sc.DeliveryMethod = SmtpDeliveryMethod.Network; //ユーザー名とパスワードを設定する var userName = "xxxxx@hotmail.co.jp"; var password = "zzzzz"; sc.Credentials = new NetworkCredential(userName, password); //SSLを使用する sc.EnableSsl = true; // 次のメール送信エラーハンドリング // - サーバ接続エラー // - 送信アドレス誤りエラー(同イントラ内。別ドメインへのメール送信エラーは制御出来ない) try { //メッセージを送信する sc.Send(msg); ViewBag.Message = "送信成功"; } catch (SmtpFailedRecipientsException e) { // 送信アドレス誤りエラーが2件以上の場合 // 誤ったアドレス分、例外を発生させる。 // 正しいアドレスには、メールが送られる。 var message = "SmtpFailedRecipientsException 発生で2件以上送信アドレス誤りエラー: "; foreach (var item in e.InnerExceptions) { message = message + " " + item.FailedRecipient; } ViewBag.Message = message; } catch (SmtpFailedRecipientException e) { // 送信アドレス誤りエラーが1件のみの場合 ViewBag.Message = "SmtpFailedRecipientException 発生で1件だけ送信アドレス誤りエラー: " + e.Message; } catch (SmtpException e) { // SmtpException クラス (System.Net.Mail) https://msdn.microsoft.com/ja-jp/library/system.net.mail.smtpexception(v=vs.110).aspx // Host、Port、userName、Password に原因がある // Host が原因ならば、SmtpException.InnerException に格納された WebException // Port が原因ならば、SmtpException.InnerException.InnerException に格納された SocketException // userName、password が原因ならば、SmtpException // WebException、SocketException を個別にキャッチすることはできない。 ViewBag.Message = "SmtpException 発生でサーバ接続エラー: " + e.Message; } finally { //後始末 msg.Dispose(); sc.Dispose(); } return View(); }
@using (Html.BeginForm()) { @Html.AntiForgeryToken() <div class="form-horizontal"> @Html.ValidationSummary(true, "", new { @class = "text-danger" }) <div class="form-group"> <div class="col-md-offset-2 col-md-10"> <input type="submit" value="メール送信" class="btn btn-default" /> </div> </div> </div> } <h3>@ViewBag.Message</h3>
実行した時のエラーメッセージ
パスワードを間違えた時
SmtpException 発生でサーバ接続エラー: メールボックスが使用できません。 サーバーの応答:5.7.3 Requested action aborted; user not authenticated
おわりに
メール送受信時のエラーは、メールが相手に届いたかどうか確認できたら素晴らしいのに、、、と思うのですけれどもメールが送信元のサーバーをはなれてしまうためどうにもなりません><。
思ったよりもサポートできる範囲が限られてしまう印象ですの。
以上です。