NSURLConnection vs. NSData + GCD NSURLConnection vs. NSData + GCD ios ios

NSURLConnection vs. NSData + GCD

You are losing a lot of functionality here:

  • Can't follow the download progression
  • Can't cancel the download
  • Can't manage the possible authentication process
  • You can't handle errors easily, which is really important especially in mobile development like on iPhone of course (because you often lose your network in real conditions, so it is very important to track such network error cases when developing for iOS)

and there's probably more I guess.

The right approach for that is to create a class than manages the download.

See my own OHURLLoader class for example, which is simple and I made the API to be easy to use with blocks:

NSURL* url = ...NSURLRequest* req = [NSURLRequest requestWithURL:url];OHURLLoader* loader = [OHURLLoader URLLoaderWithRequest:req];[loader startRequestWithCompletion:^(NSData* receivedData, NSInteger httpStatusCode) {    NSLog(@"Download of %@ done (statusCode:%d)",url,httpStatusCode);    if (httpStatusCode == 200) {        NSLog(%@"Received string: %@", loader.receivedString); // receivedString is a commodity getter that interpret receivedData using the TextEncoding specified in the HTTP response    } else {        NSLog(@"HTTP Status code: %d",httpStatusCode); // Log unexpected status code    }} errorHandler:^(NSError *error) {    NSLog(@"Error while downloading %@: %@",url,error);}];

See the README file and sample project on github for more info.

This way:

  • you still rely on the asynchronous methods provided by NSURLConnection (and as the Apple's documentation says about Concurrency Programming if an API already exists to make asynchronous tasks, use it instead of relying on another threading technology if possible)
  • you keep advantages of NSURLConnection (error handlings, etc)
  • but you also have the advantages of the blocks syntax that makes your code more readable than when using delegate methods

WWDC 2010 Session Videos:

  • WWDC 2010 Session 207 - Network Apps for iPhone OS, Part 1
  • WWDC 2010 Session 208 - Network Apps for iPhone OS, Part 2

The lecturer said

"Threads Are Evilâ„¢".

For network programming, it is strongly recommended to use asynchronous API with RunLoop.

Because, if you use NSData + GCD like the following, it uses one thread per connection.

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void) {    NSData* data = [NSData dataWithContentsOfURL:someURL];

And it's likely to use many connections and many threads. It is too easy to use GCD :-)Then, many threads eats huge amount of memory for its stack.Thus, you'd better to use asynchronous API as AliSoftware said.

As of OS X v10.9 and iOS 7 the preferred way is to use NSURLSession. It gives you a nice, block-based interface and features like canceling, suspending and background downloading.