April 2016

Volume 31 Number 4

[Cutting Edge]

Pushing Notifications to Mobile Apps

By Dino Esposito | April 2016

Dino EspositoIn my last few columns, I’ve written mostly about software design and architecture. While the role of architecture in the building of a software system should never be undervalued or denied, any application in the end results from the sum of individual features. It’s the same User Experience Driven Development (UXDD) philosophy that says the measure of success for a software application is in the experience the user goes through when she deals with the application. If your software system comprehends a mobile front end, then you can hardly ignore a feature like push notifications.

In this column, I’ll summarize what it takes to add a notification layer on top of mobile applications, regardless of the mobile OS itself. In doing so, I’ll review the services of the Microsoft Azure Notification Hub platform.

Push Notifications at a Glance

A push notification is when a mobile device receives a message from the application’s back end without first sending an explicit request. Most of the interactions between the client and server components of an application occur through an explicit action—typically, a user action—that solicits feedback. In a way, a push notification is a sort of unsolicited feedback, a message that the back end sends when some important information is available. To be precise, the term “unsolicited” is not completely accurate here. Any mobile application must subscribe to the available feed in order to receive push notifications. However, once subscribed to the service, notifications arrive in an unsolicited manner.

The net effect of push notifications on a user is the delivery of relevant updates whether or not he’s actively using the app. For example, installing an airliner’s app probably enables you to receive quick and timely updates on schedule and gate changes. At some point your phone beeps or vibrates and visible feedback appears somewhere on the phone’s interface. Where exactly it appears, however, strictly depends on the version of the OS on which your device is based, as well as app configuration and user settings. Depending on the OS, a push notification can take the form of an icon on the top bar, a toast message, a badge update and so on.

The crucial point of push notifications is that all of their technical aspects are rigorously platform-specific. For example, the way an application subscribes to a push notification service is different in iOS, Android, Windows Phone and Universal Windows Platform (UWP) apps. Likewise, each platform uses its own payload to deliver messages to connected devices and each platform requires you to configure a different dispatching engine. In spite of significant differences in the actual implementation, I dare say that the overall architecture of a push notification system (PNS) is quite common and looks like the diagram in Figure 1.

Overall Architecture of a Platform-Specific Push Notification System
Figure 1 Overall Architecture of a Platform-Specific Push Notification System

Working with Multiple Push Notification Systems

It comes as no surprise that the variety of mobile platforms out there also reflects in a variety of push notification platforms. A developer creating a mobile app for multiple platforms must become familiar with multiple different push notification engines and must set up a proper server environment for each. Unless you’re developing an app for a single mobile platform with no foreseeable plans to port it to other platforms, you might want to look into cross-platform PNSes, as shown in Figure 2. Compared to the diagram in Figure 1, the new architecture adds one more layer and offers a single entry point for programming.

Overall Architecture of a Cross-Platform Push Notification System
Figure 2 Overall Architecture of a Cross-Platform Push Notification System

The mobile application registers with the generic push notification hub and the application’s back end queues messages to the hub. Next, the hub delivers physical messages to the specific mobile platform using the appropriate protocol and payload. By using one of these cross-platform mobile notification systems, you can use a single API to push messages to Android, iOS and Windows Phone devices in a single shot.

The Azure Notification Hub is just one of these cross-platform notification systems. Let’s see how it works.

The Azure Notification Hub

The first step to use the Azure Notification Hub is setting up an Azure plan. The service is offered in three levels, the lowest of which is free and sets a limit in the number of reachable devices (500) and maximum notifications you can send (1 million). For more information, refer to bit.ly/1Tbimew. To get started, all you need is a free account to create a Notification Hub and a namespace in it. This information comes in handy later to establish the connection from the application’s back end to queue mes­sages for the devices.

