当我的一个 NSManagedObjectContext 运行它的 performBlock
时,用户选择退出他们的帐户(这将重置所有上下文并删除持久存储)。这个重置代码显然是在与 performBlock 类似的时间运行的,因此应用程序崩溃并出现异常:
*** 由于未捕获的异常“NSInvalidArgumentException”而终止应用程序,原因:“无法从此 NSManagedObjectContext 的协调器访问对象的持久存储”
它崩溃的确切位置似乎是当一个上下文保存在其 performBlock
中时,然后它将发出 did save
通知,并合并到另一个上下文中.这是堆栈跟踪:
0 CoreFoundation 0x03b96df6 __exceptionPreprocess + 182
1 libobjc.A.dylib 0x03820a97 objc_exception_throw + 44
2 CoreData 0x034f7791 _PFRetainedObjectIDCore + 1169
3 CoreData 0x034f72f0 -[NSManagedObjectContext(_NSInternalAdditions) _retainedObjectWithID:] + 32
4 CoreData 0x034db0f3 -[NSManagedObjectContext objectWithID:] + 595
5 CoreData 0x0352e14e _faultBatchAtIndex + 1102
6 CoreData 0x0352ed02 -[_PFBatchFaultingArray objectAtIndex:] + 50
7 CoreData 0x035dd010 +[NSFetchedResultsController(PrivateMethods) _insertIndexForObject:inArray:lowIdx:highIdx:sortDescriptors:] + 144
8 CoreData 0x035d7ba2 -[NSFetchedResultsController(PrivateMethods) _postprocessInsertedObjects:] + 738
9 CoreData 0x035da3dd __77-[NSFetchedResultsController(PrivateMethods) _managedObjectContextDidChange:]_block_invoke + 2285
10 CoreData 0x034e7454 developerSubmittedBlockToNSManagedObjectContextPerform + 196
11 CoreData 0x034e7337 -[NSManagedObjectContext performBlockAndWait:] + 231
12 CoreData 0x035d9acf -[NSFetchedResultsController(PrivateMethods) _managedObjectContextDidChange:] + 127
13 Foundation 0x00eff929 __57-[NSNotificationCenter addObserver:selector:namebject:]_block_invoke + 40
14 CoreFoundation 0x03b61974 __CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 20
15 CoreFoundation 0x03a4f61b _CFXNotificationPost + 3051
16 Foundation 0x00eeef26 -[NSNotificationCenter postNotificationNamebject:userInfo:] + 98
17 CoreData 0x034c84d3 -[NSManagedObjectContext(_NSInternalNotificationHandling) _postObjectsDidChangeNotificationWithUserInfo:] + 83
18 CoreData 0x034d9cbe -[NSManagedObjectContext _mergeChangesFromDidSaveDictionary:usingObjectIDs:] + 3934
19 CoreData 0x034d8d40 -[NSManagedObjectContext mergeChangesFromContextDidSaveNotification:] + 496
20 App 0x00319707 __57-[ContextManager contextDidSavePrivateQueueContext:]_block_invoke + 103
这仅适用于 iOS 8 - iOS 7 可以正常工作。我无法弄清楚这是否是我感受到影响的 iOS 8 的一个错误,或者 Apple 是否在 Core Data 中引入了破坏我们重置流程的“新功能”。任何人都可以对此有所了解吗?
我通过在 NSManagedObjectContext
上添加一个类别并使用 objc_setAssociatedObject
魔法添加一个标志来修复了这个错误。该标志用于确定上下文是否可以安全地执行任何出现的 performBlock。为此,我在名为 safePerformBlock
的类别上添加了另一个方法,该方法查看标志。如果为假,我立即返回,而不是处理传入的 block 。
当我删除上下文中的持久存储时,该标志设置为不安全。当用户随后重新登录并重新创建持久存储时,该标志将设置为安全。
本质上,我将上下文中的此标志视为 performBlocks 上的取消标记。我不知道为什么 API 中没有任何内容。在这种情况下,这是我能找到的最佳解决方案。
关于在 performBlock 中重置我的 NSManagedObjectContext 时,iOS 8 应用程序崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26234523/
欢迎光临 OStack程序员社区-中国程序员成长平台 (https://ostack.cn/) | Powered by Discuz! X3.4 |