iosobjective-cnsurlconnectiondelegate

Multiple NSURLConnection sendAsynchronous requests with a singleton class


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.


Solution

  • 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.