-
Notifications
You must be signed in to change notification settings - Fork 13
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
6b79762
commit 9cd4b75
Showing
2 changed files
with
6 additions
and
213 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,213 +1,3 @@ | ||
# SLRESTfulCoreData [![Build Status](https://travis-ci.org/OliverLetterer/SLRESTfulCoreData.png)](https://travis-ci.org/OliverLetterer/SLRESTfulCoreData) ![Version Badge](https://cocoapod-badges.herokuapp.com/v/SLRESTfulCoreData/badge.png) ![License Badge](https://go-shields.herokuapp.com/license-MIT-blue.png) | ||
# SLRESTfulCoreData | ||
|
||
###### Objc naming conventions, autogenerated accessors at runtime, URL substitutions and intelligent attribute mapping | ||
|
||
`SLRESTfulCoreData` builds on top of [AFNetworking](https://github.com/AFNetworking/AFNetworking) and [SLCoreDataStack](https://github.com/OliverLetterer/SLCoreDataStack) and lets you map your JSON REST API to your CoreData model in minutes. Checkout [this blog post](http://sparrow-labs.github.io/2013/04/22/introducing_slrestfulcoredata.html) or [this sample project](https://github.com/OliverLetterer/GitHubAPI?source=cr) for getting started. | ||
|
||
## Getting started | ||
|
||
* Add | ||
|
||
``` | ||
pod 'SLRESTfulCoreData' | ||
``` | ||
to your `Podfile`. | ||
|
||
* Instead of subclassing `AFHTTPClient`, subclass `AFRESTfulCoreDataBackgroundQueue` | ||
|
||
``` | ||
@interface GHBackgroundQueue : AFRESTfulCoreDataBackgroundQueue | ||
@end | ||
@interface GHBackgroundQueue (Singleton) | ||
+ (GHBackgroundQueue *)sharedInstance; | ||
@end | ||
``` | ||
|
||
and register your background queue as the default background queue in | ||
|
||
``` | ||
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions | ||
{ | ||
[NSManagedObject setDefaultBackgroundQueue:[GHBackgroundQueue sharedInstance]]; | ||
... | ||
} | ||
``` | ||
|
||
* You need to provide two `NSManagedObjectContext` instances at runtime. One `NSMainQueueConcurrencyType` which will be used to display your model to the UI and one `NSPrivateQueueConcurrencyType` which will be used to updated for CoreData model with data coming from the API. Implementing a new CoreData Stack can be challenging. Therefore, SLRESTfulCoreData ships by default with the [SLCoreDataStack](https://github.com/OliverLetterer/SLCoreDataStack) dependency. You need to subclass `SLCoreDataStack`: | ||
|
||
``` | ||
@interface GHDataStoreManager : SLCoreDataStack | ||
@end | ||
@implementation GHDataStoreManager | ||
- (NSString *)managedObjectModelName | ||
{ | ||
return @"GithubAPI"; // return the name of your CoreData model here. | ||
} | ||
@end | ||
``` | ||
|
||
and register both contexts | ||
|
||
``` | ||
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions | ||
{ | ||
[NSManagedObject registerDefaultBackgroundThreadManagedObjectContextWithAction:^NSManagedObjectContext *{ | ||
return [GHDataStoreManager sharedInstance].backgroundThreadManagedObjectContext; | ||
}]; | ||
[NSManagedObject registerDefaultMainThreadManagedObjectContextWithAction:^NSManagedObjectContext *{ | ||
return [GHDataStoreManager sharedInstance].mainThreadManagedObjectContext; | ||
}]; | ||
... | ||
} | ||
``` | ||
|
||
## Attribute mappings | ||
|
||
`SLRESTfulCoreData` maps underscored API attributes to camelized objc attributes by default. That means by default `some_json_value` will be mapped to `someJsonValue` and `user_id` to `userId`. Custom attribute mappings can be registered in your `NSManagedObject` subclass's initializer: | ||
|
||
``` | ||
+ (void)initialize | ||
{ | ||
// register multiple attribute mappings at once | ||
[self registerAttributeMapping:@{ | ||
@"someJSONValue": @"some_json_value" | ||
}]; | ||
// register one attribute mapping | ||
[self registerAttributeName:@"someJSONValue" forJSONObjectKeyPath:@"some_json_value"]; | ||
} | ||
``` | ||
|
||
`SLRESTfulCoreData` supports naming conventions in case you don't want to repeat yourself in attribute mappings all the time. Therefore you can register global default naming conventions: | ||
|
||
``` | ||
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions | ||
{ | ||
... | ||
[SLAttributeMapping registerDefaultObjcNamingConvention:@"identifier" forJSONNamingConvention:@"id"]; | ||
[SLAttributeMapping registerDefaultObjcNamingConvention:@"URL" forJSONNamingConvention:@"url"]; | ||
} | ||
``` | ||
|
||
From now on, an API attribute `id` will always be mapped to `identifier` and every API attribute containing an `id` key will be mapped to an `identifier` in objc. For example `user_id` will automatically be mapped to `userIdentifier` and `some_url_value` to `someURLValue`. | ||
|
||
## Fetching objects from your API | ||
|
||
`SLRESTfulCoreData` extends `NSManagedObject` for fetching objects from your API by | ||
|
||
``` | ||
@interface NSManagedObject (SLRESTfulCoreDataQueryInterface) | ||
+ (void)fetchObjectFromURL:(NSURL *)URL | ||
completionHandler:(void(^)(id fetchedObject, NSError *error))completionHandler; | ||
+ (void)fetchObjectsFromURL:(NSURL *)URL | ||
completionHandler:(void(^)(NSArray *fetchedObjects, NSError *error))completionHandler; | ||
- (void)fetchObjectsForRelationship:(NSString *)relationship | ||
fromURL:(NSURL *)URL | ||
completionHandler:(void (^)(NSArray *fetchedObjects, NSError *error))completionHandler; | ||
- (void)postToURL:(NSURL *)URL completionHandler:(void (^)(id JSONObject, NSError *error))completionHandler; | ||
- (void)putToURL:(NSURL *)URL completionHandler:(void (^)(id JSONObject, NSError *error))completionHandler; | ||
- (void)deleteToURL:(NSURL *)URL completionHandler:(void (^)(NSError *error))completionHandler; | ||
@end | ||
``` | ||
|
||
You can use them like | ||
|
||
``` | ||
@interface GHUser : NSManagedObject | ||
+ (void)userWithName:(NSString *)name completionHandler:(void(^)(GHUser *user, NSError *error))completionHandler; | ||
@end | ||
@implementation GHUser | ||
+ (void)userWithName:(NSString *)name completionHandler:(void(^)(GHUser *user, NSError *error))completionHandler | ||
{ | ||
NSURL *URL = [NSURL URLWithString:[NSString stringWithFormat:@"/users/%@", name]]; | ||
[self fetchObjectFromURL:URL completionHandler:completionHandler]; | ||
} | ||
@end | ||
``` | ||
|
||
### CRUD for your model | ||
|
||
`SLRESTfulCoreData` ships with CRUD support for your model. Simply register a CRUD base URL | ||
|
||
``` | ||
+ (void)initialize | ||
{ | ||
[self registerCRUDBaseURL:[NSURL URLWithString:@"/repos/:repository.full_name/issues"]]; | ||
} | ||
``` | ||
|
||
and use the following methods | ||
|
||
``` | ||
@interface NSManagedObject (SLRESTfulCoreDataQueryInterface) | ||
// GET /repos/:repository.full_name/issues/:number | ||
- (void)updateWithCompletionHandler:(void(^)(id managedObject, NSError *error))completionHandler; | ||
// POST /repos/:repository.full_name/issues | ||
- (void)createWithCompletionHandler:(void(^)(id managedObject, NSError *error))completionHandler; | ||
// POT /repos/:repository.full_name/issues/:number | ||
- (void)saveWithCompletionHandler:(void(^)(id managedObject, NSError *error))completionHandler; | ||
// DELETE /repos/:repository.full_name/issues/:number | ||
- (void)deleteWithCompletionHandler:(void(^)(NSError *error))completionHandler; | ||
@end | ||
``` | ||
|
||
### URL substitution | ||
|
||
The above used key path `repository.full_name` will be transformed to the objc key path `repository.fullName` based on your registered attribute mappings and naming conventions and will be evaluated with the correct NSManagedObject instance. | ||
|
||
### CRUD for relationships | ||
|
||
`SLRESTfulCoreData` lets you register CRUD base URLs for relationships | ||
|
||
``` | ||
@implementation GHUser | ||
+ (void)initialize | ||
{ | ||
[self registerCRUDBaseURL:[NSURL URLWithString:@"/repos/:repository.full_name/issues"] forRelationship:@"issues"]; | ||
} | ||
@end | ||
``` | ||
|
||
which will implement and provide | ||
|
||
``` | ||
@interface GHRepository (CoreDataGeneratedAccessors) | ||
// GET /repos/:self.full_name/issues | ||
- (void)issuesWithCompletionHandler:(void(^)(NSArray *issues, NSError *error))completionHandler; | ||
// POST /repos/:repository.full_name/issues | ||
- (void)addIssuesObject:(GHIssue *)issue withCompletionHandler:(void(^)(GHIssue *issue, NSError *error))completionHandler; | ||
// DELETE /repos/:repository.full_name/issues/:number | ||
- (void)deleteIssuesObject:(GHIssue *)issue withCompletionHandler:(void(^)(NSError *error))completionHandler; | ||
@end | ||
``` | ||
|
||
at runtime for you. | ||
SLRESTfulCoreData has been deprecated by [CloudBridge](https://github.com/Cloud-Bridge/CloudBridge). |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters