MailItem 啥时候不是 MailItem? [关闭]

Posted

技术标签:

【中文标题】MailItem 啥时候不是 MailItem? [关闭]【英文标题】:When is a MailItem not a MailItem? [closed]MailItem 什么时候不是 MailItem? [关闭] 【发布时间】:2010-09-09 21:15:20 【问题描述】:

我在 Outlook 的 Visual Basic(我们使用 Outlook 2003 和 Exchange Server)中编写了一个消息处理函数来帮助我整理传入的电子邮件。

它对我有用,但有时规则会失败并且 Outlook 会停用它。

然后我重新打开规则并在我的收件箱上手动运行它以赶上进度。该规则会自发失败并每天停用数次。

我很想一劳永逸地解决这个问题。

【问题讨论】:

***.com/a/42547062/4539709 【参考方案1】:

这段代码向我展示了收件箱中的不同类型名称:

Public Sub GetTypeNamesInbox()
Dim myOlItems As Outlook.Items
Set myOlItems = application.GetNamespace("MAPI").GetDefaultFolder(olFolderInbox).Items
Dim msg As Object

For Each msg In myOlItems
    Debug.Print TypeName(msg)
    'emails are typename MailItem
    'Meeting responses are typename MeetingItem
    'Delivery receipts are typename ReportItem
Next msg

End Sub

HTH

【讨论】:

【参考方案2】:

在 Outlook 的 Visual Basic(我们使用 Outlook 2003 和 Exchange Server)中编写了一个消息处理函数来帮助我整理收到的电子邮件。它对我有用,除了有时规则失败并且 Outlook 将其停用。然后我重新打开规则并在我的收件箱上手动运行它以赶上。该规则自发失败并每天停用几次。我很想一劳永逸地解决这个问题。

以下是去掉了功能的代码,但让您了解它的外观:

   Public WithEvents myOlItems As Outlook.Items

   Public Sub Application_Startup()
       ' Reference the items in the Inbox. Because myOlItems is declared
       ' "WithEvents" the ItemAdd event will fire below.
       ' Set myOlItems = Outlook.Session.GetDefaultFolder(olFolderInbox).Items
       Set myOlItems = Application.GetNamespace("MAPI").GetDefaultFolder(olFolderInbox).Items
   End Sub

   Private Sub myOlItems_ItemAdd(ByVal Item As Object)
       On Error Resume Next
       If TypeName(Item) = "MailItem" Then
           MyMessageHandler Item
       End If
   End Sub

   Public Sub MyMessageHandler(ByRef Item As MailItem)
       Dim strSender As String
       Dim strSubject As String

       If TypeName(Item) <> "MailItem" Then
           Exit Sub
       End If

       strSender = LCase(Item.SenderEmailAddress)
       strSubject = Item.Subject

       rem do stuff
       rem do stuff
       rem do stuff
   End Sub

我得到的一个错误是调用 MyMessageHandler 的“类型不匹配”,其中 VB 抱怨 Item 不是 MailItem。好的,但是TypeName(Item)返回的是“MailItem”,那为什么Item不是MailItem呢?

我收到的另一封邮件是一封主题为空的电子邮件。线

strSubject = Item.Subject

给我一​​个错误。我知道 Item.Subject 应该为空,但为什么会出现错误?

谢谢。

【讨论】:

TypeName 询问类型以获得人类可读的版本。由于可以有两种不同的类型具有相同的名称,因此依赖 TypeName 进行类型检查会导致误报/否定。试试“TypeOf Item is MailItem” 如果TypeName(Item) = "MailItem",那么调用一个过程......它不仅只接受MailItems,而且再次检查该项目是否是MailItem?【参考方案3】:

我在直接引用 Outlook 库的其他 Office 应用程序中使用以下 VBA 代码 sn-p。

' Outlook Variables

  Dim objOutlook As Outlook.Application: Set objOutlook = New Outlook.Application
  Dim objNameSpace As Outlook.NameSpace: Set objNameSpace = objOutlook.GetNamespace("MAPI")
  Dim objFolder As MAPIFolder: Set objFolder = objNameSpace.PickFolder()
  Dim objMailItem As Outlook.MailItem

  Dim iCounter As Integer:  iCounter = objFolder.Items.Count
  Dim i As Integer

  For i = iCounter To 1 Step -1
    If TypeOf objFolder.Items(i) Is MailItem Then
      Set objMailItem = objFolder.Items(i)
      With objMailItem

等等

【讨论】:

我更喜欢TypeOf,而不是将“MailItem”硬编码为字符串。 好答案,但就我而言,我还必须检查MessageClass 以排除IPM.Outlook.Recall 的情况,除了Subject 之外基本上没有定义任何属性 基于ms doc,对于电子邮件,您应该验证条件If TypeOf objFolder.Items(i) Is MailItem And objFolder.Items(i).MessageClass = "IPM.Note" Then【参考方案4】:

对此我的记忆有些模糊,但我相信当 MailItem 类似于已读回执时,它就不是 MailItem。 (不幸的是,证明这一点的 VBA 代码是在另一份工作中编写的,现在不存在了。)

我还编写了用于处理传入消息的代码,原因可能与您所做的相同(Exchange 的规则太多,或者规则向导的规则太复杂),并且似乎记得遇到过同样的问题,即有些项目似乎来自不同的类型,即使我用你写的东西来捕捉它们。

如果有帮助,我会看看我是否可以提供一个具体的例子。

【讨论】:

【参考方案5】:

在默认收件箱中可以看到多种类型的项目。

在被调用的过程中,将传入的项目分配给Object 类型的变量。然后用TypeOf或者TypeName判断是不是MailItem。只有这样,您的代码才能执行适用于电子邮件的操作。

Dim obj As Object

If TypeName(obj) = "MailItem" Then
  ' your code for mail items here
End If

【讨论】:

【参考方案6】:
Dim objInboxFolder As MAPIFolder
Dim oItem As MailItem
Set objInboxFolder = GetNamespace("MAPI").GetDefaultFolder(olFolderInbox)

For Each Item In objInboxFolder.Items
    If TypeName(Item) = "MailItem" Then
    Set oItem = Item

next

【讨论】:

请在您的代码中添加解释。【参考方案7】:

为什么不对代码使用简单的错误处理程序?严重地。您可以为每次读取似乎失败的属性或对象写入错误。然后无论如何都要恢复。无需复杂的错误处理。考虑一个显示空主题的测试。由于您不知道它将返回什么值(如果有的话),而且它似乎在空或空白主题上出错,因此您需要将其描述为一个可能存在错误的简单测试。将测试作为 if 语句运行(无论如何都会出错),并让程序在出错时恢复。

On Error Resume Next
If object.subject = Null 'produces an error when subject is null, otherwise allows a good read
  strSubject = ""   'sets the subject grab string to a null or empty string as a string
Else
 strSubject = object.subject 'Sets the subject grab string to the subject of the message\item
End If

【讨论】:

以上是关于MailItem 啥时候不是 MailItem? [关闭]的主要内容,如果未能解决你的问题,请参考以下文章

仅保存 Outlook MailItem 的真实附件

比较两个VBA代码以获取mailitem的SMTP地址

MailItem.HtmlBody 抛出未实现的异常

Outlook.MailItem.EntryID 和 Mapi32.dll MessageID 之间的区别

Excel 和 Outlook 2016 中的“对象 '_mailItem' 的方法 'body' 失败”错误

在 Outlook 中捕获对 MailItem.SendUsingAccount 属性的更改