I have a NSFetchedResultsController
that managed my UITableView
data source.
I am trying to modify a property of a NSManagedObject
called amountToCompute
using a NSBatchUpdateRequest
. So I create the batch update:
let batchUpdate = NSBatchUpdateRequest(entityName: "MyEntity")
batchUpdate.propertiesToUpdate = ["amountToCompute" : newAmount]
batchUpdate.resultType = .UpdatedObjectIDsResultType
I execute it:
var batchError: NSError?
let batchResult = managedContext.executeRequest(batchUpdate, error: &batchError) as! NSBatchUpdateResult?
And to update my current managed context, I update each managedObject in the managedContext and perform a new fetch of fetchedResultsController
:
if let result = batchResult {
let objectIDs = result.result as! [NSManagedObjectID]
for objectID in objectIDs {
let managedObject: NSManagedObject = managedContext.objectWithID(objectID)
if !managedObject.fault {
managedContext.refreshObject(managedObject, mergeChanges: true)
}
if !fetchedResultsController.performFetch(&error) {
println("error: + \(error?.localizedDescription), \(error!.userInfo)")
}
}
}
I implemented some methods of the delegate NSFetchedResultsControllerDelegate
to manage changes in the results sent by the NSFetchedResultsController
:
func controllerWillChangeContent(controller: NSFetchedResultsController) {
tableView.beginUpdates()
}
func controller(controller: NSFetchedResultsController, didChangeObject anObject: AnyObject, atIndexPath indexPath: NSIndexPath?, forChangeType type: NSFetchedResultsChangeType, newIndexPath: NSIndexPath?) {
switch type {
...
case .Update:
reloadRowsAtIndexPaths([indexPath!], animation: reloadRowsWithAnimation)
let myManagedObject = anObject as! MyManagedObject
println("update : \(myManagedObject.amountToCompute)")
...
}
}
func controllerDidChangeContent(controller: NSFetchedResultsController) {
tableView.endUpdates()
}
I run the app on my 8.4 iOS simulator and everything goes fine.
println("update : \(myManagedObject.amountToCompute)")
prints the new value.
I run the app on my iPhone 6 8.4.1 and the value is not updated, println("update : \(myManagedObject.amountToCompute)")
prints the old value. The new value is saved properly but the changes don't appear in my table view while they do on the simulator.
What's wrong? How come it can be different whether I'm on the simulator or on my device. The versions are not exactly the same but I doubt Apple touched Core Data architecture in their last update.
This is a an unusual, but known problem that I ran into myself and spent a couple of days pulling out my hair until found this blog post, which worked for me.
https://stevenpsmith.wordpress.com/2011/08/12/nsfetchedresultscontroller-and-core-data-managed-object-updates/
It boiled down to adding this single line of code that set the staleness interval to zero:
[context setStalenessInterval:0];
If I'm reading your post right you're having the same issue. :)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With