2016-08-10 4 views
1

Ich verwende SmtpClient.SendAsync (C#), um E-Mails in ASP.NET-Webanwendungen und -Diensten zu senden. Die Webanwendung/der Dienst wird auf Windows Server 2012 R2 unter Verwendung von IIS 8 ausgeführt.Warum hängt SmtpClient.SendAsync?

Es gibt Zeiten, in denen der Aufruf von SendAsync auflegt und scheint die E-mail-Nachricht nicht asynchron zu senden, so blockiert der aufrufende Thread. Dieses Verhalten scheint sporadisch zu sein. Ich kann das Problem nicht in einer Testumgebung replizieren. Dies ist besonders problematisch, wenn die E-Mail als Ergebnis eines Aufrufs an eine Webmethode gesendet wird, da das Zeitlimit 60 Sekunden beträgt (ich verwende SendAsync aus genau diesem Grund, damit der Client keine Zeitverzögerung erfährt).

Hier ist mein Code-Snippet.

SmtpClient client; 
MailMessage msg; 

public void SendMail() 
{ 
    try 
    { 
     client = new SmtpClient("[email protected]"); 
     msg = new MailMessage(); 
     msg.Subject = "Test"; 
     msg.Body = "This is the body"; 
     msg.From = "[email protected]"; 
     msg.To.Add("[email protected]"); 

     client.SendCompleted += new SendCompletedEventHandler(sendCompletedCallback); 
     client.SendAsync(msg, "Test"); 
    } 
    catch (Exception ex) 
    { 
     // Log error 
    } 
} 

private void sendCompletedCallback(object send, AsyncCompletedEventArgs e) 
{ 
    if (e.Error != null) 
    { 
     // Log error 
    } 
    else if (e.Cancelled) 
    { 
     // Log cancellation 
    } 
    else 
    { 
     // Log success 
    } 

    client.Dispose(); 
    msg.Dispose(); 
} 

Warum der Ruf an SendAsync hängen und den aufrufenden Thread zu Zeiten blockieren?

+1

Das sollte wirklich nicht der Fall sein. Warum sagst du, dass es deinen aufrufenden Thread blockiert? Führen Sie es im 'Release'-Modus aus und sehen Sie, ob es noch blockiert. Bei einem asynchronen Aufruf unterscheidet sich das Verhalten beim Debuggen mithilfe von Haltepunkt. Compiler hinter der Szene macht Sachen, um Ihnen ein Gefühl zu geben, dass Sie eine normale Methode austesten. Mail sendet nicht, könnte ein Problem mit Ihrem SMTP-Server sein. – Rahul

+0

Ich habe ein paar andere Beispiele gefunden, die sich so online verhalten, ohne zufriedenstellende Antwort. Die am häufigsten verwendete Problemumgehung scheint darin zu bestehen, sie in einen Aufruf von 'ThreadPool.QueueUserWorkItem' einzubinden. –

+0

@Rahul Ich weiß, dass es blockiert, weil ich zusätzliche Protokollierung nach dem Aufruf von SendAsync in meinem Webdienst habe und ich sehe diese Protokollmeldungen nicht. Ich werde nur im Freigabemodus zur Produktion bereitstellen. – JT9

Antwort

1

Bitte überprüfen Sie untenstehenden Link, https://msdn.microsoft.com/en-us/library/x5x13z6h(v=vs.110).aspx Es könnte zwei Fall sein, entweder es ist nicht für E-Mail-Übertragung warten, um zu vervollständigen, bevor Sie eine andere E-Mail-Nachricht oder Empfänger senden ist ungültig

+0

Wenn zu meinem Problem beigetragen wurde, warum blockierte der aufrufende Thread, wenn die Nachricht wirklich asynchron gesendet wurde? Ich erstelle jedes Mal, wenn ich eine E-Mail sende, eine neue Instanz der SmtpClient-Klasse. Daher sollte mir vor dem ersten Senden keine weitere Nachricht gesendet werden. Ich erhalte auch keine SmtpException, die ausgelöst werden sollte, wenn einer der Empfänger ungültig ist. – JT9

+0

Wenn Sie über eine GUI verfügen, auf der das Senden von E-Mails eine Wartezeit hat, dann ist es sinnvoll, 'client.SendAsync' zu verwenden, da dies die Benutzeroberfläche nicht einfriert. Für den Fall, dass Sie eine Stapelverarbeitung oder eine Konsolenanwendung verwenden, sehe ich keinen Vorteil bei der Verwendung von 'client.SendAsync'. Sie können die obigen Fälle in Ihrem Code testen. Zumindest MSDN gibt diese Gründe für die Ausnahme. – GauravKP