Как удалить новые объекты из NSManagedObjectContext - PullRequest
2 голосов
/ 03 апреля 2012

Хорошо, давайте начнем с кода.Я перебираю возвращенный массив словарей и создаю (или обновляю) объекты на их основе.В этом методе я пытаюсь найти или создать новую сущность.И затем, если объект должен быть удален, я бы хотел сделать это и не тратить время на обновление его новой информацией.

- (void)updateOrCreateObjectWith:(NSDictionary*)dictionary {
    RKManagedObjectStore *objectStore = ((MyAppDelegate*)[[UIApplication sharedApplication] delegate]).objectStore;

    id updateObject = (NSManagedObject*)[objectStore findOrCreateInstanceOfEntity:[resource entity] withPrimaryKeyAttribute:@"myID" andValue:[dictionary objectForKey:@"id"]];

    [updateObject setMyID:[dictionary objectForKey:@"id"]];

    // if marked for deletion, delete it now
    if ([[dictionary objectForKey:@"deleted_at"] isKindOfClass:[NSString class]]) {
        if ([updateObject isNew]){
            NSError *error = nil;
            [objectStore.managedObjectContext save:&error];
            if (error) {
                NSLog(@"error saving before delete: %@",error);
                return;
            }
//          [objectStore.managedObjectContext deleteObject:updateObject];
//          [objectStore.managedObjectCache delete:updateObject];  
        }
        else {
            [objectStore.managedObjectContext deleteObject:updateObject];            
        }
        return;
    }

    [updateObject updateWith:dictionary];
}

Часть, о которой нужно знать, - это раздел selected_at с(1) сохранить раздел, (2) удалить объект из контекста и (3) удалить объект из кэша.Я попробовал несколько комбинаций этих трех, но я не получил желаемых результатов.

Если я удаляю его из кэша (только # 3):

  • Объекты получаютсохранены, но у них нет атрибутов.

Если я удаляю его из управляемого контекста (просто # 2), я получаю:

NSUnderlyingException=Cannot update object that was never inserted.

Поскольку он никогда не вставлялся, я подумал, чтоЯ бы сохранил его, а затем удалил (# 1 и # 2), но затем я получил:

*** Terminating app due to uncaught exception 'NSObjectInaccessibleException', reason: 'CoreData could not fulfill a fault for '0xed27810 <x-coredata://4EE6AD5A-CC34-460A-A97A-0909454126A4/User/p166>''

Так, как правильно удалить «новый» объект из NSMangedObjectContext?

Ответы [ 2 ]

2 голосов
/ 04 апреля 2012

Получить экземпляр RKManagedObjectStore проще с помощью [[RKObjectManager sharedManager] objectStore] (при условии, что вы хотите использовать общий ресурс, что, как вам кажется, так как вы вызываете делегат приложения).

Проверьте наличие deleted_at, прежде чем вы создадите NSManagedObject.Этот код предполагает, что вы конвертируете в тип Resource, который является подклассом NSManagedObject.Это не проверено, но должно дать вам представление о том, что вы должны делать.

- (void)updateOrCreateObjectWith:(NSDictionary*)dictionary {
RKManagedObjectStore *objectStore = [[RKObjectManager sharedManager] objectStore];

    //get a reference to the object
    Resource *resource = [Resource findFirstByAttribute:@"myID" withValue:[dictionary objectForKey:@"id"]];

    //see if "deleted_at" exists in dictionary
    if ([[dictionary objectForKey:@"deleted_at"] isKindOfClass:[NSString class]])
    {
        //check to see if object exists in the context
        if(resource)
        {
            //if it exists, delete it
            [objectStore.managedObjectContext deleteObject:resource];
        }
    } else {
        //no "deleted at", so create the object
        if (!resource) {
            //resource is nil (it doesn't exist in the context), so we need to create it
            resource = [Resource object];
        }
        [resource updateWith:dictionary];
    }

    NSError *error = nil;
    [objectStore.managedObjectContext save:&error];
    if (error) {
        NSLog(@"error saving before delete: %@",error);
    }
}
1 голос
/ 03 апреля 2012

Вы хотите избежать создания управляемых объектов без необходимости. Лучшая стратегия - следовать этому псевдокоду:

NSManagedObject *existingObject = ...; // fetch the object
if (existingObject) {
    if (deleted) {
        [self.managedObjectContext deleteObject: existingObject];
    }
} else {
    if (!deleted) {
        // create the object, insert it into the MOC, set the object properties
    }
}
...