2

MagicalRecord를 사용하고 있지만 MagicalRecord 또는 CoreData의 버그인지 확실하지 않습니다.변경 사항이 인식되지 않음 배경 스레드에 연결된 NSFetchedResultsController

나는 사용자가 새로운 버튼을 클릭하면 내 UI 스레드에서 새로운 엔티티를 생성하고이 기본 컨텍스트에 저장됩니다 :

- (IBAction) saveToCoreData:(UIButton *)sender { 
    NSManagedObjectContext *context = [NSManagedObjectContext MR_defaultContext]; 
    Report *report = [Report MR_createInContext:context]; 
    report.dirty = [NSNumber numberWithBool:YES]; 
    report.timestamp = [NSDate date]; 

    Document *document = [Document MR_createInContext:context]; 
    document.dirty = [NSNumber numberWithBool:YES]; 
    document.timestamp = [NSDate date]; 
    document.report = report; 

    NSLog(@"Saving................................."); 
    [context MR_saveToPersistentStoreWithCompletion:^(BOOL success, NSError *error) { 
     NSLog(@"Saved report and document to PS"); 
    }]; 
} 

공지 사항 나는 문서가

를 부착 자녀와 보고서의 실체를 그런 다음 변경 사항을 수신 할 책임이있는 백그라운드 스레드가 있습니다. 보고서가 변경되면 더티 == 예, 그러면 서버에 제출해야합니다.

백그라운드 스레드에 NSFetchedResultsController를 설정하여 변경 사항을 수신하면 서버에 저장할 때 알 수 있습니다.

- (void)controller:(NSFetchedResultsController *)controller didChangeObject:(id) anObject atIndexPath:(NSIndexPath *) indexPath forChangeType:(NSFetchedResultsChangeType)type newIndexPath:(NSIndexPath *) newIndexPath { 
    switch(type) { 

     case NSFetchedResultsChangeInsert: 
      NSLog(@"report inserted"); 
      [self pushReport:anObject]; 
      break; 
     case NSFetchedResultsChangeUpdate: 
      NSLog(@"report updated"); 
      [self pushReport:anObject]; 
      break; 
    } 
} 

을 서버에 밀어 :

// This should get me a new background context, use it in FRC below 
    self.fetchedResultsController = [Report MR_fetchAllSortedBy:@"timestamp" 
                 ascending:NO 
                withPredicate:[NSPredicate predicateWithFormat:@"dirty == YES"] 
                 groupBy:nil 
                 delegate:self 
                 inContext:_managedObjectContext]; 

그럼 내가 변경을 수신하는 방법을 구현

- (void) pushReport:(Report *) report { 
    __weak ReportPushService *weakSelf = self; 
    AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager]; 
    [manager GET:@"http://echo.jsontest.com/" parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) { 
     [weakSelf.managedObjectContext performBlockAndWait:^{ 
      report.remoteId = @"12345"; // fake id from server 
      report.dirty = [NSNumber numberWithBool:NO]; 

      [weakSelf.managedObjectContext MR_saveToPersistentStoreWithCompletion:^(BOOL success, NSError *error) { 
       NSLog(@"Saved server info to Report"); 
      }]; 
     }]; 
    } failure:^(AFHTTPRequestOperation *operation, NSError *error) { 
     NSLog(@"Error: %@", error); 
    }]; 
} 

FRC는 마치 마법처럼 작동 및 UI 스레드를 추가 할 때 지저분한 새 보고서 == 예 : FRC가 그것을 집어 서버에 제출합니다.

여기 내가 문제가되는 곳입니다. 보고서가 서버에 저장되면 서버는 해당 보고서의 ID를 반환합니다. 나는 그것을 report.remoteId로 설정했다.

나는 문서를 서버에 저장하는 책임이있는 다른 클래스에 FRC가 있습니다. ! 그것은 즉, 더러운 == YES와 그것이 부모 (보고서) remoteId = 전무 문서를 확인합니다 :

self.fetchedResultsController = [Document MR_fetchAllSortedBy:@"timestamp" 
                 ascending:NO 
                withPredicate:[NSPredicate predicateWithFormat:@"report.remoteId != nil && dirty == YES"] 
                 groupBy:nil 
                 delegate:self 
                 inContext:_managedObjectContext]; 

그것은 보고서 "푸시"클래스에서 FRC 컨트롤러와 같은 배경 MOC를 사용합니다.

내가 그 FRC의 변경을 수신! 나는 내가 remoteId 보고서를 가지고 있다는 것을 확인하는 경우에도,

- (void)controller:(NSFetchedResultsController *)controller didChangeObject:(id) anObject atIndexPath:(NSIndexPath *) indexPath forChangeType:(NSFetchedResultsChangeType)type newIndexPath:(NSIndexPath *) newIndexPath { 
    switch(type) { 
     case NSFetchedResultsChangeInsert: 
      NSLog(@"document inserted"); 
      [self pushDocument:anObject]; 
      break; 
     case NSFetchedResultsChangeUpdate: 
      NSLog(@"document updated"); 
      [self pushDocument:anObject]; 
      break; 
    } 
} 

자신의 FRC는 변경 사항을 볼 수 없습니다 그러나 = 전무와 (자식) 문서로 더러운 == 예.

왜 문서 FRC는 해당 술어와 일치하는 객체를 보지 못합니까?

+1

당신은 UI 스레드에서 MOC의'NSManagedObjectContextDidSaveNotification'을 관찰하고 백그라운드 스레드에서 MOC에 변화를 병합합니까? – bluedome

+0

MOC를 설정하는 방법과 스레드를 관리하는 방법을 설명해야합니다 (항상 MOC의 올바른 스레드에 있고 MOC 전반에 병합 된 변경 사항이 있습니까) – Wain

+0

오작동하는 NSFetchedResultsController가 반입을 수행합니까? 올바른 컨텍스트에 있습니까? 모든 필수 위임 메서드가 구현되고 NSFetchedResultsController의 대리자가 설정 되었습니까? – quellish

답변