av激情亚洲男人的天堂国语,日韩欧美精品一中文字幕,无码av一区二区三区无码,国产又色又爽又刺激的a片,国产又色又爽又刺激的a片

C#網(wǎng)絡編程系列十:實現(xiàn)簡單的郵件收發(fā)器

引言:在我們的平常工作中,郵件的發(fā)送和接收應該是我們經常要使用到的功能的。因此知道電子郵件的應用程序的原理也是非常有必要的,在這一個專題中將介紹電子郵件應用程序的原理、電子郵件應用程序中涉及的協(xié)議和實現(xiàn)一個簡答的電子郵件收發(fā)器程序。

廬陽ssl適用于網(wǎng)站、小程序/APP、API接口等需要進行數(shù)據(jù)傳輸應用場景,ssl證書未來市場廣闊!成為成都創(chuàng)新互聯(lián)的ssl證書銷售渠道,可以享受市場價格4-6折優(yōu)惠!如果有意向歡迎電話聯(lián)系或者加微信:18982081108(備注:SSL證書合作)期待與您的合作!

一、郵件應用程序基本知識

1.1 電子郵件原理及相關協(xié)議

說到電子郵件的原理,其實和我們現(xiàn)實生活中寄郵件和寄包裹是一樣的原理的。就讓我們先回顧下現(xiàn)實生活中寄郵件的流程吧——首先,我們先寫好信,信封上面寫好收信人的地址,寫信人的地址,然后把信放到寄信箱中,然后郵局的人會某個時候去這個信箱中的信取出來,然后郵局的人根據(jù)信封上寫的收信人地址進行轉發(fā)到當?shù)氐泥]局,當?shù)剜]局然后把信寄到收信人的信箱中(寄包裹的話可能會電話聯(lián)系,像我們在淘寶,京東買的東西的,收貨人就是通過電話聯(lián)系一樣),最后收信人會到自己的信箱中收取信件。上面大致是我們平時生活中寄信的一個流程的。前面已經講過電子郵件的原理和這個差不多的,下面就介紹了本專題中電子郵件的原理,大家可以和現(xiàn)實生活中的寄信過程進行對比下的,這樣可以更加容易理解和掌握:

我們通過電子郵件應用(例如 基于客戶端的Outlook電子郵件軟件 和一些基于Web的電子郵件系統(tǒng)——新浪郵箱、谷歌郵箱、QQ郵箱等都屬于電子郵件應用)將一封寫好的郵件(相當于現(xiàn)實生活中的信,當然郵件也要寫明收件人地址,郵件內容等信息的)通過電子郵件協(xié)議(SMTP,在后面的電子郵件相關協(xié)議中會介紹)發(fā)送到SMTP服務器(就是存儲郵件的地方,相當于生活中的郵局一樣),然后SMTP服務器根據(jù)收件人的地址通過SMTP協(xié)議轉發(fā)到相應SMTP接收服務器上,(SMTP服務器進行轉發(fā)相當于現(xiàn)實生活中郵局的人配送信的過程,配送到收件人當?shù)氐泥]局,然而現(xiàn)實生活中郵局都是一家,所以可以相互識別——意思就是發(fā)送到當?shù)剜]局,當?shù)剜]局會接收,并且?guī)椭惆l(fā)送到指定人的信箱中,在網(wǎng)上上就是通過SMTP協(xié)議來規(guī)定這樣的一個過程的,發(fā)送到別人的SMTP服務器上別人的服務器必須要認識發(fā)送來的郵件并接收)結束,接收端郵件服務器(POP3服務器)把郵件存放到接受者的電子信箱內(相當于當?shù)剜]局的人把信放到收信人的郵箱中),最后收件人可以登錄自己的電子信箱,再與POP3服務器進行連接,從POP3服務器上下載發(fā)送來的郵件,這樣在收件人的電子信箱中就可以看到發(fā)送來的電子郵件了(這就是現(xiàn)實生活中收信人從自己的信箱中取信的一個過程)。

注:括號中都是個人的理解,如果有什么不對的地方還望大家指出來,我好及時更正。

