時折起こるクラッシュレポートをユーザーから受け取りました(自分では再現できません)。それはNSManagedObjectContext refreshObject
と関係があります。クラッシュメッセージ「アンNSManagedObjectContextは、他のコンテキスト内のオブジェクトを更新することはできません」NSManagedObjectContextでクラッシュするrefreshObject
ある
それがクラッシュするコードはここにある:
dispatch_async(self.filterMainQueue, ^{
NSArray *items = [Person getAllNonPrivatePersonsWithContext: self.backgroundContextImage];
if (items.count) {
for (Person *person in items) {
[self.backgroundContextImage performBlockAndWait: ^{
[person loadContactReferenceAndImage];
// crashes here
[self.backgroundContextImage refreshObject: person mergeChanges:NO];
}];
}
}
});
+ (NSArray *) getAllNonPrivatePersonsWithContext: (NSManagedObjectContext *) context{
__block NSArray *items = nil;
[context performBlockAndWait: ^{
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
// Edit the entity name as appropriate.
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Person" inManagedObjectContext: context];
[fetchRequest setEntity:entity];
// Set the batch size to a suitable number.
//[fetchRequest setFetchBatchSize: 500];
[fetchRequest setPredicate: [NSPredicate predicateWithFormat: @"isContactPrivate == FALSE"]];
[fetchRequest setReturnsObjectsAsFaults: FALSE];
[fetchRequest setIncludesPendingChanges: FALSE];
NSError *error = nil;
items = [context executeFetchRequest:fetchRequest error:&error];
}];
return items;
}
これは、なぜ私はかなりよく分かりませんクラッシュする。 backgroundContextImage
はNSPrivateQueueConcurrencyType
を使用して作成されており、そのコンテキストで管理対象オブジェクトを取得してアクセスするときにはperformBlockAndWait
を使用していることを確認します。 filterMainQueue
はシリアルキューで、メインスレッドではなくバックグラウンドスレッドでこの作業を行うのに役立ちます。
クラッシュレポートは次のようになります。
Exception Type: SIGABRT
Exception Codes: #0 at 0x197fb7140
Crashed Thread: 3
Application Specific Information:
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'An NSManagedObjectContext cannot refresh objects in other contexts.'
Last Exception Backtrace:
0 CoreFoundation 0x0000000182a98f48 __exceptionPreprocess + 124
1 libobjc.A.dylib 0x000000019764bf80 objc_exception_throw + 52
2 CoreData 0x0000000182786898 -[NSManagedObjectContext refreshObject:mergeChanges:] + 1320
3 CJournal 0x00000001001729c4 __75-[ContactsSyncController loadContactImagesAndLinksWithPermissionWithBlock:]_block_invoke_2 (ContactsSyncController.m:102)
4 CoreData 0x00000001827dc900 developerSubmittedBlockToNSManagedObjectContextPerform + 192
5 libdispatch.dylib 0x0000000197e696a8 _dispatch_client_callout + 12
6 libdispatch.dylib 0x0000000197e74954 _dispatch_barrier_sync_f_invoke + 96
7 CoreData 0x00000001827dc7e8 -[NSManagedObjectContext performBlockAndWait:] + 248
8 CJournal 0x00000001001728bc __75-[ContactsSyncController loadContactImagesAndLinksWithPermissionWithBlock:]_block_invoke (ContactsSyncController.m:97)
9 libdispatch.dylib 0x0000000197e696e8 _dispatch_call_block_and_release + 20
10 libdispatch.dylib 0x0000000197e696a8 _dispatch_client_callout + 12
11 libdispatch.dylib 0x0000000197e756ec _dispatch_queue_drain + 860
12 libdispatch.dylib 0x0000000197e6d1ac _dispatch_queue_invoke + 460
13 libdispatch.dylib 0x0000000197e696a8 _dispatch_client_callout + 12
14 libdispatch.dylib 0x0000000197e77b40 _dispatch_root_queue_drain + 2136
15 libdispatch.dylib 0x0000000197e772dc _dispatch_worker_thread3 + 108
16 libsystem_pthread.dylib 0x000000019807d470 _pthread_wqthread + 1088
17 libsystem_pthread.dylib 0x000000019807d020 start_wqthread + 0
任意のアイデア?
あなたの個人オブジェクトは、他のCoreDataオブジェクトを参照してい:?私が思いついた解決策は
managedObjectContext
が同じだった、とだけにしてオブジェクトを更新かどうかを確認することでしたかあなたのインスタンスはかなり安全に見えますが、何らかの形で別のコンテキストで何かに接続されていますか? – deanWombourneいいえ、そうは思わない...人からの関係がありますが、このコンテキストではフォルトとしてロードする必要があります。私は確認するためにさらに見ていきます。しかし、私の感心しているのは、別のプロセスが永続ストア(およびそれを使用して、メインの管理オブジェクトコンテキスト)をリセットする可能性があるということです。潜在的に問題を説明できるでしょうか? –
@ZSそうです。 – Mundi