前面写了一篇通过smtp协议利用qq邮箱去实现发送邮件的功能。这一篇我们使用pop协议来实现一下接收邮件。
由于邮件的内容类型比较丰富,我暂时没有一个比较好的解决方案(确切的说我是懒得一种种去解析),所以这里就获取下邮件的列表,以及邮件的标题信息
实现功能
C#获取QQ邮箱内的邮件
开发环境
开发工具: Visual Studio 2013
.NET Framework版本:4.5
实现代码
static class Program
{
static string mail = "", pwd = "";
static void Main(string[] args)
{
Connect();
Console.WriteLine("结束运行");
Console.ReadKey();
}
static void Connect()
{
TcpClient tcpClient = new TcpClient("pop.qq.com", 995);
Console.WriteLine("已建立连接");
SslStream sslStream = new SslStream(tcpClient.GetStream(), true);
sslStream.AuthenticateAsClient("pop.qq.com");
//发送邮箱账号
sslStream.SendPop("user " + mail);
Console.WriteLine(sslStream.ReadString().msg);
//发送邮箱密码
sslStream.SendPop("pass " + pwd);
Console.WriteLine(sslStream.ReadString().msg);
//获取邮箱统计数据
sslStream.SendPop("stat");
Console.WriteLine(sslStream.ReadString().msg);
//获取邮件数量和每个邮件的大小
sslStream.SendPop("list");
string listMsg = sslStream.ReadString().msg;
List<string> list = listMsg.Split(new string[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries).ToList();
if (list.Count < 2)
{
Console.WriteLine("未获取到邮件");
return;
}
list.RemoveAt(0);
list.RemoveAt(list.Count - 1);
for (int i = list.Count - 1; i > -1; i--)
{
string[] arr = list[i].Split(' ');
//获取邮件前n行内容
sslStream.SendPop("top " + arr[0] + " 1");
Console.WriteLine(list[i]);
Console.WriteLine(GetHeader(sslStream.ReadString().msg));
Console.WriteLine();
Console.WriteLine();
}
//string id = Console.ReadLine();
//sslStream.SendPop("retr " + id);
//Console.WriteLine(GetContext(sslStream.ReadString().msg));
sslStream.Close();
tcpClient.Close();
}
/// <summary>
/// 解析邮件标题
/// </summary>
/// <param name="text"></param>
/// <returns></returns>
static string GetHeader(string text)
{
List<string> list = text.Split(new string[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries).ToList();
list.RemoveAt(0);
list.RemoveAt(list.Count - 1);
StringBuilder sb = new StringBuilder();
for (int i = 1; i < list.Count; i++)
{
if (list[i].StartsWith("Date: "))
{
sb.AppendLine("发送时间:" + list[i].Substring("Date: ".Length));
}
if (list[i].StartsWith("From: "))
{
string value = list[i].Substring("From: ".Length);
sb.AppendLine("发送人:" + GetText(value));
}
if (list[i].StartsWith("Subject: "))
{
string value = list[i].Substring("Subject: ".Length);
sb.AppendLine("邮件标题:" + GetText(value));
}
if (list[i].StartsWith("Cc: "))
{
string value = list[i].Substring("Cc: ".Length);
sb.AppendLine("抄送:" + GetText(value));
}
}
return sb.ToString();
}
/// <summary>
/// 解析邮件内容
/// </summary>
/// <param name="text"></param>
/// <returns></returns>
static string GetContext(string text)
{
List<string> list = text.Split(new string[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries).ToList();
list.RemoveAt(0);
list.RemoveAt(list.Count - 1);
StringBuilder sb = new StringBuilder();
string s = list.Where(a => a.StartsWith("Content-Transfer-Encoding:")).SingleOrDefault();
int index = list.IndexOf(s) + 1;
for (int i = index; i < list.Count - index; i++)
{
sb.AppendLine(GetText(list[i]));
}
return sb.ToString();
}
/// <summary>
/// 解析原始文本
/// </summary>
/// <param name="value"></param>
/// <returns></returns>
static string GetText(string value)
{
string encoding = "utf-8";
if (value.IndexOf("=?") == 0)
{
string tag = "";
if (value.Contains("?B?"))
{
tag = "?B?";
encoding = value.SubStr("=?", tag);
}
if (value.Contains("?b?"))
{
tag = "?b?";
encoding = value.SubStr("=?", tag);
}
if (value.Contains("?Q?"))
{
tag = "?Q?";
encoding = value.SubStr("=?", tag);
}
if (tag != "")
{
string last = "";
int lastIndex = value.LastIndexOf("?=");
if (lastIndex != value.TrimEnd().Length - 2)
{
last = value.Substring(lastIndex + 2);
}
string text = value.SubStr(tag, "?=");
if (tag.ToLower().Contains("b"))
{
return Encoding.GetEncoding(encoding).GetString(Convert.FromBase64String(text)) + last;
}
else if (tag.ToLower().Contains("q"))
{
return DecodeQP(text, encoding) + last;
}
}
}
return value;
}
static string SubStr(this string text, string start, string end)
{
try
{
int s = text.IndexOf(start);
int e = text.LastIndexOf(end);
if (s == -1 || e == -1)
{
return text;
}
string result = text.Substring(s + start.Length, e - s - start.Length);
return result;
}
catch (Exception ex)
{
throw ex;
}
}
/// <summary>
/// 发送数据到pop
/// </summary>
/// <param name="sslStream"></param>
/// <param name="text"></param>
/// <param name="isNewLine"></param>
static void SendPop(this SslStream sslStream, string text, bool isNewLine = true)
{
if (isNewLine)
{
text += "\r\n";
}
sslStream.Write(Encoding.ASCII.GetBytes(text));
}
static dynamic ReadString(this SslStream sslStream)
{
try
{
byte[] buffer = new byte[2048 * 2048];
int len = sslStream.Read(buffer, 0, buffer.Length);
string result = Encoding.UTF8.GetString(buffer, 0, len);
if (result.StartsWith("-ERR"))
{
throw new Exception(result);
}
else
{
return new { code = 1, msg = result };
}
}
catch (Exception ex)
{
return new { code = 0, msg = "读取错误:" + ex.Message };
}
}
//Quoted-Printable 解码(QP解码)
static string DecodeQP(string data, string encoding)
{
char ch;
string ret = "";
byte[] bytes = new byte[data.Length];
int bIdex = 0;
try
{
for (int rIndex = 0; rIndex < data.Length; rIndex++)
{
ch = data[rIndex];
if (ch == '=')
{
rIndex++;
if (rIndex < data.Length && (Char.IsDigit(data[rIndex]) || Char.IsLetter(data[rIndex])))
{
bytes[bIdex++] = Byte.Parse(data.Substring(rIndex++, 2), System.Globalization.NumberStyles.HexNumber);
continue;
}
if (rIndex < data.Length && data[rIndex] == '\r' && (rIndex + 1) < data.Length && data[rIndex + 1] == '\n')
{
rIndex++;
continue;
}
}
if (ch == '\r' || ch == '\n')
continue;
bytes[bIdex++] = (byte)ch;
}
ret = Encoding.GetEncoding(encoding).GetString(bytes, 0, bIdex);
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
return ret;
}
}
到此这篇关于C#实现接收QQ邮件的示例代码的文章就介绍到这了,更多相关C#接收QQ邮件内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!