NSFetchedResultsController does not update TableView after UIManagedDocuments receives new data

I use NSFetchedResultsControllerin conjunction with UIManagedDocumentwhich is updated in the background thread.

I set up NSFetchedResultsController exactly as described in this tutorial: How to use NSFetchedResultsController

I set the delegate _fetchedResultsController.delegate = selfand protocol for my view controller NSFetchedResultsControllerDelegate.

My code works fine when it loads data after launch. However, it NSFetchedResultsController does not update the TableView whenever it has processed and stored data in the background thread. In particular, the delegation methods of NSFetchedResultsController -controllerWillChangeContent:controller, etc. never called.

I double checked that the SQLite database contains the data correctly. This is how I process and save data in the view controller:

[backgroundContext performBlock:^{
        [company parseAttributesFrom:xmlStr inManagedObjectContext:backgroundContext]; //self.managedDocument.managedObjectContext

        NSError *error = nil;
        [backgroundContext save:&error];
         if (error) NSLog(@"error: %@",error.localizedDescription);
        [self.managedDocument.managedObjectContext performBlock:^{
            NSError *error = nil;
            [self.managedDocument.managedObjectContext save:&error];
            if (error) NSLog(@"error: %@",error.localizedDescription);
        }];
        [self.managedDocument saveToURL:self.managedDocument.fileURL forSaveOperation:UIDocumentSaveForOverwriting completionHandler:NULL];
        [self.managedDocument updateChangeCount:UIDocumentChangeDone];
    }];

How can I get NSFetchedResultsController to update the TableView automatically when the underlying data changes?

Thank you for your help!

+1
source share
2 answers

I think the reason is managedObjectContext. You make changes in the background and NSFetchedResultsControllerchoose from the main one. So you need to merge the changes into one context by adding an observer about the changes in the context

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(contextChanged:) name:NSManagedObjectContextDidSaveNotification object:nil];

- ) , . http://www.cimgf.com/2011/08/22/importing-and-displaying-large-data-sets-in-core-data/

+2

, UIManagedDocument, .

backgroundContext = [[NSManagedContext alloc] initWithConcurrencyType:NSPrivateQueueConcurrencyType];
backgroundContext.parent = self.managedDocument.managedObjectContext;

, , , , . , UIManagedDocument, "" , ChangeDone.

[backgroundContext performBlock:^{
    [company parseAttributesFrom:xmlStr inManagedObjectContext:backgroundContext]; //self.managedDocument.managedObjectContext

    NSError *error = nil;
    [backgroundContext save:&error];
     if (error) NSLog(@"error: %@",error.localizedDescription);

    // NOTE: Now, the changes have been pushed into the main context of your document.
    // DO NOT call save directly on the managed document context.
    [self.managedDocument.managedObjectContext performBlock:^{
        [self.managedDocument updateChangeCount:UIDocumentChangeDone];
    }];
}];

, , .

+1

Source: https://habr.com/ru/post/1777971/


All Articles