EWS 2.2.0获取所有联系人求助:过滤GAL及联系人组
解决EWS获取所有联系人(含自定义文件夹)并排除GAL和联系人组的问题
你当前用EWS 2.2.0获取全邮箱联系人的思路是对的,但几个细节没处理好,导致拿到了GAL和联系人组。我来帮你调整下:
先说说问题出在哪
- ItemClass取值错误:你写的
"Microsoft.Exchange.WebServices.Data.ContactSchema"是.NET类的名称,而Exchange识别的联系人ItemClass是**IPM.Contact,联系人组对应的是IPM.DistList**,用这两个值才能准确筛选。 - 没有排除系统地址列表文件夹:GAL属于Exchange的系统地址列表文件夹(FolderClass为
IPM.Configuration.AddressBook),遍历这类文件夹会拿到非用户邮箱内的联系人,需要直接过滤掉。 - 结果列表被覆盖:你每次循环都把
result重新赋值为当前文件夹的结果,之前文件夹的联系人会丢失,应该用AddRange累积结果。
修改后的代码(遍历文件夹版本)
List<Contact> result = new List<Contact>(); // 先过滤掉系统地址列表文件夹,避免拿到GAL相关内容 FindFoldersResults allFolders = _service.FindFolders(WellKnownFolderName.Root, new SearchFilter.IsNotEqualTo(FolderSchema.FolderClass, "IPM.Configuration.AddressBook"), new FolderView(int.MaxValue) { Traversal = FolderTraversal.Deep }); foreach (var folder in allFolders) { // 组合过滤条件:是联系人,且不是联系人组 SearchFilter searchFilter = new SearchFilter.SearchFilterCollection(LogicalOperator.And, new SearchFilter.IsEqualTo(ItemSchema.ItemClass, "IPM.Contact"), new SearchFilter.IsNotEqualTo(ItemSchema.ItemClass, "IPM.DistList")); FindItemsResults<Item> discoveredContactsInFolder = _service.FindItems(folder.Id, searchFilter, new ItemView(int.MaxValue)); // 用AddRange累积所有文件夹的联系人,避免覆盖 result.AddRange(discoveredContactsInFolder.OfType<Contact>()); }
更高效的方式:跨文件夹直接搜索
其实EWS支持直接在整个邮箱范围内搜索联系人,不需要手动遍历每个文件夹,代码更简洁,性能也更好:
List<Contact> result = new List<Contact>(); // 构建过滤条件:只取IPM.Contact类型,排除联系人组 SearchFilter searchFilter = new SearchFilter.SearchFilterCollection(LogicalOperator.And, new SearchFilter.IsEqualTo(ItemSchema.ItemClass, "IPM.Contact"), new SearchFilter.IsNotEqualTo(ItemSchema.ItemClass, "IPM.DistList")); // 在Root文件夹下深度搜索所有符合条件的项 FindItemsResults<Item> allContacts = _service.FindItems(WellKnownFolderName.Root, searchFilter, new ItemView(int.MaxValue) { Traversal = ItemTraversal.Shallow }); result.AddRange(allContacts.OfType<Contact>()); // 处理分页:如果结果超过单次返回上限,循环获取下一页 while (allContacts.MoreAvailable) { allContacts = _service.FindItems(allContacts.NextPageOffset, searchFilter, new ItemView(int.MaxValue)); result.AddRange(allContacts.OfType<Contact>()); }
关键要点说明
- ItemClass的正确值:Exchange中所有项目都有标准的ItemClass标识,联系人是
IPM.Contact,联系人组是IPM.DistList,这是Exchange原生识别的字符串,不是.NET类名。 - 系统文件夹过滤:
IPM.Configuration.AddressBook类型的文件夹是Exchange存储全局地址列表、离线地址簿等系统数据的地方,完全不需要遍历。 - 分页处理:EWS的
FindItems默认有返回数量限制(通常是1000),如果你的邮箱联系人较多,一定要处理分页逻辑,避免丢失数据。 - OfType
() :比as Contact更安全,直接过滤出Contact类型的项,不会混入null值。
内容的提问来源于stack exchange,提问作者Svetoslav Georgiev
相关产品推荐
相关产品推荐

