【问题标题】:Parsing emails in outloook with C#使用 C# 在 Outlook 中解析电子邮件
【发布时间】:2012-03-12 19:24:42
【问题描述】:

我正在编写一个程序来阅读我所有的 Outlook 电子邮件,最终搜索会更具体,但现在我想阅读我收件箱中的所有电子邮件。由于某种原因,我正在运行的代码可以读取我想要的最高 169 的内容...

namespace reademail
{
static class Program
{
    public static Microsoft.Office.Interop.Outlook.Application myApp;

    public static void Main(string[] args)
    {            
       // myApp = new Microsoft.Office.Interop.Outlook.Application();
        //myApp.NewMailEx += new Microsoft.Office.Interop.Outlook.ApplicationEvents_11_NewMailExEventHandler(OutlookNewMailReceived);
        ReadMail();
    }

    static void ReadMail()
    {
        Microsoft.Office.Interop.Outlook.Application app = null;
        Microsoft.Office.Interop.Outlook._NameSpace ns = null;
        Microsoft.Office.Interop.Outlook.MailItem item = null;
        Microsoft.Office.Interop.Outlook.MAPIFolder inboxFolder = null;


            app = new Microsoft.Office.Interop.Outlook.Application();
            ns = app.GetNamespace("MAPI");
            //ns.Logon(null, null, false, false);

            inboxFolder = ns.GetDefaultFolder(Microsoft.Office.Interop.Outlook.OlDefaultFolders.olFolderInbox);
           // subFolder = inboxFolder.Folders["Inbox"]; //folder.Folders[1]; also works
            Console.WriteLine("Folder Name: {0}, EntryId: {1}", inboxFolder.Name, inboxFolder.EntryID);
            Console.WriteLine("Num Items: {0}", inboxFolder.Items.Count.ToString());

            //System.IO.StreamWriter strm = new System.IO.StreamWriter("C:/Test/Inbox.txt");
            for (int counter = 1; counter <= inboxFolder.Items.Count; counter++)
            {
                Console.Write(inboxFolder.Items.Count + " " + counter);
                item = (Microsoft.Office.Interop.Outlook.MailItem)inboxFolder.Items[counter];
                Console.WriteLine("Item: {0}", counter.ToString());
                Console.WriteLine("Subject: {0}", item.Subject);
                Console.WriteLine("Sent: {0} {1}", item.SentOn.ToLongDateString(), item.SentOn.ToLongTimeString());
                Console.WriteLine("Sendername: {0}", item.SenderName);
                Console.WriteLine("Body: {0}", item.Body);
                //strm.WriteLine(counter.ToString() + "," + item.Subject + "," + item.SentOn.ToShortDateString() + "," + item.SenderName);

            }
            //strm.Close();
        }


    }
}

循环读取多达 169 封电子邮件,然后崩溃,它还开始在似乎是任意日期阅读电子邮件...我不确定是什么阻止它阅读所有电子邮件...

Folder Name: Inbox, EntryId: 000000003527EA8DB4FFC04EB6ABA4DE31CB4BA40100C6D3EBA
DBDB57E438D0B53C5FB515CC50000660627C70000
Num Items: 1048
System.InvalidCastException: Unable to cast COM object of type 'System.__ComObje
ct' to interface type 'Microsoft.Office.Interop.Outlook.MailItem'. This operatio
n failed because the QueryInterface call on the COM component for the interface
with IID '{00063034-0000-0000-C000-000000000046}' failed due to the following er
ror: No such interface supported (Exception from HRESULT: 0x80004002 (E_NOINTERF
ACE)).
 at CallSite.Target(Closure , CallSite , Object )
 at reademail.Program.ReadMail() in C:\Documents and Settings\DBubel\my docume
nts\visual studio 2010\Projects\reademail\reademail\Program.cs:line 60

按任意键继续。 . .

【问题讨论】:

  • 当它崩溃时,您需要告诉我们具体的Exception 是什么,以便我们解决问题。

标签: c# parsing email outlook inbox


【解决方案1】:

