Reputation: 967
I have a core data entity, "Entity 1" it has a one to many relationship lets call it "entityRelationship" to another entity "Entity 2".
I'd like to be able to perform a NSFetchRequest for use with a NSFetchResultsController to return the list of "Entity 2" objects for a specific "Entity 1" object.
I have the "Entity 1" stored out as it's own variable, but i can't seem to find the correct way to set up an NSPredicate to return the objects:
Here's my code:
NSFetchedResultsController *fetchedEvents;
NSFetchRequest *fetchRequest;
NSError *error = nil;
fetchRequest = [[NSFetchRequest alloc] initWithEntityName:@"Entity2"];
[fetchRequest setPredicate:[NSPredicate predicateWithFormat:@"Entity2 IN self = %@",entity1Object]];
[fetchRequest setSortDescriptors:@[]];// no sort descriptors
fetchedEvents = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:theManagedObjectContext sectionNameKeyPath:nil cacheName:nil];
[fetchedEvents performFetch:&error];
if (error) {
NSLog(@"Unable to perform fetch.");
NSLog(@"%@, %@", error, error.localizedDescription);
}
return fetchedEvents;
This crashes with the following error:
** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Unable to parse the format string "NSMDEvents IN self = %@"'
Am i doing something wrong? Or is this the incorrect way to go about returning entities with relationships?
Upvotes: 1
Views: 904
Reputation: 967
Trying the suggested code (thanks vadian) kept causing my app to crash with various errors regarding keys not existing etc, this turned out to be down to a relationship issue.
"Entity2" was inheriting from another entity (had its parent Entity field set in the Data Model Inspector)"Entity 0". However the relationship between "Entity1" was between itself and "Entity0" not "Entity2".
So after a rejig of the core data model "Entity2" had a relationship added (lets call it "EntityEvents") between itself and "Entity1". Now using the following code i was able to select the specific events from the current object:
NSFetchedResultsController *fetchedEvents;
NSFetchRequest *fetchRequest;
NSError *error = nil;
fetchRequest = [[NSFetchRequest alloc] initWithEntityName:@"Entity2"];
[fetchRequest setPredicate:[NSPredicate predicateWithFormat:@"EntityEvents == %@",Entity1]];
[fetchRequest setSortDescriptors:@[]];// no sort descriptors
fetchedEvents = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:theManagedObjectContext sectionNameKeyPath:nil cacheName:nil];
[fetchedEvents performFetch:&error];
if (error) {
NSLog(@"Unable to perform fetch.");
NSLog(@"%@, %@", error, error.localizedDescription);
}
return fetchedEvents;
Upvotes: 0
Reputation: 285059
Since you have entity1Object
and the defined relationship, you can retrieve the Entity2
objects directly from there
NSSet *entity2Objects = [entity1Object valueForKey:@"entityRelationship"];
An extra fetch is not needed.
But if you really need the fetch define a reverse relationship and use a property with an unique value.
For example let's assume that entity1
are clubs
and entity2
are their members
and you want to get all members for a specific club use this predicate:
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] initWithEntityName:@"Member"];
[NSPredicate predicateWithFormat:@"club.name == %@", currentClub.name];
The literal club
in the predicate is the reverse relationship object.
Or translated to your example
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] initWithEntityName:@"Entity2"];
[NSPredicate predicateWithFormat:@"entity1.property == %@", entity1Object.property];
Upvotes: 0