magicalpanda / MagicalRecord

Super Awesome Easy Fetching for Core Data!
Other
10.8k stars 1.79k forks source link

AllThatIsLeftToUsIsHonor #1006

Open elviin opened 9 years ago

elviin commented 9 years ago

Hello,

I am using MR 2.2 and started my app with the argument -com.apple.CoreData.ConcurrencyDebug 1 because occasionally the app crashed with CoreData could not fulfil a fault. I get another exception with the help of the command (com.apple.CoreData.ConcurrencyDebug) from the very start I use MR:

CoreData`+[NSManagedObjectContext __Multithreading_Violation_AllThatIsLeftToUsIsHonor__]: ->  0x181c128bc <+0>: brk    #0x1

at this call

[MagicalRecord setupCoreDataStackWithAutoMigratingSqliteStoreNamed:[TSNAppPreferences standardUserDefaults].applicationStoreName]; 

exactly in

+ (NSManagedObjectContext *) MR_contextWithStoreCoordinator:(NSPersistentStoreCoordinator *)coordinator;
{
    NSManagedObjectContext *context = nil;
    if (coordinator != nil)
    {
        context = [self MR_contextWithoutParent];
        [context performBlockAndWait:^{
            [context setPersistentStoreCoordinator:coordinator];
        }];

        MRLog(@"-> Created Context %@", [context MR_workingName]); //on this line
    }
    return context;
}

Is setupCoreDataStackWithAutoMigratingSqliteStoreNamed deprecated? I should mention I also use RestKit (0.24.1). But at the moment the AllThatIsLeftToUsIsHonor exception is triggered the Restkit is not even yet initialised.

Thank you.

Alydyn commented 9 years ago

Try using v2.3.0beta5.

itsSaad commented 9 years ago

im using 2.3 release. and getting the exception when accessing a relationship on a User entity.

Alydyn commented 9 years ago

@itsSaad you are accessing an entity on the wrong queue. You need to wrap in a -performBlock: or -performBlockAndWait:. This is not a MR issue.

ryanjm commented 9 years ago

I'm getting this same error. Only started running into it after Xcode 7 / LLVM 7 on iOS 8.4 (not iOS 9 for some reason).

[MagicalRecord saveWithBlockAndWait:^(NSManagedObjectContext *localContext) {
            NSArray *cleanedResources...;

            [NSClassFromString(entityName) MR_importFromArray:cleanedResources
                                                    inContext:localContext];
}];

Any ideas why this code would run into a threading issue? This code is run in an NSOperation of it's own.

alexszilagyi commented 8 years ago

@ryanjm : have you sorted it out? Facing this issue too (iOS 8.0, XCode Version 7.2.1 (7C1002))

ryanjm commented 8 years ago

@alexszilagyi Sorry, I don't remember what I did to fix this. I've been building MR locally for a little while so I'm not sure how much of my code base is different from the main branch anymore.

elviin commented 8 years ago

I had to clean up the project from the deprecated implementations. I am using both versions of the saving methods: synchronous saveWithBlockAndWait: and asynchronous saveWithBlock:completion: exclusively.

Remove any calls using the older implementation saveUsingCurrentThreadContextWithBlock etc. Also if you need to access a CD object during the whole application lifetime you have to create a special context for this object, use it exclusively for the CD object and not to lose it.

Here is an example how to use the pair context(_transactionFilterContext) & CD(_transactionFilter) in your db interface implementation:

`      - (NSManagedObjectContext*) transactionFilterContext {

            if(_transactionFilterContext == nil) {
                _transactionFilterContext = [NSManagedObjectContext MR_context];
            }

            return _transactionFilterContext;
        }

        - (TSNLocalEntityTransactionFilter*) loadTransactionSettingsFilter {

            [_transactionFilterContext reset];
            self.transactionFilter = [TSNLocalEntityTransactionFilter MR_findFirstInContext:self.transactionFilterContext];

            if(self.transactionFilter == nil) {

                [self savePersistenStoreAndWait:^(NSManagedObjectContext *localContext) {

                    self.transactionFilter = [TSNLocalEntityTransactionFilter MR_createEntityInContext:localContext];
                    [self.transactionFilter  updateToDefaultValues];
                }];

                self.transactionFilter = [self.transactionFilter MR_inContext:self.transactionFilterContext];
            }

            return self.transactionFilter;
        }

        - (void) saveTransactionFilterWithCompletion:(MRSaveCompletionHandler)completion {

            [self.transactionFilterContext MR_saveToPersistentStoreWithCompletion:completion];
        }`