Search code examples
iosobjective-ccore-datansmanagedobjectcontextmagicalrecord

Exec Bad Access on using MagicalRecord when saving objects


I have encountered a problem on using MagicalRecord when saving objects.

saving the context using:

    - (void)saveContext {
    [[NSManagedObjectContext defaultContext] saveToPersistentStoreWithCompletion:^(BOOL success, NSError *error) {
        if (success) {
            NSLog(@"You successfully saved your context.");
        } else if (error) {
            NSLog(@"Error saving context: %@", error.description);
        }
    }];
}

this cause cause my app randomly crashes with EXEC_BAD_ACCESS on [[self MR_defaultContext] mergeChangesFromContextDidSaveNotification:notification];

I have used another methods:

//get correct order based on indexPath
Order *orderToComplete = [self objectInOrdersAtIndex:indexPath.section];
//set order as completed
[MagicalRecord saveWithBlock:^(NSManagedObjectContext *localContext)
 {
     Order *localOrder = [orderToComplete inContext:localContext];
     [localOrder setIsCompletedValue:YES];
 }completion:^(BOOL success, NSError *error)
 {
     if(success)
         NSLog(@"You successfully saved your context.");
     else
         NSLog(@"Error saving context: %@", error.description);
 }];

but still randomly crashes.

my app is not a multithreaded app. here is a shot: enter image description here

Does anyone have any idea?


Solution

  • I could fix my problem. But couldn't find the exact reason.

    steps you should follow

    1. clear all the code in target method and just create an object and save it? does save? if so:
    2. add your code and step by step test it you can find it where in you code, the managedObjectStore will go to inconsistence state. for me it was because of calling delegate method. I put [NSManagedObjectContext saveContext] after delegate method calling. it fixed

    Im using version 2.2 I could find where problem happens but I couldn't understand why! but here am I doing: a new Item will be pushed to device from network, so if it is the first record the cell should automatically be selected. then I call the detailsView controller delegate setItems to update its item. after that KVO will notify about changes and tries to update the tableView: imagine there is no record, a new item will be pushed to the device and its subItems will be added to detailsViewController via a delegate method

    self.subItems = subItems;

    landscape

    steps : 1- update view 2- save context

    the delegate method calls twice in every push. then KVO notices there is a change in subItems NSKeyValueChangeSetting after second push if second push contains new subItems KVO for the first time notices there is an insert in item subItemsNSKeyValueChangeInsertion , then as I said delegate method calls twice, KVO notice there is a change NSKeyValueChangeSetting. at this step after reloading table app crashes!

    NSNumber *kind = [change objectForKey:NSKeyValueChangeKindKey];
            //if we are setting new items to the items array; i.e. when we select a new row
            if ([kind integerValue] == NSKeyValueChangeSetting) {
                // adding the all the new items at top of the tableView
                NSArray *newItems = [change valueForKey:@"new"];
                [self.tableView reloadData];
    
            }
            //if we are adding one new order to the orders array
            else if ([kind integerValue] == NSKeyValueChangeInsertion)
            {
                // adding the new order at top of the tableView
                [self.tableView insertSections:[NSIndexSet indexSetWithIndex:0] withRowAnimation:UITableViewRowAnimationTop];
            }
    

    at last I tried the delegate called once to solve this crash. but I couldn't understand why the above error happens!

    https://github.com/magicalpanda/MagicalRecord/issues/877