I just found out RestKit and it will be an important part of the app I'm doing. At the time, I was able to integrate it with the core data, but have not figured out the best way to send multiple GET requests.
What I need to do is:
Get data from the following addresses:
http://url.com/api/banner/
http://url.com/api/category/
http://url.com/api/link/
The URL will always be in the following format: http://url.com/api/SOMETHING/
Once all requests are finished, I would like to run a code (such as calling a new view controller). What would be the best way to do this?
At the moment, this is the code I'm using:
- (id)init
{
self = [super init];
if (self) {
[self setupConnector];
[self setupDatabase];
[self setupMappings];
[self sendRequests];
}
return self;
}
- (void)setupConnector
{
// Initialize RestKIT
RKObjectManager *objectManager = [RKObjectManager managerWithBaseURL:[NSURL URLWithString:@"http://baseURL"]];
self.managedObjectStore = [[RKManagedObjectStore alloc] initWithManagedObjectModel:[[NLCoreData shared] managedObjectModel]];
objectManager.managedObjectStore = self.managedObjectStore;
}
- (void)setupDatabase
{
NSString *storePath = [[NLCoreData shared] storePath];
NSError *error = nil;
NSPersistentStore *persistentStore = [self.managedObjectStore addSQLitePersistentStoreAtPath:storePath fromSeedDatabaseAtPath:nil withConfiguration:nil options:nil error:&error];
NSAssert(persistentStore, @"Failed to add persistent store with error: %@", error);
[self.managedObjectStore createManagedObjectContexts];
self.managedObjectStore.managedObjectCache = [[RKInMemoryManagedObjectCache alloc] initWithManagedObjectContext:self.managedObjectStore.persistentStoreManagedObjectContext];
}
- (void)setupMappings
{
RKObjectManager *objectManager = [RKObjectManager sharedManager];
// Mappings
// banner
RKEntityMapping *bannerMapping = [RKEntityMapping mappingForEntityForName:@"Banner" inManagedObjectStore:self.managedObjectStore];
[bannerMapping addAttributeMappingsFromDictionary:@{
@"title": @"title",
@"id": @"bannerID",
@"created_at": @"created_at",
@"image": @"image",
@"resource_uri": @"resource_uri",
@"updated_at": @"updated_at",
@"url": @"url"
}];
bannerMapping.identificationAttributes = @[ @"bannerID" ];
RKResponseDescriptor *bannerDescriptor = [RKResponseDescriptor responseDescriptorWithMapping:bannerMapping
pathPattern:@"/api/v1/banner/"
keyPath:@"objects"
statusCodes:RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful)];
[objectManager addResponseDescriptor:bannerDescriptor];
// category
RKEntityMapping *categoryMapping = [RKEntityMapping mappingForEntityForName:@"Category" inManagedObjectStore:self.managedObjectStore];
[categoryMapping addAttributeMappingsFromDictionary:@{
@"name": @"name",
@"id": @"categoryID",
@"created_at": @"created_at",
@"resource_uri": @"resource_uri",
@"updated_at": @"updated_at",
@"active": @"active"
}];
categoryMapping.identificationAttributes = @[ @"categoryID" ];
RKResponseDescriptor *categoryDescriptor = [RKResponseDescriptor responseDescriptorWithMapping:categoryMapping
pathPattern:@"/api/v1/category/"
keyPath:@"objects"
statusCodes:RKStatusCodeIndexSetForClass(RKStatusCodeClassSuccessful)];
[objectManager addResponseDescriptor:categoryDescriptor];
}
- (void)sendRequests
{
RKObjectManager *objectManager = [RKObjectManager sharedManager];
// Send Request
[objectManager getObjectsAtPath:@"/api/v1/banner/" parameters:nil success:^(RKObjectRequestOperation * operation, RKMappingResult *mappingResult) {
NSLog(@"SUCCESS: %@", mappingResult.array);
} failure: ^(RKObjectRequestOperation * operation, NSError * error) {
NSLog(@"FAILURE %@", error);
}];
// category
[objectManager getObjectsAtPath:@"/api/v1/category/" parameters:nil success:^(RKObjectRequestOperation * operation, RKMappingResult *mappingResult) {
NSLog(@"SUCCESS: %@", mappingResult.array);
} failure: ^(RKObjectRequestOperation * operation, NSError * error) {
NSLog(@"FAILURE %@", error);
}];
}
Any tips?
The RestKit solution would be this: instead of using the convenience method ObjectManager::getObjectsAtPath you will have to init all of your RKObjectRequestOperations manually and then use ObjectManager::enqueueBatchOfObjectRequestOperations:progress:completion: method to enqueue them.
Alternatively, and I think this is actually easier and cleaner solution, use dispatch groups as described in the accepted answer to this question.
NSURL *url1 = [NSURL URLWithString:@"http://baseURL.domain/api/banner/"];
NSMutableURLRequest *request2 = [NSMutableURLRequest requestWithURL:url1];
RKObjectRequestOperation *objectRequestOperation1 = [[RKObjectRequestOperation alloc] initWithRequest:request2 responseDescriptors:@[ ResponseDescriptor ]];
NSURL *url2 = [NSURL URLWithString:@"http://baseURL.domain/api/category/"];
NSMutableURLRequest *request2 = [NSMutableURLRequest requestWithURL:url2];
RKObjectRequestOperation *objectRequestOperation2 = [[RKObjectRequestOperation alloc] initWithRequest:request2 responseDescriptors:@[ ResponseDescriptor ]];
NSArray *requestArray = [NSArray arrayWithObjects:objectRequestOperation,objectRequestOperation1,objectRequestOperation2, nil];
[[RKObjectManager sharedManager] enqueueBatchOfObjectRequestOperations:requestArray progress:^(NSUInteger numberOfFinishedOperations, NSUInteger totalNumberOfOperations) {
//
// Handle process indicator
//
NSLog(@"%lu",(unsigned long)totalNumberOfOperations);
} completion:^(NSArray *operations) {
//
// Remove blocking dialog, do next tasks
?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With