The most cumbersome part of using push notifications isn’t dealing with a cross-platform hub, but meeting the requirements of each mobile platform you want to reach. For example, in order to deliver updates to iOS or Android devices, you must first fully configure your applications with the respective native PNSes. For more information, go to bit.ly/1o15uv2. As you may know, only registered iOS apps can receive push notifications. To register your app with the native Apple Push Notification Service you must first get a certificate from Apple that serves the purpose of uniquely identifying the notifications coming from your app. The same task for Android requires instead an API key you get through the interface of Android Studio. For UWP apps, you must first register with the Windows Store. All platform-specific steps must be accomplished for any platform you intend to support. Any registration information you get must be entered into the Azure Notification Hub, which will be acting on behalf of you with respect to the native PNSes.

Registering the Application with the Hub

Let’s say you hold a .p12 certificate file and an updated provisioning profile for your iOS application that’s enabled to receive notifications from the Apple system. You would be mostly done if you weren’t using the Azure Notification Hub. Should you really use an intermediate hub system?

The point is that any platform-specific PNS still leaves a lot of work for the devel­oper to perform commonly requested tasks such as plain broadcasting to all connected devices or just to specific groups of users such as those using the device in a particular locale. Broadcasting, in particular, is not a trivial task as it may pose nontrivial scalability issues when the number of devices grows. That’s why a scalable infrastructure in the middle that decouples core platform-specific services from the code you write is a tremendous benefit. To use the Azure Notification Hub, though, you also need to upload the Apple .p12 certificate and programmatically register your application with the Azure Hub. If you’re using Xamarin.iOS to write the iOS app, an excellent step-by-step tutorial is at bit.ly/1KaySJ3.

The mobile application has two main responsibilities. First, it needs to incorporate code that subscribes to the Azure notification feed. Second, it needs to include code to process in some way any incoming notifications. An iOS app physically receives push notifications from the Apple service so it needs to subscribe to it. This is accomplished through the UIApplication.Shared­Application.RegisterForRemoteNotifications method. Upon exit, this method invokes an overridable method in the app delegate class named RegisteredForRemoteNotifications. Here, you subscribe to the Azure Hub. This method receives the device token from the OS and your code just forwards it to the Hub. The Azure Hub is identified by path and connection string, like so:

var hub = new SBNotificationHub(connectionString, hubPath);
hub.RegisterNativeAsync(deviceToken, null);

Next, when a notification is actually received, another overridable method in the app delegate class is invoked: ReceivedRemote­Notification. The method receives from the OS the actual content of the pushed message in the form of a (possibly nested) string dictionary. The method override is responsible for extracting the actual message and displaying it through whatever works for the app—badge, sound or alert.

Queuing Messages to the Azure Hub

All the work done so far is only half the effort. What remains is figuring out how to send messages to the Azure Hub and from there down to connected devices. In other words, you need to have an application back end that knows about Hub connection details and passes the message for the user. Such an application back end can be any sort of .NET application, including an ASP.NET application. If you have a business reason for a mobile app to receive push notifications, then something in the business domain is generating related messages. It can be a software trigger to send a message or it can be the action of an admin user, as shown in Figure 3.

An ASP.NET Back End to Send Locale-Specific Messages to an iOS and Android App Via the Azure Hub
Figure 3 An ASP.NET Back End to Send Locale-Specific Messages to an iOS and Android App Via the Azure Hub

To incorporate push notifications in an ASP.NET back end, all you need is the Microsoft Azure NotificationHubs Nuget package. In addition, your code is responsible for constructing the proper connection string. A connection string contains information about the related Azure Service Bus URL endpoint and an encrypted token. The Service Bus endpoint contains the name of the namespace you created when you set up the Azure service. It’s something like sb://your-ns.servicebus.windows.net. The encrypted token is read from the configuration page of your namespace under the label “Connection String.” Here’s the code you need to create a valid Hub instance:

var hub = NotificationHubClient.CreateClientFromConnectionString(
  connString, hubName);

The next step consists of creating the proper payload for each of the platforms you want to target. The payload is a string of JSON that follows a fixed pattern. You can build the JSON string any way you like. In the following example, the $ is a placeholder for the actual message to send:

