JMD
JMD

Reputation: 1590

Conflicting executions of the same method in separate threads?

I have a method that saves the current managed context.

But lately a bug has been appearing when inside this method. In certain locations in my program (but not all the time) it appears as if execution in this method just abruptly stops and everything quits executing... although there is no crash. The first execution works. But when I trigger the event again, the bug occurs.

If however, I insert a break point and execute the method one line at a time, everything works fine.

Basically I am getting data from a JSON connection, then saving those objects. Inside the method I save the objects, I call a 'saveManagedContext' method and this is the method the bug occurs.

- (void)saveManagedObjectContext
{ 
  NSLog(@"saving context 1");
  NSManagedObjectContext *managedObjectContext;

  // get the context for the current thread
  NSThread *currentThread = [NSThread currentThread];

  if ([currentThread.name isEqual:THREAD_NAME]) {
   NSLog(@"saving context 2");
    managedObjectContext = _backgroundQueueManagedObjectContext;
  } else {NSLog(@"saving context 3");
    //managedObjectContext = _managedObjectContext;
    managedObjectContext = [self managedObjectContext];
  }
  NSLog(@"saving context 4");
  NSError *error = nil;
  if (managedObjectContext != nil) {
    NSLog(@"saving context 5");
    if ([managedObjectContext hasChanges] && ![managedObjectContext save:&error]) {
     NSLog(@"saving context 6");
        [self logError:error];
        //abort();
    }
  }
   NSLog(@"saving context 7");
}

I have inserted an NSLog at almost every line and execution generally stops after NSLog(@"saving context 5");

This method is being called in separate threads and I have a theory it is being accessed at relatively close to the same time causing conflicts. Here are some NSLog outputs I print. Again, most of these logs occur like in the above code, under If's etc.

This log is when things execute correctly at 1 line at a time.

 connection complete 10
 connection has results
 start saving json objects
 end saving json objects
 connection complete saving context
 saving json objects thread block 1
 saving context 1
 saving json objects thread block 3
 saving context 3
 saving context 4
 saving context 5
 saving json objects thread block 4
 saving json objects thread block 6
 saving context 1
 saving context 2
 saving context 4
 saving context 5
 saving context 7
 saving context 7
 saving json objects thread block 7
 inside block 1
 inside block 2

This log is when it hangs.

connection complete 10
connection has results
start saving json objects
end saving json objects
connection complete saving context
saving context 1
saving context 3
saving context 4
saving context 5
saving json objects thread block 1
saving json objects thread block 3
saving json objects thread block 4
saving json objects thread block 6
saving context 1
saving context 2
saving context 4
saving context 5

with that said though, I've seen execution stop with different looking logs, but generally around saving context 5.

Upvotes: 0

Views: 66

Answers (1)

Ken
Ken

Reputation: 1985

Core Data isn't thread safe, see this document on CoreData concurrency:

http://developer.apple.com/library/ios/#documentation/cocoa/conceptual/CoreData/Articles/cdConcurrency.html

The easiest solution is probably to call tryLock and unlock on your NSManagedObjectContext

Upvotes: 2

Related Questions