上面已經把電子郵件的原理和現(xiàn)實生活中寄信的過程進行對比,相信大家可以更加清楚電子郵件的原理和發(fā)送接收過程的,其實網(wǎng)絡上的很多應用都可以以現(xiàn)實生活的例子去理解,這樣的話我認為可以加深對知識的理解。下面就介紹下電子郵件中的相關協(xié)議的內容:

網(wǎng)絡上的應用的核心就是協(xié)議,因為協(xié)議讓網(wǎng)絡上的客戶端相互認識發(fā)生來的數(shù)據(jù),所以電子郵件應用也不例外,也有相關的電子郵件協(xié)議來完成發(fā)送電子郵件和接收電子郵件的過程,這些協(xié)議主要是:SMTP(簡單郵件傳輸協(xié)議,Simple Mail Transfer Protocol)、POP3(郵局協(xié)議,Post Office Protocol)和IMAP(網(wǎng)絡郵件訪問協(xié)議,Internet Message Access Protocol)。

SMTP——SMTP 主要負責將郵件從一臺機器轉發(fā)至另一臺機器(可以對照上面電子郵件的過程來理解SMTP的作用)

POP3——3表示POP協(xié)議的版本,主要負責將郵件從郵箱中(POP3服務器)傳輸?shù)奖镜赜嬎銠C。

IMAP——現(xiàn)在常用的版本為第四版本,即IMAP4,主要負責郵件的檢索和處理功能,客戶端不需要下載郵件到本地計算機,可直接從郵件客戶端軟件對服務器上的信件和文件目錄進行操作,它是POP3的替代協(xié)議的。

1.2 郵件系統(tǒng)的分類

郵件系統(tǒng)主要分為兩類的——基于客戶端的郵件系統(tǒng)和基于Web瀏覽器的郵件系統(tǒng)。Office OutLook就是基于客戶端的郵件客戶端系統(tǒng),而像我們經常使用的QQ郵箱、新浪、網(wǎng)易郵箱等都是屬于基于Web瀏覽器的郵件系統(tǒng),基于客戶端的郵件系統(tǒng)的收發(fā)過程,通過下面的圖片來描述(圖片從網(wǎng)上摘下的):

圖 1.1 基于客戶端的郵件收發(fā)過程

發(fā)送方通過郵件客戶端,將編輯好的郵件向郵件服務(SMTP服務器,在發(fā)送過程中也叫發(fā)送端郵件服務器)發(fā)送,發(fā)送端郵件服務器根據(jù)收件人的地址來識別接收端郵件服務器(POP3服務器),然后向POP3服務器發(fā)送郵件信息,接收端郵件服務器將郵件存放在接收者的電子信箱中,并告知接收者有新郵件,接收者通過郵件客戶端與POP3服務器連接后,就可以查看新郵件。

然而,基于Web瀏覽器的郵件系統(tǒng)與基于客戶端的郵件系統(tǒng)不同的地方有:

基于Web瀏覽器郵件系統(tǒng)用戶代理(代理的概念也就是用戶不是直接與服務器進行通信,而是通過代理的方式,讓代理去與服務器通信,然后用戶在從代理中獲的服務器的信息,代理也就是中間人的作用,相當于生活中中介,在.net中很多技術都用到了代理,例如委托的概念其實也就是代理的一個概念的)是Web瀏覽器,基于客戶端的郵件系統(tǒng)而是郵件客戶端應用程序,一般是Windows Form程序。

瀏覽器發(fā)送郵件到SMTP服務器和從POP3服務器中獲得郵件的方式都是通過HTTP協(xié)議來實現(xiàn),與基于客戶端的郵件系統(tǒng)不同(基于客戶端的郵件系統(tǒng)發(fā)送通過SMTP協(xié)議或ESMTP(Extended SMTP),獲得通過POP3或IMAP協(xié)議)。

1.3 目前主要的電子郵件服務系統(tǒng)

