Intro
This is a lightweight ActiveRecord way of managing Core Data objects.
The syntax is borrowed from Ruby on Rails.
And yeah, no AppDelegate code.
It's fully tested with Kiwi.
Usage
- Install with CocoaPods or clone
#import "ObjectiveRecord.h"
in your model or .pch file.
Create / Save / Delete
Person *john = [Person create];
john.name = @"John";
[john save];
[john delete];
[Person create:@{ @"name" : @"John", @"age" : @12, @"member" : @NO }];
Finders
// all Person entities from the database
NSArray *people = [Person all];
// Person entities with name John
NSArray *johns = [Person where:@"name == 'John'"];
// And of course, John Doe!
Person *johnDoe = [Person where:@"name == 'John' AND surname == 'Doe'"].first;
// Members over 18 from NY
NSArray *people = [Person where:@{
@"age" : @18,
@"member" : @YES,
@"state" : @"NY"
}];
// I wanna be fancy and write my own NSPredicate
NSPredicate *membersPredicate = [NSPredicate predicateWithBlock:^BOOL(Person *person, NSDictionary *bindings) {
return person.isMember == YES;
}];
NSArray *members = [Person where:membersPredicate];
Custom ManagedObjectContext
NSManagedObjectContext *newContext = [[NSManagedObjectContext alloc] initWithConcurrencyType:NSPrivateQueueConcurrencyType];
newContext.persistentStoreCoordinator = [[CoreDataManager instance] persistentStoreCoordinator];
Person *john = [Person createInContext:newContext];
Person *john = [Person where:@"name == 'John'" inContext:newContext].first;
NSArray *people = [Person allInContext:newContext];
Custom CoreData model or .sqlite database
If you've added the Core Data manually, you can change the custom model and database name on CoreDataManager
[CoreDataManager instance].modelName = @"MyModelName";
[CoreDataManager instance].databaseName = @"custom_database_name";
Examples
// find
[[Person all] each:^(Person *person) {
person.member = @NO;
}];
for(Person *person in [Person all]) {
person.member = @YES;
}
// create / save
Person *john = [Person create];
john.name = @"John";
john.surname = @"Wayne";
[john save];
// find / delete
[[Person where: @{ "member" : @NO }] each:^(Person *person) {
[person delete];
}];
Mapping
The most of the time, your JSON web service returns keys like first_name
, last_name
, etc.
Your ObjC implementation has camelCased properties - firstName
, lastName
.
Since v1.2, camel case is supported automatically - you don't have to do nothing! Otherwise, if you have more complex mapping, here's how you do it:
// just override - mappings in your NSManagedObject subclass
// this method is called just once, so you don't have to do any caching / singletons
@implementation Person
- (NSDictionary *)mappings {
return @{
@"id": @"remoteID",
@"mmbr": @"isMember",
// you can also map relationships, and initialize your graph from a single line
@"employees": @{
@"class": [Person class]
},
@"cars": @{
@"key": "vehicles",
@"class": [Vehicle class]
}
};
// first_name => firstName is automatically handled
}
@end
Testing
ObjectiveRecord supports CoreData's in-memory store. In any place, before your tests start running, it's enough to call
[[CoreDataManager sharedManager] useInMemoryStore];
Roadmap
- NSIncrementalStore support