Logic High Software Blog

So I heard that blocks were one of the new features of 4.1 and I decided to give it a try. And it’s awesome! Within half an hour I’d solved a problem that I’d had to make much more complicated implementations to solve previously, and I’m so excited I decided I’d share the code.

Problem: NSURLConnection asynchronous connections are ugly. If you want to have one controller make multiple different calls you have to make unique delegates for each call or have some convoluted way for the connection manager to tell one delegate from another. It’s a real mess.

Solution: BLOCKS!

Step 1: Create NSURLConnection block extension that allows for calling async methods from class API like you would sync method.

14 Comments

I should comment… seems blocks are a little more work then I’d originally hoped. While this will work in some places, NSThread is a lot of overhead, and using a Singleton connection manager is probably a more efficient way to go. Additionally, when you are using values in blocks, it’s important to make sure they are in scope (make copies of parameter variables) and to check for the existence of those variables before calling them. Otherwise nasty, hard to track errors can occur with nested blocks.

@Kevin Lohman: actually the blocks should be copied in only one case (but that’s a big case): if the block is supposed to be live beyond the scope in which it’s created (it’s the case in asynchronous operations like here), the block MUST be copied to the heap or you will get a crash for sure. And the code in this blog post is bound to crash.

Short explanation: blocks are allocated on the stack for optimization purpose, when the function returns the stack is cleaned up and the block dies out. The block has to be moved to the heap to exist beyond the scope, at that point it works like any other ObjC objects.

When the block is still on the stack, -retain doesn’t do anything to the object, -retain must always return the receiver, that’s part of the semantic, thus sending retain to a block (like what NSDictionary is doing) won’t copy it to the heap. It has to be copied explicitly, you can then autorelease it because the dictionary will retain the block, in this case it works properly because -retain on a heap block increase its retain count just like normal ObjC objects.

Misleading title. Making a Synchronous network call on background thread doesn’t make it asynchronous. You are blocking thread that makes synchronous request and waits for response, if the server takes several minutes to reply back your thread is blocked until then.

As Marcelo Cantos stated, much better solution is to wrap this in NSURLConnections’ asynchronous model. YOu get more functionality, and speed. i wrote URLConnection, it’s easy to use and add to your project. Find the link to it below:

FYI — Code here is mostly to demonstrate blocks, and is actually a really terrible way to do async connection handling (it spawns a new thread for EACH connection, bad memory management). A better solution is to use NSOperationQueue to handle it… or better still check out Apple’s NSURLSession (iOS developers only until iOS 7 goes live).

Absolutely. This was an example of making your own method with Blocks… At the time there wasn’t much on the web about them, but Apple is thankfully using it more and more (though the syntax can still get confusing and hard to write off the top of your head)