電子郵件服務系統(tǒng)——就是向大家提供郵箱服務的服務系統(tǒng),這樣的系統(tǒng)當然是由專門的公司進行研發(fā)的,我們一般叫這樣的公司為郵件服務商,我們平常使用的網(wǎng)易郵箱,新、Gmail郵箱等都是建立在電子郵件服務系統(tǒng)(這里我的理解是——我們使用的新浪,網(wǎng)易等郵箱相當于現(xiàn)實生活中每個人的信箱,通過信箱可以獲得郵局來的信,同樣道理通過郵箱可以獲得郵件服務系統(tǒng)的郵件,這樣電子郵件系統(tǒng)相當于郵局) ?,F(xiàn)在主要電子郵件服務系統(tǒng)主要有下面幾種:

基于Postfix/Qmail的郵件系統(tǒng)。例如,雅虎郵箱基于Qmail系統(tǒng)

微軟Exchange 郵件系統(tǒng)

IBM Lotus Domino郵件系統(tǒng)

Scalix郵件系統(tǒng)

Zimbra郵件系統(tǒng)

MDeamon郵件系統(tǒng)

二、.Net 平臺對郵件發(fā)送功能的支持

在.NET類庫中,在System.Net.Mail命名空間下定義了對郵件處理的類,這樣使郵件的發(fā)送更加方便(這些類也就是對SMTP協(xié)議的封裝,使我們更好地區(qū)編程,只需要使用類中的方法和屬性等去完成郵件的發(fā)送,避免寫復雜的SMTP協(xié)議的命令),下面是一張在System.Net.Mail命名空間下對郵件發(fā)送的支持的類截圖:

從圖片中類的名字中也可以看出每個類的作用的,在這里我就不一個介紹的, 大家可以參考MSDN去看每個類的使用,并且我在后面程序的實現(xiàn)部分也會有詳細的注釋去介紹程序中使用到類的使用。從圖中還可以i看出一點——就是只有SMTP的字樣,卻沒有POP3這樣的字樣的,這說明.Net類庫本身中并沒有提供對POP3協(xié)議的封裝類,但是我們可以使用Jmail組件來完成從POP3服務器中收取郵件的功能,具體的使用將在后面的郵件收發(fā)器程序中郵件的接收部分介紹的。

三、郵件收發(fā)器程序的實現(xiàn)

3.1 郵件發(fā)送功能的實現(xiàn)

3.1.1 SMTP協(xié)議

SMTP 協(xié)議是用于電子郵件的傳輸?shù)膮f(xié)議,電子郵件是通過SMTP服務器進行發(fā)送的,SMTP服務器的默認端口為25,通常發(fā)送郵件有兩種方式——一種是不使用客戶端認證,即客戶端可以使用匿名發(fā)送郵件(這種方式叫做SMTP);另一種是客戶端必須提供用戶名和密碼認證(這種方式叫做ESMTP,Extended SMTP)目前大部分郵件服務器采用用戶名和密碼認證的方式。

客戶端發(fā)送郵件過程為——先通過客戶端軟件(本程序中的郵件收發(fā)器)將郵件發(fā)送到SMTP服務器,然后再由SMTP服務器發(fā)送到目標SMTP服務器。下面介紹SMTP協(xié)議的內容:

SMTP協(xié)議總共定義了14個命令,命令由命令碼和氣候的參數(shù)域組成, 不區(qū)別大小寫的(通過前面專題的講述可以得出各個協(xié)議的命令組成都差不多的),下面就簡單介紹下5個常用的命令碼

電子郵件由信封、首部、正文和結束符號4部分組成,下面就具體介紹下這4個部分的內容:

1. 信封

信封包括發(fā)信人的郵件地址和接收人的郵件地址,具體對應兩條SMTP命令——Mail from: [email protected](發(fā)信人的地址)和Rcpt to:  [email protected]

2. 首部

首部中常用的命令有:

Subject:<郵件主題>——表示郵件的主題

Date:<時間>——表示發(fā)郵件的時間

reply-to:<郵件地址>——表示郵件的回復地址

Content-Type:<郵件類型>——表示郵件包含文本、HTML超文本和附件的類型。

X-Priority:<郵件優(yōu)先級>——表示郵件發(fā)送的優(yōu)先級,優(yōu)先級為3表示為普通郵件;如 X-Priority:3

3. 正文

正文當然指的就是郵件的內容了, 用Data命令指定,首部以一個空行結束,下面就是正文部分

