Skip to main content
 首页 » 编程设计

c#之从 Windows 窗体应用程序发送电子邮件

2024年01月13日31findumars

我正在构建一个应该在远程/隔离机器上运行并通过电子邮件向管理员发送错误通知的 Windows 窗体应用程序。我试过使用 System.Net.Mail 类来实现这一点,但我遇到了一个奇怪的问题:

1. 我收到一条错误消息:

System.IO.IOException: Unable to read data from the transport connection:  
An existing connection was forcibly closed by the remote host.---> 
System.Net.Sockets.SocketException: An existing connection was forcibly closed by  
the remote host at System.Net.Sockets.Socket.Receive(Byte[] buffer, Int32 offset,  
Int32 size, SocketFlags socketFlags) at System.Net.Sockets.NetworkStream. 
Read(Byte[] buffer, Int32 offset, Int32 size) 

2. 我试着嗅探网络事件,看看出了什么问题。事情是这样的:

i) The DNS lookup for my SMTP server's hostname works 
ii) My application connects to the SMTP server and sends "EHLO MY-HOSTNAME" 
iii) SMTP server responds back with it's usual 
iv) My application sends "AUTH login abcdxyz" and receives an acknowledgement packet 

此时,似乎 SMTP 服务器似乎没有请求密码,或者我的机器在 SMTP 服务器可以请求密码之前关闭了与 SMTP 服务器的连接。

我试过使用不同的 SMTP 端口和 SMTP 主机。此外,我尝试禁用我的防火墙和 AV,但没有成功。使用 PuTTY 连接到我的 SMTP 服务器并发出与我的应用程序相同的命令序列(从数据包嗅探器中挑选)时,一切正常,我能够发送电子邮件。

这是我正在使用的代码:

Imports System.Net 
Imports System.Net.Mail 
 
Public Function SendMail() As Boolean 
 
     Dim smtpClient As New SmtpClient("smtp.myserver.com", 587) 'I tried using different hosts and ports 
     smtpClient.UseDefaultCredentials = False 
     smtpClient.Credentials = New NetworkCredential("username@domain.com", "password") 
     smtpClient.EnableSsl = True 'Also tried setting this to false 
 
     Dim mm As New MailMessage 
     mm.From = New MailAddress("username@domain.com") 
     mm.Subject = "Test Mail" 
     mm.IsBodyHtml = True 
     mm.Body = "<h1>This is a test email</h1>" 
     mm.To.Add("someone@domain.com") 
 
     Try 
          smtpClient.Send(mm) 
          MsgBox("SUCCESS!") 
     Catch ex As Exception 
          MsgBox(ex.InnerException.ToString) 
     End Try 
 
     mm.Dispose() 
     smtpClient.Dispose() 
 
     Return True 
 
End Function 

有什么建议吗?

请您参考如下方法:

在 C# 中它是这样工作的:

public partial class MainWindow : Window 
{ 
    public MainWindow() 
    { 
        InitializeComponent(); 
    } 
 
    private void btnTest_Click(object sender, RoutedEventArgs e) 
    { 
        MailAddress from = new MailAddress("Someone@domain.topleveldomain", "Name and stuff"); 
        MailAddress to = new MailAddress("Someone@domain.topleveldomain", "Name and stuff"); 
        List<MailAddress> cc = new List<MailAddress>(); 
        cc.Add(new MailAddress("Someone@domain.topleveldomain", "Name and stuff")); 
        SendEmail("Want to test this damn thing", from, to, cc); 
    } 
 
    protected void SendEmail(string _subject, MailAddress _from, MailAddress _to, List<MailAddress> _cc, List<MailAddress> _bcc = null) 
    { 
        string Text = ""; 
        SmtpClient mailClient = new SmtpClient("Mailhost"); 
        MailMessage msgMail; 
        Text = "Stuff"; 
        msgMail = new MailMessage(); 
        msgMail.From = _from; 
        msgMail.To.Add(_to); 
        foreach (MailAddress addr in _cc) 
        { 
            msgMail.CC.Add(addr); 
        } 
        if (_bcc != null) 
        { 
            foreach (MailAddress addr in _bcc) 
            { 
                msgMail.Bcc.Add(addr); 
            } 
        } 
        msgMail.Subject = _subject; 
        msgMail.Body = Text; 
        msgMail.IsBodyHtml = true; 
        mailClient.Send(msgMail); 
        msgMail.Dispose(); 
    } 
} 

不要忘记 using System.Net.Mail;

我认为在VB中它是这样工作的,这是代码,它可能有一些错误,我不经常在vb.net中写:

Private Sub btnTest_Click(ByVal sender As System.Object, ByVal e As System.Windows.RoutedEventArgs) 
    Dim _from As New MailAddress("Someone@domain.topleveldomain", "Name and stuff") 
    Dim _to As New MailAddress("Someone@domain.topleveldomain", "Name and stuff") 
    Dim cc As New List(Of MailAddress) 
    cc.Add(New MailAddress("Someone@domain.topleveldomain", "Name and stuff")) 
    SendEmail("Wan't to test this thing", _from, _to, cc) 
End Sub 
 
Protected Sub SendEmail(ByVal _subject As String, ByVal _from As MailAddress, ByVal _to As MailAddress, ByVal _cc As List(Of MailAddress), Optional ByVal _bcc As List(Of MailAddress) = Nothing) 
 
    Dim Text As String = "" 
    Dim mailClient As New SmtpClient("Mailhost") 
    Dim msgMail As MailMessage 
    Text = "Stuff" 
    msgMail = New MailMessage() 
    msgMail.From = _from 
    msgMail.To.Add(_to) 
    For Each addr As MailAddress In _cc 
        msgMail.CC.Add(addr) 
    Next 
    If _bcc IsNot Nothing Then 
        For Each addr As MailAddress In _bcc 
            msgMail.Bcc.Add(addr) 
        Next 
    End If 
    msgMail.Subject = _subject 
    msgMail.Body = Text 
    msgMail.IsBodyHtml = True 
    mailClient.Send(msgMail) 
    msgMail.Dispose() 
End Sub 

不要忘记导入 System.Net.Mail