iOS 13 中历史相关的 Contacts 框架类都有哪些?

Posted

技术标签:

【中文标题】iOS 13 中历史相关的 Contacts 框架类都有哪些?【英文标题】:What are the history-related Contacts framework class in iOS 13?iOS 13 中历史相关的 Contacts 框架类有哪些? 【发布时间】:2019-10-12 19:46:59 【问题描述】:

ios 13 中新增了一系列与历史相关的类,例如 CNChangeHistoryEvent 和 CNChangeHistoryFetchRequest。没有文档,并且在我能找到的任何 WWDC 2019 视频中都没有提到它们。它们有什么用途以及如何使用它们?

【问题讨论】:

您在使用此 API 方面取得过任何进展吗?现在是 2020 年 4 月,Apple 的文档仍然说“没有可用的概述”! 哈......我很确定一大块 API 不会像那样泄漏,或者至少如果确实如此,它不会在如此多的后续版本中持续存在。我有机会在 WWDC19 上与联系人团队中的某个人交谈(非常简短),向他们询问了新 API,他们说他们“很快”就会有一些文档。但是(与 Apple 的其他团队一样)他们没有跟进。 【参考方案1】:

API 应该以您可以将“令牌”传递给更改历史请求的方式运行,它会为您提供自该令牌以来添加/删除/更新的联系人(或组)。

到目前为止,我只能像这样“运行”历史获取请求:

    CNChangeHistoryFetchRequest *fetchHistory = [[CNChangeHistoryFetchRequest alloc] init];
    fetchHistory.startingToken = [[NSUserDefaults standardUserDefaults] dataForKey:@"CNContactChangeHistoryToken"];

    NSError *error = nil;

    CNContactStore *store = [[CNContactStore alloc] init];
    CNFetchResult *fetchResult = [store enumeratorForChangeHistoryFetchRequest:fetchHistory error:&error];

    NSEnumerator *enumerator = [fetchResult value];
    id object;

    while ((object = [enumerator nextObject])) 
        // do something with object
        NSLog(@"change history enumerator object = %@", object);
        CNChangeHistoryEvent *historyEvent = (CNChangeHistoryEvent *) object;
        if ([historyEvent isKindOfClass:[CNChangeHistoryDropEverythingEvent class]]) 
            NSLog(@"change history - DROP EVERYTHING!");
            [historyEvent acceptEventVisitor: self];
         else 
            if ([historyEvent isKindOfClass:[CNChangeHistoryAddContactEvent class]]) 
                CNChangeHistoryAddContactEvent *addContactEvent = (CNChangeHistoryAddContactEvent *) object;
                NSLog(@"change history - AddContact event container %@ - %@", addContactEvent.containerIdentifier, addContactEvent.contact);
             else if ([historyEvent isKindOfClass:[CNChangeHistoryUpdateContactEvent class]]) 
                CNChangeHistoryUpdateContactEvent *updateContactEvent = (CNChangeHistoryUpdateContactEvent *) object;
                NSLog(@"change history - UpdateContact event - %@", updateContactEvent.contact);
             else if ([historyEvent isKindOfClass:[CNChangeHistoryDeleteContactEvent class]]) 
                CNChangeHistoryDeleteContactEvent *deleteContactEvent = (CNChangeHistoryDeleteContactEvent *) object;
                NSLog(@"change history - DeleteContact event - %@", deleteContactEvent.contactIdentifier);
            
        
    

枚举运行,它始终是“CNChangeHistoryDropEverythingEvent”事件,然后是整个联系人列表的“添加联系人”和“添加组”事件。这是因为我找不到在任何地方获取当前令牌的方法。 'fetchResult' 对象应该有一个currentHistoryToken,但它总是为零; CNContactStore 的currentHistoryToken 对象也是如此。所以我不知道从哪里得到它,所以下次我可以将它传递给startingToken

【讨论】:

你能得到 currentHistoryToken 吗? Apple 上没有关于更改历史的文档,甚至 Swift 上也没有 enumerate 方法:( 我不久前提交了“反馈”,Apple 最近向我确认,他们从 iOS14.6 及更高版本开始修复了此问题,您可以从系统中获得有效的currentHistoryToken 谢谢你解释了为什么我无法在模拟器(iOS 14.5)上得到它。我在设备(iOS 14.7)上尝试了它,并且能够获得令牌。

以上是关于iOS 13 中历史相关的 Contacts 框架类都有哪些?的主要内容,如果未能解决你的问题,请参考以下文章

ios9-通讯录

UITableView 类似 Contacts ios 7 中的社交部分

iOS 索引功能

IOS AddressBook Contacts真实设备上的Null问题

实体框架查询忽略我的 orderby

iOS 13 版本的 XCUI 测试框架中未检测到 iOS Search Bar