Friday, March 20, 2009

iPhone OS/SDK 3.0: Remote Notifications

If you are an iPhone developer, you were probably excited about Apple revealing a beta of OS 3.0 and the corresponding beta of SDK 3.0. There was a lot of excitement and speculation over what new features would be available in 3.0. One of the most anticipated ones was Push Notifications. Everyone thought that Apple would release this since they had promised it in the past, and they were right. So how do you use it? That was the question I asked myself, and here is what I have been able to figure out so far from the documentation.

The first thing you need to do is have your application call the new API registerForRemoteNotifications. This a new API on UIApplication. So when you create your app's delegate (i.e. the class that conforms to the UIApplicationDelegate protocol) you will probably want to invoke registerForRemoteNotifications in your applicationDidFinishLaunching: method (or in the application:didFinishLaunchingWithOptions: method, more on that later.) This will cause the UIApplication to send a request to the Apple Push Service (APS) and it will respond with a token.

When the UIApplication receives that token, it will invoke your app delegate's application:didRegisterForRemoteNotificationsWithDeviceToken:. As the name implies, you get a token as one of the parameters to this method. Your application needs to send this token to your servers. When your server then determines that a notification needs to be sent to a particular device, it will send a request to APS using this token. That is how APS knows where to send the notification to, and also what application the notification is being sent to. It looks like you are pretty limited in what you send to APS, i.e. you do not send (much) application data to APS. You just send it a message saying "hey tell this device that I've got something waiting for it." APS will send this to the user's device.

So the notification arrives, and now there are two possibilities. First, the user is still using your application. In that case, your app delegate is once again invoked, this time it's application:didReceiveRemoteNotification: method is invoked. This lets your app know that you need to phone home to your server and go get the new yummy data.

If your application was no longer active, i.e. that pesky user quit it so they could do something else, then the user will receive a pop-up asking them if they want to launch your application because a notification has been sent to it. If they choose to do so, then when you application launches the app delegate's application:didFinishLaunchingWithOptions: method will be invoked.

In both cases, the delegate will receive an NSDictionary representing the notification as the last parameter passed in. Again, it appears that what can be in this dictionary is pretty limited as its max size is 256 bytes. You can put some custom stuff, like maybe some enum value to represent what kind of notification it is, or an ID to use as a request to get more information.

That is pretty much it! It is fairly straightforward, pretty close to how many people imagined this would work.


Michel-Ange said...

Hi! Just to let you know that we released today javapns, a Java implementation of the Apple Push Notification Service, under LGPL.
See for more.

raj said...

When my application is not running, I receive a push notification, my applicaition launches but I don't see the dictionary. But if my application is running and remote notification is received, I see the dictionary.

Any ideas why I am not able to see the payload.