4. 結束符號

郵件以“."結束,

接收方收到SMTP命令之后,會給出一個響應碼,每個命令都只有一個響應碼,SMTP響應碼也是由3位數(shù)字組成,后面附加一些文本信息,響應信息的格式為:

響應碼<空格>文本信息<回車換行>

客戶端發(fā)出一條命令后,服務器端返回一個響應,發(fā)送者在發(fā)送下一條命令前必須等待服務器的響應,成功接收到響應碼后才繼續(xù)發(fā)送命令。

附:SMTP常用的響應碼:

 

3.1.2 郵件的發(fā)送過程

第一步:客戶端與服務器建立連接(該步中客戶端首先發(fā)送EHLO local 連接命令,服務器如果返回“220”響應碼表示服務器準備就緒了,客戶端再繼續(xù)發(fā)送“Auto login”命令,請求登錄,服務器收到命令后返回“334”響應碼,表示要輸入用戶名,之后客戶端發(fā)送用戶名命令,等到響應后再發(fā)送密碼命令,具體在程序的實現(xiàn)中也會有注釋。)

第二步:客戶端發(fā)送郵件的信封

第三步:開始發(fā)送郵件數(shù)據(jù),(包括郵件首部,正文和結束符號,注:結束符號要單獨占一行,表示郵件發(fā)送結束)

第四步: 客戶端與服務器斷開連接。

3.1.3 發(fā)送功能的實現(xiàn)代碼