我的猜测是,您的收件箱中有未应用 Microsoft.Office.Interop.Outlook.MailItem 接口的项目,因此代码在循环并尝试投射时崩溃。如果您使用 .NET4,因为它支持动态,一种可能的解决方法是不强制转换对象,而是将其传递给动态变量。

dynamic item = inboxFolder.Items[counter];

这对我有用,因为您的代码在处理收件箱文件夹中的会议邀请时遇到问题。

完整修改代码:

 namespace reademail
    {
     static class Program
    {
        public static Microsoft.Office.Interop.Outlook.Application myApp;

        public static void Main(string[] args)
        {
            // myApp = new Microsoft.Office.Interop.Outlook.Application();
            //myApp.NewMailEx += new Microsoft.Office.Interop.Outlook.ApplicationEvents_11_NewMailExEventHandler(OutlookNewMailReceived);
            ReadMail();
        }

        static void ReadMail()
        {
            Microsoft.Office.Interop.Outlook.Application app = null;
            Microsoft.Office.Interop.Outlook._NameSpace ns = null;
            //Microsoft.Office.Interop.Outlook.MailItem item = null;
            Microsoft.Office.Interop.Outlook.MAPIFolder inboxFolder = null;


            app = new Microsoft.Office.Interop.Outlook.Application();
            ns = app.GetNamespace("MAPI");
            //ns.Logon(null, null, false, false);

            inboxFolder = ns.GetDefaultFolder(Microsoft.Office.Interop.Outlook.OlDefaultFolders.olFolderInbox);
            // subFolder = inboxFolder.Folders["Inbox"]; //folder.Folders[1]; also works
            Console.WriteLine("Folder Name: {0}, EntryId: {1}", inboxFolder.Name, inboxFolder.EntryID);
            Console.WriteLine("Num Items: {0}", inboxFolder.Items.Count.ToString());

            //System.IO.StreamWriter strm = new System.IO.StreamWriter("C:/Test/Inbox.txt");
            for (int counter = 1; counter <= inboxFolder.Items.Count; counter++)
            {
                Console.Write(inboxFolder.Items.Count + " " + counter);
                dynamic item = inboxFolder.Items[counter];
                //item = (Microsoft.Office.Interop.Outlook.MailItem)inboxFolder.Items[counter];
                Console.WriteLine("Item: {0}", counter.ToString());
                Console.WriteLine("Subject: {0}", item.Subject);
                Console.WriteLine("Sent: {0} {1}", item.SentOn.ToLongDateString(), item.SentOn.ToLongTimeString());
                Console.WriteLine("Sendername: {0}", item.SenderName);
                Console.WriteLine("Body: {0}", item.Body);
                //strm.WriteLine(counter.ToString() + "," + item.Subject + "," + item.SentOn.ToShortDateString() + "," + item.SenderName);

            }
            //strm.Close();
        }
    }

}

【讨论】:

  • 如果我在循环中的项目前面添加动态,它说它改变了范围,我试图将它转换为这样 item = (dynamic)inboxFolder.Items[counter];仍然是同样的错误。我的代码对你有用吗?
  • 是的,我只需要删除顶部的变量声明。 (参见上面的完整修改代码)
【解决方案2】:

如果您只想要MailItems,那么您应该检查您检索的项目是否是有效的MailItem,而不是假设您有一个。可能是CalendarItemDocumentItem 等,因olItemType 而异。您当前的代码明确假设您的收件箱中只有 MailItems

item = inboxFolder.Items[counter] as Microsoft.Office.Interop.Outlook.MailItem;
if (item != null)
{
   ....
}

您的错误表明您可能有一个MailItem - 但它可能是一个邮件递送报告(已读回执等)。请参阅 this post for reference 与转换错误。他们建议利用Outlook Table interface 作为解决方法并检查对象Class。这可能是您的另一种选择。

【讨论】:

  • 我认为这将是解决方法,但发生了完全相同的行为,这对我来说很奇怪,它读取任意数量的电子邮件并从任意日期开始......
  • 我会试试这个,我要回家了。我稍后会回来。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2013-09-22
  • 1970-01-01
  • 2017-09-05
  • 2013-11-28
  • 1970-01-01
  • 1970-01-01
  • 2011-03-04
相关资源
最近更新 更多