简体   繁体   中英

SMTP via .Net C# Web application - second email not sending on production server

We have a C# ASP.Net project which sends an email through SMTP.
We have a normal password recovery cycle, two emails are sent. The first one has an access code to recover password, the second one returns a temporary password.

When the user requests his lost password, this email is always received. Then the user then clicks on a link in the email, enters a code and a second email should be sent. The first email is always received.

The second email is always received in our development environment but only received intermittently in our deployed version. (Webdrive server)

The second email uses the same mail configuration. It is a mail message object where we call the send method. We do not get any error messages. We've considered that it could be being treated as spam but ..... Any ideas?

The emails run on a separate thread. The two emails are sent asynchronously.

The email web.config settinga are:

<mailSettings>
      <smtp deliveryMethod="Network" from="info@mysite.com">
        <network host="smtp.webhost.co.nz"
                     defaultCredentials="false"
                     enableSsl="true"
                     password="password"
                     port="587"
                     userName="info@mysite.com"/>
     </smtp>
    </mailSettings>

Here's the code:

public bool SendEMailTempPass(string EmailRecipients, string Subject, string Body, bool isHTML = true)
        {
            try
            {
                var sendMailThreadPass = new Thread(() =>
                {
                    System.Net.Configuration.SmtpSection smtpSettings = new System.Net.Configuration.SmtpSection();
                    System.Net.Mail.SmtpClient smtp = new System.Net.Mail.SmtpClient();//settings.Smtp.Network.Host);
                    string strFrom = ConfigurationManager.AppSettings["Mailto"];
                    MailMessage mailObj = new MailMessage(strFrom, EmailRecipients, Subject, Body);
                    mailObj.IsBodyHtml = isHTML;
                    smtp.SendCompleted += new SendCompletedEventHandler(PassChangeEmail_SendCompleted);

                    smtp.SendAsync(mailObj, null);
                });

                sendMailThreadPass.Start();

            }
            catch (Exception ex)
            {
                ErrorMessage = ex.Message;
                return false;
            }
            ErrorMessage = "";
            return true;
        }

        void PassChangeEmail_SendCompleted(object sender, AsyncCompletedEventArgs e)
        {
            if (e.Cancelled)
            { }
            else if (e.Error != null)
            {
                ErrorMessage = e.Error.ToString();
                EmailStatus = 0;
            }
            else
            {
                ErrorMessage = "";
                SuccessMessage = "Thank you.  We will be in touch!";
                EmailStatus = 1;
            }
        }

This is how it gets called:

string body = PassResetEmail.PopulateBodyPassReset(this.Name + " " + this.Lastname,                                                                               LinkURL,PicURL, NewPassword, strPassResetEmailTemplate);

PassResetEmail.SendEMailTempPass(this.Email, "Change your temporary password", body, true);

I tested it with a google account and we had the same issue: the first email gets sent and the second rarely makes it through.

Any ideas on where to look at or what to look at?

At first we thought it could have been some sort of spam filter but it seems to be the same with two different providers.

The other thing is that it works perfectly on our local environment, even with the same mail provider settings.

Any ideas would be much appreciatted!

Thanks!

I've had issues with SendAsync masking the actual errors - I can't recall the exact scenario but I replaced it with my own asynchronous call using the ThreadPool:

Replace your call to smtp.SendAsync(mailObj, null); with

ThreadPool.QueueUserWorkItem(SendEmail, new EmailPair { Client = client, Email = message });

you'll need the following helper class and the actual method that sends the Email:

public class EmailPair
{
    public SmtpClient Client { get; set; }
    public MailMessage Email { get; set; }
}

public static void SendEmail(object state)
{
    var pair = (EmailPair) state;
    try
    {
        pair.Client.Send(pair.Email);
    }
    catch (Exception e)
    {
        Log.Error(e);
    }
}

You really need to log ALL the exceptions of e (make sure e.InnerException is being logged properly so you can see what is going on)

You probably need to get your friendly network guy involved to see if he can see what actually hits the mail server.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM