Reputation: 3852
I am using a Master Detail Controller. In the Master list there are 5 items. On selecting each item, there are Asynchronous calls made.
There is one SingleTon class, which handles all network calls.
[[MyNetwokCommunication connectionInstance]
makeRequest:"url1" delegate:self];
[[MyNetwokCommunication connectionInstance] makeRequest:"url2" delegate:self];
Actual implementation in makeRequest:delegate:
is [[NSURLConnection alloc] initWithRequest:request delegate:self startImmediatley:YES]
.
So, is this a correct way to handle network connection with a singleton class, as it might over-ride data part of one request with another.
Upvotes: 0
Views: 386
Reputation: 10417
There are a lot of ways to handle it. Unfortunately, the fact that NSURLConnection can't be used as a key in a dictionary makes life particularly miserable.
The best thing to do, assuming you don't still need to support iOS 6 and earlier (or OS X v10.8 or earlier) is to ditch NSURLConnection for NSURLSession. Then use block-based calls to make the request and handle the response. Unlike NSURLConnection objects, you can use NSURLSessionTask objects as dictionary keys, which makes it easy to keep track of what data came from which request, and to store additional objects or other data associated with that request (e.g. storing the UI cell where the data should go).
If you have to use NSURLConnection to support older operating systems, you might consider subclassing NSURLRequest and adding extra data. Note that this alternative approach does not work with NSURLSession, and you'll need to provide your own redirect handler, because otherwise you'll end up getting back generic NSURLRequest objects whenever a redirect happens, IIRC. Or you can add Objective-C associated objects on the connection object. (At least I'm 99% sure that this works.)
Upvotes: 1
Reputation: 6705
That's not how I would do it.
The best paradigm on iOS to serialize things is an NSOperationQueue. You can create a queue with concurrency of 1, then queue your NSURLConnection or NSURLSession children as NSOperations.
This allows you to do neat things like create operations that are dependent on the success of other operations.
Here's the creation of the queue:
@property (strong, nonatomic) NSOperationQueue *queue;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
_queue = [[NSOperationQueue alloc] init];
[_queue setMaxConcurrentOperationCount:1];
});
Then to create a network operation:
// HTTPOperation.h
#import <Foundation/Foundation.h>
@interface HTTPOperation : NSOperation
@end
//
// HTTPOperation.m
//
#import "HTTPOperation.h"
@implementation HTTPOperation
- (void) main
{
NSURLRequest * urlRequest = [NSURLRequest requestWithURL:[NSURL URLWithString:@"http://google.com"]];
NSURLResponse * response = nil;
NSError * error = nil;
NSData * data = [NSURLConnection sendSynchronousRequest:urlRequest
returningResponse:&response
error:&error];
if (error == nil)
{
// Parse data here
NSLog(@"Completed successfully");
}
}
@end
To execute the operations:
- (IBAction)queueHTTP {
HTTPOperation *op = [HTTPOperation new];
[self.queue addOperation:op];
}
You can queue as many as you want from anywhere and they will execute serially. I recommend watching the WWDC video on Advanced NSOperations:
https://developer.apple.com/videos/wwdc/2015/?id=226
It was very informative.
Upvotes: 0