C# - IMAP Class

This code snippet demonstrates a simple IMAP class that can connect to an IMAP email server and get messages.

Usage

  1. using System;  
  2. using System.Collections.Generic;  
  3. using System.Linq;  
  4. using System.Text;  
  5.  
  6. namespace ImapDemo  
  7. {  
  8.     class Program  
  9.     {  
  10.         static void Main(string[] args)  
  11.         {  
  12.             /* Connect to gmail using ssl. */  
  13.             Imap imap = new Imap("imap.gmail.com", 993, true);  
  14.  
  15.             /* Authenticate using google email and password /*  
  16.             imap.Authenicate("user""password");  
  17.  
  18.             /* Get a list of folders /*  
  19.             var folders = imap.GetFolders();  
  20.  
  21.             /* Select a mailbox /*  
  22.             imap.SelectFolder("INBOX");  
  23.  
  24.             /* Get message using UID /*  
  25.             /* Second parameter is section type. e.g Plain text or HTML /*  
  26.             Console.WriteLine(imap.GetMessage("UID message number""1"));  
  27.  
  28.             /* Get message using index /*  
  29.             Console.WriteLine(imap.GetMessage(1, "1"));  
  30.  
  31.             /* Get total message count /*  
  32.             Console.WriteLine(imap.GetMessageCount());  
  33.  
  34.             /* Get total unseen message count /*  
  35.             Console.WriteLine(imap.GetUnseenMessageCount());  
  36.  
  37.             Console.ReadKey();  
  38.         }  
  39.     }  
  40. } 

Imap.cs

  1. using System;  
  2. using System.Collections.Generic;  
  3. using System.Linq;  
  4. using System.Text;  
  5. using System.Text.RegularExpressions;  
  6. using System.Net;  
  7. using System.Net.Sockets;  
  8. using System.Net.Security;  
  9. using System.IO;  
  10.  
  11.  
  12. class Imap  
  13. {  
  14.     protected TcpClient _tcpClient;  
  15.     protected StreamReader _reader;  
  16.     protected StreamWriter _writer;  
  17.  
  18.     protected string _selectedFolder = string.Empty;  
  19.     protected int _prefix = 1;  
  20.  
  21.     public Imap(string host, int port, bool ssl = false)  
  22.     {  
  23.         try  
  24.         {  
  25.             _tcpClient = new TcpClient(host, port);  
  26.  
  27.             if (ssl)  
  28.             {  
  29.                 var stream = new SslStream(_tcpClient.GetStream());  
  30.                 stream.AuthenticateAsClient(host);  
  31.  
  32.                 _reader = new StreamReader(stream);  
  33.                 _writer = new StreamWriter(stream);  
  34.             }  
  35.             else  
  36.             {  
  37.                 var stream = _tcpClient.GetStream();  
  38.                 _reader = new StreamReader(stream);  
  39.                 _writer = new StreamWriter(stream);  
  40.             }  
  41.  
  42.             string greeting = _reader.ReadLine();  
  43.         }  
  44.         catch(Exception e){  
  45.             Console.WriteLine(e.Message);  
  46.         }  
  47.     }  
  48.  
  49.     public void Authenicate(string user, string pass)  
  50.     {  
  51.         this.SendCommand(string.Format("LOGIN {0} {1}", user, pass));  
  52.         string response = this.GetResponse();  
  53.     }  
  54.  
  55.     public List<stringGetFolders()  
  56.     {  
  57.         this.SendCommand("LIST \"\" *");  
  58.         string response = this.GetResponse();  
  59.  
  60.         string[] lines = response.Split(new string[] { Environment.NewLine }, StringSplitOptions.RemoveEmptyEntries);  
  61.         List<string> folders = new List<string>();  
  62.  
  63.         foreach (string line in lines)  
  64.         {  
  65.             MatchCollection m = Regex.Matches(line, "\\\"(.*?)\\\"");  
  66.  
  67.             if (m.Count > 1)  
  68.             {  
  69.                 string folderName = m[m.Count - 1].ToString().Trim(new char[] { '"' });  
  70.                 folders.Add(folderName);  
  71.             }  
  72.         }  
  73.  
  74.         return folders;  
  75.     }  
  76.  
  77.     public void SelectFolder(string folderName)  
  78.     {  
  79.         this._selectedFolder = folderName;  
  80.         this.SendCommand("SELECT " + folderName);  
  81.         string response = this.GetResponse();  
  82.     }  
  83.  
  84.     public int GetMessageCount()  
  85.     {  
  86.         this.SendCommand("STATUS " + this._selectedFolder + " (messages)");  
  87.         string response = this.GetResponse();  
  88.         Match m = Regex.Match(response, "[0-9]*[0-9]");  
  89.         return Convert.ToInt32(m.ToString());  
  90.     }  
  91.  
  92.     public int GetUnseenMessageCount()  
  93.     {  
  94.         this.SendCommand("STATUS " + this._selectedFolder + " (unseen)");  
  95.         string response = this.GetResponse();  
  96.         Match m = Regex.Match(response, "[0-9]*[0-9]");  
  97.         return Convert.ToInt32(m.ToString());  
  98.     }  
  99.  
  100.     public string GetMessage(string uid, string section)  
  101.     {  
  102.         this.SendCommand("UID FETCH " + uid + " BODY[" + section + "]");  
  103.         return this._GetMessage();  
  104.     }  
  105.  
  106.     public string GetMessage(int index, string section)  
  107.     {  
  108.         this.SendCommand("FETCH " + index + " BODY[" + section + "]");  
  109.         return this._GetMessage();  
  110.     }  
  111.  
  112.     protected string _GetMessage()  
  113.     {  
  114.         string line = _reader.ReadLine();  
  115.         MatchCollection m = Regex.Matches(line, "\\{(.*?)\\}");  
  116.  
  117.         if (m.Count > 0)  
  118.         {  
  119.             int length = Convert.ToInt32(m[0].ToString().Trim(new char[] { '{', '}}));  
  120.  
  121.             char[] buffer = new char[length];  
  122.             int read = (length < 128) ? length : 128;  
  123.             int remaining = length;  
  124.             int offset = 0;  
  125.             while (true)  
  126.             {  
  127.                 read = _reader.Read(buffer, offset, read);  
  128.                 remaining -= read;  
  129.                 offset += read;  
  130.                 read = (remaining >= 128) ? 128 : remaining;  
  131.  
  132.                 if (remaining==0)  
  133.                 {  
  134.                     break;  
  135.                 }  
  136.             }  
  137.             return new String(buffer);  
  138.         }  
  139.         return "";  
  140.           
  141.     }  
  142.  
  143.     protected void SendCommand(string cmd)  
  144.     {  
  145.         _writer.WriteLine("A" + _prefix.ToString() + " " + cmd);  
  146.         _writer.Flush();  
  147.         _prefix++;  
  148.     }  
  149.  
  150.     protected string GetResponse()  
  151.     {  
  152.         string response = string.Empty;  
  153.  
  154.         while (true)  
  155.         {  
  156.             string line = _reader.ReadLine();  
  157.             string[] tags = line.Split(new char[] { ' ' });  
  158.             response += line + Environment.NewLine;  
  159.             if (tags[0].Substring(0,1) == "A" && tags[1].Trim() == "OK" || tags[1].Trim() == "BAD" || tags[1].Trim() == "NO")  
  160.             {  
  161.                 break;  
  162.             }  
  163.               
  164.         }  
  165.  
  166.         return response;  
  167.     }  
  168. } 

1 comment:

vivek said...

The operation is not allowed on non-connected sockets.

this issue am facing

Post a Comment