You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Outlook VSTO:邮件进入已发送箱时调用函数获取发送日期失败

问题:Outlook已发送邮件箱ItemAdd事件无法触发

我想实现当邮件进入Outlook的已发送邮件箱(Sent Items)时,调用函数获取该邮件的发送日期(Sent Date),但当前代码无法正常工作。最初的代码在ThisAddIn_Startup方法中遍历Stores,绑定的是**收件箱(Inbox)**的Items.ItemAdd事件;后续将items改为全局变量后,还是无法触发已发送邮件箱的事件。

初始代码

private void ThisAddIn_Startup(object sender, System.EventArgs e) {
        try
        {
            Outlook.Stores stores = Application.Session.Stores;
            foreach (Outlook.Store store in stores)
            {
                var folder = store.Session.GetDefaultFolder(Outlook.OlDefaultFolders.olFolderInbox);
                var items = folder.Items;
                if (items.Count > 0)
                    MessageBox.Show($"Unread items in Inbox = {items.Count}");
                items.ItemAdd += ItemsAdd;
            }

        }
        catch (Exception exception)
        {
            Log.Error(exception.Message);
            throw;
        }
}

更新后代码

Outlook.Items items;

private void ThisAddIn_Startup(object sender, System.EventArgs e) {
        try
        {
            Outlook.Stores stores = Application.Session.Stores;
            foreach (Outlook.Store store in stores)
            {
                var folder = store.Session.GetDefaultFolder(Outlook.OlDefaultFolders.olFolderInbox);
                items = folder.Items;
                
                items.ItemAdd += ItemsAdd;
            }

        }
        catch (Exception exception)
        {
            Log.Error(exception.Message);
            throw;
        }
    }

修复方案

  1. 目标文件夹错误:你的代码一直绑定的是收件箱(olFolderInbox),要监听已发送邮件箱,需要改用olFolderSentMail枚举值。
  2. 全局变量覆盖问题:遍历多个Store时,全局items变量会被最后一个Store的收件箱Items覆盖,导致之前的绑定失效。需要用集合存储每个Store的已发送邮件箱Items对象,避免被垃圾回收或覆盖。

修复后的代码示例:

// 用集合存储所有已发送邮件箱的Items对象,防止被GC回收
private List<Outlook.Items> _sentItemsCollection = new List<Outlook.Items>();

private void ThisAddIn_Startup(object sender, System.EventArgs e) {
    try
    {
        Outlook.Stores stores = Application.Session.Stores;
        foreach (Outlook.Store store in stores)
        {
            // 获取当前Store的已发送邮件箱
            var sentFolder = store.GetDefaultFolder(Outlook.OlDefaultFolders.olFolderSentMail);
            var sentItems = sentFolder.Items;
            // 绑定ItemAdd事件
            sentItems.ItemAdd += SentItems_ItemAdd;
            // 添加到集合中保存引用
            _sentItemsCollection.Add(sentItems);
        }
    }
    catch (Exception exception)
    {
        Log.Error(exception.Message);
        throw;
    }
}

// 已发送邮件箱ItemAdd事件处理方法
private void SentItems_ItemAdd(object item) {
    if (item is Outlook.MailItem mail)
    {
        // 获取发送日期
        DateTime sentDate = mail.SentOn;
        // 这里添加你的业务逻辑,比如打印或记录发送日期
        MessageBox.Show($"邮件发送日期:{sentDate.ToString("yyyy-MM-dd HH:mm:ss")}");
    }
}

关键说明

  • 使用store.GetDefaultFolder而非store.Session.GetDefaultFolder:前者会获取当前Store对应的默认文件夹,后者可能返回当前会话的默认Store文件夹,避免跨Store的错误。
  • 用集合保存Outlook.Items引用:Outlook对象模型中,局部变量的Items对象容易被垃圾回收,导致事件失效,全局集合可以维持引用。
  • 类型判断:在事件处理方法中先判断item是否为MailItem,避免非邮件项触发错误。

内容的提问来源于stack exchange,提问作者gabrielcassimiro

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.20 05:40:32