const string iosFormat = "{\"aps\":{\"alert\":\"$\"}}";
const string androidFormat = "{\"data\":{\"message\":\"$\"}}";
var iosAlert = iosFormat.Replace("$", actualMessage);
var androidAlert = androidFormat.Replace("$", actualMessage);

Once the payload is constructed, sending it to the hub is as easy as the following code:

var task1 = hub.SendAppleNativeNotificationAsync(iosAlert);
var outcome1 = task1.Result;
var task2 = hub.SendGcmNativeNotificationAsync(androidAlert);
var outcome2 = task2.Result;

The outcome variables in the code snippet are instances of the NotificationOutcome type and return detailed information about the result of the operation. 

Sending Template-Based Messages

The previous code sample shows just the simplest way of sending push notifications—a plain string of text that will be broadcast unchanged to any connected devices. Moreover, you need to format it for each mobile platform of interest. A much more common scenario is sending template-based messages. A template-based message is delivered to Azure in the form of a dictionary of string and the Azure Hub ensures it gets delivered to any mobile platform the account has configured. The key idea behind template-based messages is that the application intends to use a richer format than the default. For example, let’s see how to send different messages to users following different locales:

var locale = "EN";
var template = String.Format("{{\"aps\":{{\"alert\":\"$(News_{0})\"}}}}", locale);

The example shows the template to register with the Apple PNS any incoming template-based message named News_XX where XX is the two initial letters of a locale. The nice thing about templates here is that the application back end might send multiple entries in a single dictionary, but each device receives only the message for which it registered. This is just one of the additional services brought by an intermediate hub such as the Azure Notification Hub. To send locale-specific messages you need the following code:

var messages = new Dictionary<string, string>
  {"News_EN", "..."},
  {"News_ES", "..."},  {"News_PT", "..."},
  {"News_IT", "..."}
};var task = hub.SendTemplateNotificationAsync(messages);
var outcome = task.Result;

With a single push, you reach devices across platforms with the guarantee that each user sees just the notification appropriate for the locale he has selected on the phone. Note that this is a feature slightly different from automatic localization of messages that’s available, for example, on iOS devices. On iOS devices, in fact, you can send messages with a placeholder that maps to entries in the localized strings dictionary and the OS does the magic of automatically translating the message before calling the alert. Template messages, instead, are an Azure feature that lets you send different messages to segmented groups of users and you decide how to segment the groups of users.

Scheduled Messages

Another interesting feature you’ll find in the Azure Notification Hub is scheduled messages. Scheduled messages are notifications delivered to Azure but sent to connected devices only at a given time. To send scheduled notifications you only use a slightly different API:

var notification = new TemplateNotification(messages);
var task = hub.ScheduleNotificationAsync(notification, new DateTime(...));
var outcome = task.Result;

It’s worth noting that scheduled notifications require a Standard Tier subscription and aren’t available in the free test subscription.

Be a Good Citizen

Beyond the mere technical aspects of how to register and send push notifications via the Azure Hub, the real painful point of push notifications is using them in the context of a successful communication with the user.

You don’t want to bug the user with plain informational notifications day and night. Because it’s a “push” notification, you want to make sure there’s a real interest from the user in being pushed. In this regard, segmented groups of users are a great feature on which to rely. The size of the message does matter, too. I suggest you keep any message close to the size of a tweet. Until iOS 8, for example, the maximum size of push notifications was 256 bytes and rose to 2K in newer systems. It’s 4K on Android. Last, but not least, make sure the OS you’re targeting makes the entire feature easy to opt out. That’s mostly true with most recent OSes, but you’d better double check.

Dino Esposito is the author of “Microsoft .NET: Architecting Applications for the Enterprise” (Microsoft Press, 2014) and “Modern Web Applications with ASP.NET” (Microsoft Press, 2016). A technical evangelist for the .NET and Android platforms at JetBrains, and frequent speaker at industry events worldwide, Esposito shares his vision of software at software2cents@wordpress.com and on Twitter: @despos.

Thanks to the following Microsoft technical expert for reviewing this article: Jon Arne Saeteras

Discuss this article in the MSDN Magazine forum