Supongamos que tengo un NSManagedObject personalizado Department
y esto tiene una propiedad que representa una relación de muchos a empleados, es decir, NSSet *employees;
.¿Cómo eliminar todos los objetos a través de una relación de datos centrales?
Para un departamento determinado, quiero eliminar todos los objetos en empleados. ¿Cuál es la mejor/mejor forma de hacer esto, por favor?
Así que, hipotéticamente, el código se vería así:
Department.h
@interface Department: NSManagedObject {
}
@property (retain) NSString *departmentName;
@property (retain) NSSet *employees;
@end
Department.m
@implementation Department
@dynamic departmentName;
@dynamic employees;
Employee.h
@interface Employee: NSManagedObject {
}
@property (retain) NSString *firstName;
@property (retain) NSString *lastName;
@property (retain) Department *worksIn;
@end
doCoreDataStuff
- (void)doCoreDataStuff:sender {
//add a department, give it a couple employees, then try to remove those employees
NSEntityDescription *deptEntity = [NSEntityDescription entityForName:@"Department"
inManagedObjectContext:self.managedObjectContext];
Department *dept = [Department alloc] initWithEntity:deptEntity
insertIntoManagedObjectContext:self.managedObjectContext];
NSError *error;
dept.departmentName = @"Accounting";
//save more often than normal to see more easily what causes error
if (![self.managedObjectContext save:&error]) NSLog(@"\nError: %@", [error localizedDescription]);
NSEntityDescription *empEntity = [NSEntityDescription entityForName:@"Employee"
inManagedObjectContext:self.managedObjectContext];
emp.firstName = @"Steve";
emp.lastName = @"Smith";
emp.worksIn = dept;
if (![self.managedObjectContext save:&error]) NSLog(@"\nError: %@", [error localizedDescription]);
emp = [[Employee alloc] initWithEntity:empEntity
insertIntoManagedObjectContext:self.managedObjectContext];
emp.firstName = @"Natasha";
emp.lastName = @"Johnson";
emp.worksIn = dept;
if (![self.managedObjectContext save:&error]) NSLog(@"\nError: %@", [error localizedDescription]);
//all good so far! now will try to delete all employees for this department
dept.employees = [NSSet set];
if (![self.managedObjectContext save:&error]) NSLog(@"\nError: %@", [error localizedDescription]); //"Multiple validation errors occurred."
//this also produces the same error
[[dept mutableSetValueForKey:@"employees"] removeAllObjects];
if (![self.managedObjectContext save:&error]) NSLog(@"\nError: %@", [error localizedDescription]); //"Multiple validation errors occurred."
La relación employees
no es opcional, así que supongo que la eliminación de los empleados del departamento significa que estoy tratando de "huérfanos" de los empleados, es decir, mantener a los empleados en el persistido modelo sin un departamento asociado.
Entonces, creo que mi pregunta original debe volver a redactarse: ¿cuál es la mejor/manera recomendada de eliminar todos los objetos "secundarios" de un "padre" cuando los hijos tienen una relación no opcional con el padre?
Sospecho que la respuesta será "recorrer y borrar los objetos del empleado de a uno por vez".
ACTUALIZACIÓN
De acuerdo con una respuesta y un enlace a la documentación de Apple, yo debería ser capaz de establecer la norma de supresión de "cascada" y luego un código como department.employees = [NSSet set];
funcionará. Sin embargo, esto no funciona en mi proyecto muy simple donde he configurado la regla de eliminación en consecuencia.
Gracias
me pregunto si ha encontrado una solución a ese problema? Estoy teniendo el mismo problema ... para seguir con su ejemplo, tengo un proceso de sincronización en el que intento eliminar a todos los empleados y luego crearlos desde cero (para no complicar demasiado mi sincronización) ... pero actualmente la única manera Conseguí que trabajar fuera eliminar la relación 'a muchos' para ambos lados - iterar a los empleados que llamaban a [managedObjectContext deleteObject: employee] y luego hacer un [[department mutableSetValueForKey: @ "employees"] removeAllObjects]; que simplemente parece estar mal, pero funciona ... – herbert
Nunca me salió el ejemplo de arriba para que funcione. Al final, repetí iterativamente a través de los empleados y los eliminé, como en la respuesta a continuación, acabo de aceptar como la respuesta – stifin
Usted entiende mal la documentación. Cuando ELIMINA el objeto del departamento, la regla de eliminación se aplicará a los objetos del empleado en el conjunto de empleados. Cambiar la relación no eliminará ningún objeto. – Eric