How should Asynchronous Networking be handled? This is quite a common question in various places, starting from interviews to forums like Stackoverflow. Yet, this is not a question to be answered in a sentence. There are several ways with their own strengths and weaknesses. This article is a humble effort to outline them all.
NSURLConnection Approach – New approach
The most modern of the approaches would be to use
Following is an example of the usage of the method:
This approach has the following benefits:
- This does away with the repetitive code that handles intermediate results
- Race conditions are avoided which sometimes occur if using NSURLConnection delegates, as some of the part of the delegate gets prematurely released. The block here is retained
- In case of multiple asynchronous request, the code for handling each of the response is cleanly separated and thus less chance of mixup
But all these good things comes with a price tag.
- You lose some control over the operations. Imagine the scenario when you will need to cancel the download of a large chunk of data. In the above implementation, there is no way you can actually cancel the request without leaking memory.
You can probably try cancelling the NSOperation within the queue that is sent as a parameter to the method, but that does not necessarily cancel the operation. It merely marks the operation as cancelled so that when you query the isCancelled property of the operation you get back a positive. But you will have to cancel all your activities yourself based on this isCancelled flag.
- As stated in the first beneficial point, you can not handle intermediate results.
- With this approach when a request is made, it either fails or succeeds, and it fails even for authentication challenges.
NSURLConnection – Traditional Approach
Then there is the traditional approach where we implement the
NSURLConnectionDelegate methods and initiate the request with
NSURLRequest. A quick example follows:
One benefit of using the traditional approach with NSURLConnection is that you get to handle authentication challenges through delegates. Though handling authentication challenges properly might be a lengthy and difficult, but it is nonetheless possible.
Following is the delegate method which handles authentication challenge:
But if there are multiple requests, then in the authentication challenge handler it becomes difficult to understand for which request the authentication challenge is thrown.
A Better Approach – NSURLSession
As we discussed both of the above approaches has their pros and cons. So, Apple has come up with an approach which takes the best of both. This is the approach with
Block based approach
Delegate based approach
Finally, the best approach in my humble opinion, would be to use AFNetworking, or RESTKit. There are other third party APIs too, like MKNetworkKit etc. I have not used MKNetworkKit by Mugunth Kumar, but the other two are really good when it comes to asynchronous networking and a myriad of other related features.
With AFNetworking, the above task can be performed as:
AFNetworking also allows to track progress with multipart request. The following is an example of an upload task with progress indicator: