2015-09-28 5 views
5

Привет, ребята У меня проблема с NSBatchDeleteRequest, кажется, что невозможно удалить ссылки ссылок.NSBatchDeleteRequest не удаляет отношения

У меня есть две сущности:

  • Новости
  • Категории

где категория может иметь несколько новостей.

Теперь, когда я пытаюсь удалить все объекты в основных данных с помощью NSBatchDeleteRequest со следующим кодом, тогда поиск в файле sqlite кажется, что все категории удалены, все новости удалены, но взаимосвязь между категориями и новостями сохраняется, и это вызывает ошибки.

Здесь функция удаления:

NSFetchRequest *fetchRequest = [NSFetchRequest fetchRequestWithEntityName:entityName]; 
NSBatchDeleteRequest *delete = [[NSBatchDeleteRequest alloc] initWithFetchRequest:fetchRequest]; 
[delete setResultType:NSBatchDeleteResultTypeCount]; 
NSError *error; 
NSBatchDeleteResult *results = [deleteContext executeRequest:delete error:&error]; 

Любая идея о том, как это исправить?

+0

Какое правило вы используете? – Shizam

+0

@Shizam Я использую Nullify – Serluca

+0

Сколько записей?Менее 10.000? Вы также можете использовать граф объектов. – Mundi

ответ

4

shouldDeleteInaccessibleFaults: до YES и недостижимые/неисполняемые неисправности будут удалены. Это решает ближайшую проблему.

Сеанс WWDC 2015 Что нового в Core Data говорит об этом немного. Оба NSBatchDeleteRequest и NSBatchUpdateRequest изменяют постоянное хранилище без участия NSManagedObjectContext, что приведет к тому, что контекст будет отображаться несовместимыми с хранилищем данными.

Копия удаленного объекта в памяти должна быть обновлена ​​в NSManagedObjectContext - попросите пакетный запрос удаления вернуть идентификаторы объектов удаленных объектов и сообщить NSManagedObjectContext, чтобы обновить эти идентификаторы.

Это будет выглядеть примерно так:

[managedObjectContext performBlock:^{ 
    NSBatchDeleteRequest batchDeleteRequest = [NSBatchDeleteRequest alloc] initWithFetchRequest:fetchRequest]; 
    NSBatchDeleteResult  result    = nil; 

    result = [managedObjectContext executeRequest:batchDeleteRequest error:&error]; 

    if ([[result result] count] > 0){ 
     [managedObjectContext performBlock:^{ 
      NSArray<NSManagedObjectID *> *objectIDs = (NSArray<NSManagedObjectID *>)[result result]; 
      [objectIDs enumerateObjectsUsingBlock:^(NSManagedObjectID *objID, NSUInteger idx, BOOL *stop) { 
       NSError *error = nil; 
       NSManagedObject *obj = [managedObjectContext existingObjectWithID:objID error:&error]; 
       if (![obj isFault]) { 
        [managedObjectContext refreshObject:obj mergeChanges:YES]; 
       } 
      }]; 
     }]; 
    } 
}]; 

Когда партия удаления прогонов, отношения будут удалены или аннулированы, но каскадный набор правил удаления не может быть выполнен, и правило проверки не будет выполнены - ваше приложение должно обеспечить целостность данных при использовании любого из запросов на изменение партии.

Ваша модель данных может потребовать, чтобы вы выдавали несколько запросов на удаление, чтобы не допустить, чтобы связанные объекты были потеряны, но все еще можно найти. Например, вам может понадобиться второе удаление пакета для поиска ранее связанных объектов, которые теперь имеют пустые отношения. Предикат для такого запроса может выглядеть следующим образом:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"[email protected] == 0"];

Или может использовать подзапрос и т.д.

+0

Привет, @quellish, к сожалению, не работает, я обновляю объекты, вызывающие refreshAllObjects в контексте после удаления. Я знаю, что это зависит от приложения, но если я удалю оба объекта, у меня нет ссылки, то удалить связь – Serluca

+0

Кажется, необходимо установить: 'batchDeleteRequest.resultType = NSBatchDeleteResultTypeObjectIDs' , чтобы это работало, иначе result.result по умолчанию - статус, т.е. успех/сбой. –

0

Я думаю, что лучшим решением может быть первым или удалить категории в графе объектов, тем самым сводя на нет все отношения.

После этого вы можете перейти к NSBatchDeleteRequest для новостей.

3

Возможно, вы можете сделать [manageObjectContext reset];

Смежные вопросы