I want to implement a UI-responsive downloading and parsing of a large data set, saving it with Core Data.
My setup:
I display the downloaded content in a custom view controller. I don't use a NSFetchedResultsController.
There are 3 MOCs:
- masterMOC (responsible for saving to disk, NSPrivateQueueConcurrencyType)
- mainMOC (used by UI, NSMainQueueConcurrencyType, a child of the masterMOC)
- backgroundMOC (responsible for the import from JSON, created in a separate thread, a child of the masterMOC)
I am importing in batches - every 50 items I perform the MOC saving in the following way:
NSError *error;
[backgroundMOC save:&error];
NSManagedObjectContext *masterMOC = backgroundMOC.parentContext; //set during initialization
[masterMOC performBlock:^{
NSError *parentContextError = nil;
[masterMOC save:&parentContextError];
}];
I expect the changes in the mainMOC to be made after the masterMOC is saved. If I try to access some relationship of a random managed object while the masterMOC is saving (saving takes some time), the UI hangs until the saving is completed.
Question: how to avoid the UI freeze while the masterMOC is saving?
Your problem probably is that the data store is blocking while you are writing to it. So, either make the data store non-blocking (this may or may not be possible in your case) or if not viable, make the accessor non-blocking. In the latter case the GUI will not hang, but it also will not update either until the result of the access comes back.