首页 > 解决方案 > 如何检查邮件是否具有有效的数字签名?

问题描述

我需要验证传入的邮件是否在 Outlook 2010 中签名。

如果邮件未签名,则应将其移动到“NOSIG”文件夹中。

在研究时,我发现(并且有点确认)Outlook 2010 将 MessageClass 修改为“IPM.Note”,所以我尝试使用 PropertyAccessor 并阅读安全标志。

到目前为止,这是我的代码:

Sub TRCR(MAIL_ITEM As MailItem)

    Dim PR_SECURITY_FLAGS As Integer

    On Error Resume Next

    'Security-Flags: 0=none, 1=encrypted, 2=signed, 3=both
    PR_SECURITY_FLAGS = MAIL_ITEM.PropertyAccessor.GetProperty("http://schemas.microsoft.com/mapi/proptag/0x6E010003")

    'Modulo because, sometimes the flags value is added to a multiple of 32... <unfortunately I lost the source>
    If (PR_SECURITY_FLAGS > 32) Then PR_SECURITY_FLAGS = PR_SECURITY_FLAGS Mod 32

    If PR_SECURITY_FLAGS = 2 Or PR_SECURITY_FLAGS = 3 Then
        'Do all that fancy stuff I want to with that signed Mail
    Else
        MAIL_ITEM.Move Application.GetNamespace("MAPI").GetDefaultFolder(olFolderInbox).Folders.Item("NOSIG")
    End If

End Sub

我使用 Outlook 规则在每封收到的电子邮件上运行该脚本。

它有时会将签名的邮件移动到 NOSIG 文件夹。

在这些情况下,PR_SECURITY_FLAGS 在模代码行之前和之后都为 0。所以为 0,脚本工作正常,但由于邮件已签名,标志不应该是 0,而是 2。

我对同一份签名邮件反感了几十次,只是为了总是看到同样的事情发生。他们中的大多数都得到了正确的对待,而少数人在签名时总是显示标志 0 而不是 2。

我试图暂停脚本 1-5 秒,Application.Wait Now + TimeSerial(0, 0, 1)认为脚本对于 PropertyAccessor 或其他东西来说可能太快了,但暂停不起作用。(在处理多封邮件时,我感觉不到五秒钟的延迟。)

我开始认为这是一个 Outlook 问题(可能操纵类似于 MessageClass 的安全标志,但并非每次都如此)。

标签: vbaemailoutlook

解决方案


PR_SECURITY_FLAGS仅在传出邮件上设置,以告诉 Outlook 在实际发送邮件时对其进行加密。它不会出现在传入的消息中 - 使用OutlookSpy查看消息(单击 IMessage 按钮)。

对于传入的消息,您可能会认为您可以检查MessageClass属性并查看它是否为"IPM.Note.SMIME.MultipartSigned",但 OOM 非常努力地将签名和加密的消息表示为常规IPM.Note消息。您必须完全绕过 OOM 并使用扩展 MAPI(仅限 C++ 或 Delphi),或者您可以使用Redemption(任何语言,包括 VBA)。像下面这样的东西可以让你检查真正的消息类:

set Session = CreateObject("Redemption.RDOSession")
Session.MAPIOBJECT = Application.Session.MAPIOBJECT
set SourceMsg = Session.GetRDOObjectFromOutlookObject(MAIL_ITEM , true)
MsgBox SourceMsg.MessageClass

推荐阅读