相信有了上面的理論解釋郵件發(fā)送的過程后,實現(xiàn)郵件發(fā)送的功能并不難的,并且.net類庫中SMTPClient類幫我們封裝了SMTP協(xié)議,使得我們實現(xiàn)郵件發(fā)送功能就不要記住那些具體的命令了, 只需要使用該類中提供的方法來完成郵件的發(fā)送(當然你也可以通過發(fā)送命令的方式實現(xiàn),SMTPClient類的方法也是幫我們完成發(fā)送命令功能而已的),下面是郵件發(fā)送功能的核心代碼:

 
 
 
 
  1. View Code 
  2.  #region 郵件發(fā)送功能代碼
  3.          // 添加附件
  4.          private void btnAddFile_Click(object sender, EventArgs e)
  5.          {
  6.              OpenFileDialog openFileDialog = new OpenFileDialog();
  7.              openFileDialog.CheckFileExists = true;
  8.              // 只接受有效的文件名
  9.              openFileDialog.ValidateNames = true;
  10.              // 允許一次選擇多個文件作為附件
  11.              openFileDialog.Multiselect = true;
  12.              openFileDialog.Filter = "所有文件(*.*)|*.*";
  13.              if (openFileDialog.ShowDialog() != DialogResult.OK)
  14.              {
  15.                  return;
  16.              }
  17.              if (openFileDialog.FileNames.Length > 0)
  18.              {
  19.                  // 因為這里允許選擇多個文件,所以這里用AddRange而沒有用Add方法
  20.                  cmbAttachment.Items.AddRange(openFileDialog.FileNames);
  21.              }
  22.          }
  23.  
  24.          // 刪除附件
  25.          private void btnDeleteFile_Click(object sender, EventArgs e)
  26.          {
  27.              int index = cmbAttachment.SelectedIndex;
  28.              if (index == -1)
  29.              {
  30.                  MessageBox.Show("請選擇要刪除的附件!", "提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
  31.                  return;
  32.              }
  33.              else
  34.              {
  35.                  cmbAttachment.Items.RemoveAt(index);
  36.              }
  37.          }
  38.  
  39.          // 發(fā)送郵件
  40.          private void btnSend_Click(object sender, EventArgs e)
  41.          {
  42.              this.Cursor = Cursors.WaitCursor;
  43.              // 實例化一個發(fā)送的郵件
  44.              // 相當于與現(xiàn)實生活中先寫信,程序中把信(郵件)抽象為郵件類了
  45.              MailMessage mailMessage = new MailMessage();
  46.              // 指明郵件發(fā)送的地址,主題,內容等信息
  47.              // 發(fā)信人的地址為登錄收發(fā)器的地址,這個收發(fā)器相當于我們平時Web版的郵箱或者是OutLook中配置的郵箱
  48.              mailMessage.From = new MailAddress(tbxUserMail.Text);
  49.              mailMessage.To.Add(txbSendTo.Text);
  50.              mailMessage.Subject = txbSubject.Text;
  51.              mailMessage.SubjectEncoding = Encoding.Default;
  52.              mailMessage.Body = richtbxBody.Text;
  53.              mailMessage.BodyEncoding = Encoding.Default;
  54.              // 設置郵件正文不是Html格式的內容
  55.              mailMessage.IsBodyHtml = false;
  56.              // 設置郵件的優(yōu)先級為普通優(yōu)先級
  57.              mailMessage.Priority = MailPriority.Normal;
  58.              //mailMessage.ReplyTo = new MailAddress(tbxUserMail.Text);
  59.  
  60.              // 封裝發(fā)送的附件
  61.              System.Net.Mail.Attachment attachment = null;
  62.              if (cmbAttachment.Items.Count > 0)
  63.              {
  64.                  for (int i = 0; i < cmbAttachment.Items.Count; i++)
  65.                  {
  66.                      string fileNamePath = cmbAttachment.Items[i].ToString();
  67.                      string extName = Path.GetExtension(fileNamePath).ToLower();
  68.                      if (extName == ".rar" || extName == ".zip")
  69.                      {
  70.                          attachment = new System.Net.Mail.Attachment(fileNamePath, MediaTypeNames.Application.Zip);
  71.                      }
  72.                      else
  73.                      {
  74.                          attachment = new System.Net.Mail.Attachment(fileNamePath,MediaTypeNames.Application.Octet);
  75.                      }
  76.  
  77.                      // 表示MIMEContent-Disposition標頭信息
  78.                      // 對于ContentDisposition具體類的解釋大家可以參考MSDN
  79.                      // 這里我就不重復貼出來了,給個地址: http://msdn.microsoft.com/zh-cn/library/System.Net.Mime.ContentDisposition.aspx (著重看備注部分)
  80.                      ContentDisposition cd = attachment.ContentDisposition;
  81.                      cd.CreationDate = File.GetCreationTime(fileNamePath);
  82.                      cd.ModificationDate = File.GetLastWriteTime(fileNamePath);
  83.                      cd.ReadDate = File.GetLastAccessTime(fileNamePath);
  84.                      // 把附件對象加入到郵件附件集合中
  85.                      mailMessage.Attachments.Add(attachment);
  86.                  }
  87.              }
  88.  
  89.              // 發(fā)送寫好的郵件
  90.              try
  91.              {
  92.                  // SmtpClient類用于將郵件發(fā)送到SMTP服務器
  93.                  // 該類封裝了SMTP協(xié)議的實現(xiàn),
  94.                  // 通過該類可以簡化發(fā)送郵件的過程,只需要調用該類的Send方法就可以發(fā)送郵件到SMTP服務器了。
  95.                  smtpClient.Send(mailMessage);
  96.                  MessageBox.Show("郵件發(fā)送成功!", "提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
  97.  
  98.              }
  99.              catch(SmtpException smtpError)
  100.              {
  101.                  MessageBox.Show("郵件發(fā)送失敗:[" + smtpError.StatusCode + "];[" 
  102.                      + smtpError.Message+"];\r\n["+smtpError.StackTrace+"]."
  103.                      ,"錯誤",MessageBoxButtons.RetryCancel,MessageBoxIcon.Error);
  104.              }
  105.              finally
  106.              {
  107.                  mailMessage.Dispose();
  108.                  this.Cursor = Cursors.Default;
  109.              }
  110.          }
  111.  
  112.          #endregion

3.2 郵件接收功能的實現(xiàn)

3.2.1 POP3協(xié)議

前面介紹了郵件的發(fā)送,當然接收者需要登錄郵箱來查看收到的郵件了,此時就必有有一個協(xié)議去讀取服務器上郵件,POP3就是這樣的一個協(xié)議。還有兩外一種協(xié)議也是用來接收郵件的——IMAP協(xié)議,它與POP3協(xié)議區(qū)別有:

1. IMAP使用的端口號是143而POP3郵件服務器通過監(jiān)聽110端口來提供POP3服務;

2 . IMAP 允許客戶端在郵件服務器上建立文件夾來保持郵件,而不用把郵件下載到本地。而POP3需要把郵件下載到本地。

和SMTP協(xié)議一樣,客戶端要通過POP3協(xié)議從POP3服務器上獲取郵件,也需要先與POP3服務器建立TCP連接,等待服務器向客戶端發(fā)送確認信息表明連接成功時,客戶端才可以繼續(xù)發(fā)送命令給服務器來獲取郵件,在POP3協(xié)議中,規(guī)定的命令也是幾十條的,每條命令由命令和參數(shù)兩部分組成,都是以回車換行結束,并且命令和參數(shù)之間由空格分隔,命令通常也是由3-4個字母組成,參數(shù)最多可以為40個字符的長度,而服務器的響應信息是由一個狀態(tài)碼和可能附加信息的字符組成,所有的響應信息也是以回車換行結束的。狀態(tài)碼和其他協(xié)議定義的狀態(tài)碼有點不一樣,POP3服務器響應的狀態(tài)碼有兩種——“+OK”(確定)和"-ERR"(失?。_@樣客戶端可以通過檢查響應的狀態(tài)碼所包含的字符來判斷服務器是否響應客戶端發(fā)送的命令,即響應信息中包含“+OK”表示成功響應,包含“-ERR”表示服務器未響應。同時在程序的實現(xiàn)中大家可以通過Debug來查看響應消息的組成,這樣可以加深理解。

3.2.2 郵件接收的過程

客戶端從服務器接收郵件的過程主要經歷3個狀態(tài):授權狀態(tài)、操作狀態(tài)和更新狀態(tài)

(1)授權狀態(tài)——客戶端發(fā)送與POP3服務器的TCP連接請求,服務器接收后發(fā)送一個響應確認信息之后,此時客戶端需要發(fā)送正確的用戶名和密碼進行確認,因為在郵件服務器上有很多用戶郵箱,只有提供正確的用戶名和密碼才有權限訪問自己的郵箱,就像現(xiàn)實生活中我們郵箱的鑰匙一樣的。

發(fā)送用戶名命令: USER [email protected]

發(fā)送密碼命令: PASS ******(這兩個命令都在代碼中有給出的,大家可以參考代碼來理解郵件的接收過程)

(2) 操作狀態(tài)——如果客戶端提供了正確的用戶名和密碼,則授權狀態(tài)也就通過了,就相當于打開了在服務器上自己的郵箱,現(xiàn)在用戶就有權限進去下載,查看和刪除郵件等操作的,然后在現(xiàn)實生活中的取郵件和刪除郵件都很簡單(只要打開了郵箱門,用手去拿就可以了),然后在網(wǎng)絡應用上,這些操作都需要發(fā)送POP3命令給服務器,服務器接收到命令后再給出響應。操作中常用的命令有:

STAT 命令——該命令從服務器中獲取郵件總數(shù)和總字節(jié)數(shù),服務器響應命令返回郵件總數(shù)和總字節(jié)數(shù)。如:

 
 
 
 
  1. 客戶端發(fā)送POP3命令: STAT 
  2. 服務器響應命令: +OK 2 1340
    服務器響應命令:

LIST 命令——該命令從服務器中獲得郵件列表和大小,服務器響應命令返回列出郵件列表和大小。如:

 
 
 
 
  1. 客戶端發(fā)送POP3命令:LIST 
  2. 服務器響應命令: +OK 2 message(1430 octect) 
  3. 服務器響應命令:1    700 
  4. 服務器響應命令:2    730 
  5. 服務器響應命令:<一個空行>

RETR 命令—— 該命令從服務器中獲得一個郵件,格式為 RETR <郵件編號>如:

 
 
 
 
  1. 客戶端發(fā)送POP3命令:RETR 1 
  2. 服務器響應命令: 700 octets 
  3. 服務器響應命令:<郵件頭和內容> 
  4. 服務器響應命令: <空行>

DELETE 命令——該命令告訴服務器將郵件標記為刪除。(此時只是邏輯刪除)

(3)更新狀態(tài)——客戶端發(fā)送QUIT命令后,此時就進入更新狀態(tài),POP3服務器釋放在操作狀態(tài)中取得的資源,并將邏輯刪除的郵件進行物理刪除,然后關閉與客戶端的TCP連接。這樣整個郵件處理的過程就結束了。

3.2.3 接收功能的實現(xiàn)代碼

有了前面接收郵件過程的介紹,再參考代碼的實現(xiàn),相信大家可以更好的理解客戶端從POP3服務器中獲取郵件的過程的,由于.net類庫并沒有幫我們封裝POP3協(xié)議的實現(xiàn)類,要實現(xiàn)郵件的獲取可以采用發(fā)送命令的方式,也可以使用Jmail組件,這個組件其實就是POP3協(xié)議的封裝類,既然微軟沒有幫我們做,其他公司幫我們做好后來幫助我們簡單的實現(xiàn)郵件的接收的一個類庫罷了。然后在使用這個組件的過程中出現(xiàn)了好幾個問題的,在源碼中我都解釋,大家可以下載源代碼后查看的。

實現(xiàn)郵件接收的核心代碼如下:

 
 
 
 
  1. // 登錄郵箱(這里是本程序——郵件收發(fā)器)
  2.        private void btnLogin_Click_1(object sender, EventArgs e)
  3.        {
  4.            // 與POP3服務器建立TCP連接
  5.            // 建立連接后把服務器上的郵件下載到本地
  6.            // 設置當前界面的光標為等待光標(就是我們看到的一個動的圓形)
  7.            Cursor.Current = Cursors.WaitCursor;
  8.            lsttbxStatus.Items.Clear();
  9.            try
  10.            {
  11.                // POP3服務器通過監(jiān)聽TCP110端口來提供POP3服務的
  12.                // 向POP3服務器發(fā)出tcp請求
  13.                tcpClient = new TcpClient(tbxPOP3Server.Text, 110);
  14.                lsttbxStatus.Items.Add("正在連接...");
  15.            }
  16.            catch
  17.            {
  18.                MessageBox.Show("連接失敗", "錯誤", MessageBoxButtons.RetryCancel, MessageBoxIcon.Error);
  19.                lsttbxStatus.Items.Add("連接失?。?);
  20.                return;
  21.            }
  22.            // 連接成功的情況
  23.            networkStream = tcpClient.GetStream();
  24.            streamReader = new StreamReader(networkStream, Encoding.Default);
  25.            streamWriter = new StreamWriter(networkStream, Encoding.Default);
  26.            streamWriter.AutoFlush = true;
  27.            string str;
  28.            // 讀取服務器返回的響應連接信息
  29.            str = GetResponse();
  30.            if (CheckResponse(str) == false)
  31.            {
  32.                lsttbxStatus.Items.Add("服務器拒接了連接請求");
  33.                return;
  34.            }
  35.            // 如果服務器接收請求
  36.            // 向服務器發(fā)送憑證——用戶名和密碼
  37.            // 向服務器發(fā)送用戶名,請求確認
  38.            lsttbxStatus.Items.Add("核實用戶名階段...");
  39.            SendToServer("USER " + tbxUserMail.Text);
  40.            str = GetResponse();
  41.            if (CheckResponse(str) == false)
  42.            {
  43.                lsttbxStatus.Items.Add("用戶名錯誤.");
  44.                return;
  45.            }
  46.            // 用戶名審核通過后再發(fā)送密碼等待確認
  47.            // 向服務器發(fā)送密碼,請求確認
  48.            SendToServer("PASS "+txbPassword.Text);
  49.            str = GetResponse();
  50.            if (CheckResponse(str) == false)
  51.            {
  52.                lsttbxStatus.Items.Add("密碼錯誤!");
  53.                return;
  54.            }
  55.            lsttbxStatus.Items.Add("身份驗證成功,可以開始會話");
  56.            // 向服務器發(fā)送LIST 命令,請求獲得郵件列表和大小
  57.            lsttbxStatus.Items.Add("獲取郵件....");
  58.            SendToServer("LIST");
  59.            str = GetResponse();
  60.            if (CheckResponse(str) == false)
  61.            {
  62.                lsttbxStatus.Items.Add("獲取郵件列表失敗");
  63.                return;
  64.            }
  65.            lsttbxStatus.Items.Add("郵件獲取成功");
  66.            // 窗口控件控制
  67.            tabControlMyMailbox.Enabled = true;
  68.            btnReadMail.Enabled = false;
  69.            btnDownLoad.Enabled = false;
  70.            btnDeleteMail.Enabled = false;
  71.            // 登陸成功后實例化郵件發(fā)送對象,以便后面完成發(fā)送郵件的操作
  72.            // 實例化郵件發(fā)送類(SmtpClient)對象
  73.            if (smtpClient == null)
  74.            {
  75.                smtpClient = new SmtpClient();
  76.                smtpClient.Host = tbxSmtpServer.Text;
  77.                smtpClient.Port = 25;
  78.                    
  79.                // 不使用默認憑證,即需要認證登陸
  80.                smtpClient.UseDefaultCredentials = false;
  81.                smtpClient.Credentials = new NetworkCredential(tbxUserMail.Text, txbPassword.Text);
  82.                smtpClient.DeliveryMethod = SmtpDeliveryMethod.Network;
  83.            }
  84.            // 登陸成功后,自動接收新郵件
  85.            // 開始接收郵件
  86.            try
  87.            {
  88.                btnRefreshMailList.PerformClick();
  89.            }
  90.            catch
  91.            {
  92.                MessageBox.Show("讀取郵件列表失敗!", "錯誤", MessageBoxButtons.RetryCancel, MessageBoxIcon.Error);
  93.            }
  94.            lsttbxStatus.Items.Add("登陸成功!");
  95.            lsttbxStatus.TopIndex = lsttbxStatus.Items.Count - 1;
  96.            Cursor.Current = Cursors.Default;
  97.            // 窗口控件控制
  98.            richtbxMailContentReview.Enabled = true;
  99.            tbxUserMail.Enabled = false;
  100.            txbPassword.Enabled = false;
  101.            btnLogin.Enabled = false;
  102.            btnLogout.Enabled = true;
  103.            tbxSmtpServer.Enabled = false;
  104.            tbxPOP3Server.Enabled = false;
  105.            btnReadMail.Enabled = true;
  106.            btnDownLoad.Enabled = true;
  107.            btnDeleteMail.Enabled = true;
  108.            tabControlMyMailbox.Focus();
  109.        }
  110.        #region 處理與POP3服務器交互事件
  111.        // 獲取服務器響應的信息
  112.        private string GetResponse()
  113.        {
  114.            string str = null;
  115.            try
  116.            {
  117.                str = streamReader.ReadLine();
  118.                if (str == null)
  119.                {
  120.                    lsttbxStatus.Items.Add("連接失敗——服務器沒有響應");
  121.                }
  122.                else
  123.                {
  124.                    lsttbxStatus.Items.Add("收到:[" + str + "]");
  125.                    if (str.StartsWith("-ERR"))
  126.                    {
  127.                        str = null;
  128.                    }
  129.                }
  130.            }
  131.            catch(Exception err)
  132.            {
  133.                lsttbxStatus.Items.Add("連接失敗:[" + err.Message + "]");
  134.            }
  135.            return str;
  136.        }
  137.        // 檢查響應信息
  138.        private bool CheckResponse(string responseString)
  139.        {
  140.            if (responseString == null)
  141.            {
  142.                return false;
  143.            }
  144.            else
  145.            {
  146.                if (responseString.StartsWith("+OK"))
  147.                {
  148.                    return true;
  149.                }
  150.                else
  151.                {
  152.                    return false 網(wǎng)站欄目:C#網(wǎng)絡編程系列十:實現(xiàn)簡單的郵件收發(fā)器
    URL分享:http://uogjgqi.cn/article/dpeeseh.html
掃二維碼與項目經理溝通

我們在微信上24小時期待你的聲音

解答本文疑問/技術咨詢/運營咨詢/技術建議/互聯(lián)網(wǎng)交流