• notice
  • Congratulations on the launch of the Sought Tech site

System.Net.Mail.SmtpClient fails to send emails via SSL/TLS protocol

1. Problem description

1. Problem phenomenon

Sending mail by System.Net.Mail.SmtpClientusing the SSL/TLS protocol fails and reports an error
System.Net.Mail.SmtpException: Failure sending mail

Detailed error information:

System.Net.Mail.SmtpException: Failure sending mail.
 ---> System.IO.IOException: Unable to read data from the transport connection: The connection was closed.
   at System.Net.Mail.SmtpReplyReaderFactory.ProcessRead(Byte[] buffer, Int32 offset, Int32 read, Boolean readLine)
   at System.Net.Mail.SmtpReplyReaderFactory.ReadLines(SmtpReplyReader caller, Boolean oneLine)
   at System.Net.Mail.SmtpReplyReaderFactory.ReadLine(SmtpReplyReader caller)
   at System.Net.Mail.SmtpConnection.GetConnection(String host, Int32 port)
   at System.Net.Mail.SmtpTransport.GetConnection(String host, Int32 port)
   at System.Net.Mail.SmtpClient.GetConnection()
   at System.Net.Mail.SmtpClient.Send(MailMessage message)
   --- End of inner exception stack trace ---
   at System.Net.Mail.SmtpClient.Send(MailMessage message)

2. The cause of the problem

This problem is related to the protocol version of SSL/TLS. After SSL evolved to 3.0, it is still not secure enough. Therefore, an upgraded version of SSL TLS protocol has appeared. Due to the difference when establishing a connection, it is called explicit SSL and implicit SSL respectively. The SSL/TLS protocol is usually paired with SSL/TLS, but people still like to call it SSL for short.

Currently the latest version is TLS 1.3, other available versions are TLS 1.2 and TLS 1.1, of which TLS1.1 is scheduled to be deprecated in 2020

Therefore, the current mainstream email service provider encryption protocols use TLS.
However System.Net.Mail.SmtpClient, the newer TLS protocol is not supported, and no relevant instructions can be found on MSDN for the specific TLS protocol version support

Affected framework versions as of March 2020:

  • .NET Core 2.0-3.1

  • .NET Framework 2.0-4.8

At present, Microsoft MSDN has System.Net.Mail.SmtpClientmarked it as obsolete, but it is not marked in the source code, and no alternative implementation is given.

Two, the solution

1. Use System.Web.Mail

System.Web.Mail.SmtpMailAlthough it has been marked as expired, it supports the new SSL/TLS protocol after all.

However, it should be noted that System.Web.Mail.SmtpMail, only applies to .NET Framework (>=2.0)

Sample code :

using System. Web. Mail;
using System;

namespace Ken.IO.Util {

     class Program
     {
         public static void Main (string[] args)
         {
             MailMessage mmsg = new MailMessage();
             mmsg.Subject = "Mail test subject ken.io";
             mmsg.BodyFormat = MailFormat.Html;
             mmsg.Body = "Mail test body ken.io";
             mmsg.BodyEncoding = Encoding.UTF8;
             //priority
             mmsg.Priority = MailPriority.High;
             // sender email address
             mmsg.From = "[email protected]";
             //recipient inbox address
             mmsg.To = "[email protected]";
             mmsg.Fields.Add("http://schemas.microsoft.com/cdo/configuration/smtpauthenticate", "1");
             //username
             mmsg.Fields.Add("http://schemas.microsoft.com/cdo/configuration/sendusername", mmsg.From);
             //password
             mmsg.Fields.Add("http://schemas.microsoft.com/cdo/configuration/sendpassword", "password");
             //port
             mmsg.Fields.Add("http://schemas.microsoft.com/cdo/configuration/smtpserverport", 465);
             // use SSL
             mmsg.Fields.Add("http://schemas.microsoft.com/cdo/configuration/smtpusessl", "true");
             //Smtp server
             SmtpMail.SmtpServer = "smtp.qq.com";
             SmtpMail.Send(mmsg);
         }
     }
}

2. Use MailKit

MailKit is an open source MimeKit-based cross-platform email sending and receiving class library that supports IMAP, POP3, and SMTP. Among them, SmtpClient also supports the TLS protocol.

Can well support .NET Core and .NET Framework email sending

Install Nuget Packages

#.NET Core
dotnet add package MailKit --version 2.5.1

#.NET Framework
Install-Package MailKit -Version 2.5.1

Sample code :

using System;
using MailKit.Net.Smtp;
using MailKit;
using MimeKit;

namespace Ken.IO.Util {

     class Program
     {
         public static void Main (string[] args)
         {
             var message = new MimeMessage();
             message.From.Add (new MailboxAddress ("test", "[email protected]"));
             message.To.Add (new MailboxAddress ("test", "[email protected]"));
             message.Subject = "Email Test";
             //html or plain
             var bodyBuilder = new BodyBuilder ();
             bodyBuilder.HtmlBody = "<b>Mail test html body ken.io</b>";
             bodyBuilder.TextBody = "Mail test text body ken.io";
             message.Body = bodyBuilder.ToMessageBody();

             using (var client = new SmtpClient ()) {
                 client.ServerCertificateValidationCallback = (s,c,h,e) => true;
                 //smtp server, port, whether to enable ssl
                 client.Connect("smtp.qq.com", 465, true);
                 client.Authenticate("[email protected]", "password");
                 client.Send(message);
                 client. Disconnect (true);
             }
         }
     }
}


3. Remarks

1. Appendix

  • https://www.ruanyifeng.com/blog/2014/02/ssl_tls.html

  • https://docs.microsoft.com/en-us/dotnet/api/system.net.mail.smtpclient

  • https://docs.microsoft.com/en-us/dotnet/api/system.web.mail.smtpmail

  • https://zh.wikipedia.org/wiki/Transport Layer Security Protocol



Tags

Technical otaku

Sought technology together

Related Topic

0 Comments

Leave a Reply

+