Building a Notification Hub for Windows Phone on top of Windows Azure Mobile Services

For most applications, notifications are not exactly critical. Granted, a scientific calculator will not benefit from having an in-app notification hub. On the other hand, there are cases when you want to let the user know about what’s new and what changes before an update or including information in the changelog. That’s where a custom notification hub control can come in really handy.

What goes into a notification?

Before jumping to actual coding, let’s think about what actually should go in a notification. We obviously want to display the information in the form of the simplest message possible. A title and a description should do it. But a notification also usually implies that there is some action tied to it, be it opening another application or a third-party location. So maybe including a URI would be another valid addition. All in all, we end up with this layout:

image

Fantastic. You can see that there are two extra properties that I haven’t mentioned – Id and TimeStamp. Since Azure Mobile Services are used, one of the core ways to determine the identity of an entity is by its unique integer identifier in the data table – Id takes care of holding the proper value. The TimeStamp property might not carry a unique value, but will tell the user when the notification was created. Ultimately, in the application itself it is possible to set filters to only show notifications from a given date range, but that’s a different topic.

In C# code, the class above will look like this:

using Microsoft.WindowsAzure.MobileServices;
using System;

namespace Hilltop.CoreTools.Models
{
  [DataTable("notifications")]
  public class Notification
  {
    public int? Id { get; set; }
    public DateTime TimeStamp { get; set; }
    public string Title { get; set; }
    public string Content { get; set; }
    public string Url { get; set; }
  }
}

Notice the reference to Microsoft.WindowsAzure.MobileServices – make sure you install the Azure Mobile Services Windows Phone SDK in order to be able to use it. I personally prefer using NuGet for this, so feel free to use this command to get the package:

PM> Install-Package WindowsAzure.MobileServices

The Core Control

Now that there is a defined notification model, I can start working on the core control itself. I’ll start by defining the skeleton via a INotificationCenter interface:

 using System.Threading.Tasks;

namespace Hilltop.CoreTools.Interfaces
{
  interface INotificationCenter
  {
    void Initialize();
    void GetCurrent();
    void Clear();

    Task CreateNotification(string title, string content, string url);
  }
}

GetCurrent will handle the acquisition of the current notification stack, Clear will erase all existing notifications and CreateNotifications will help the developer create notifications directly from the app.

SECURITY NOTE: It is important to remember, however, that notification creation should probably be secured – the way the notification hub control works, it provides a unified “connector” to the service and it is up to the developer to have the proper separation of roles and capabilities available to different app user categories.

Without going into the boring details of dependency property registration, here is what the ultimate class for the NotificationCenter control will look like:

image

Notice that I have MobileService declared in the Fields section. This is nothing else but the core managed Azure Mobile Services client. By default, it is null:

 public static MobileServiceClient MobileService = null;

We have an entire set of properties that determine the appearance of the notification entity in the global notification list. It is possible to set the icon associated with a given notification (usually taken from the context of the application itself but can be remote as well) as well as the colors for the content displayed.

Most important, however, is to have these two properties: ZumoKey and ZumoUrl. These will be used by the managed client to connect to the specific Azure Mobile Service instance and retrieve the data.

When the control is loaded in the visual tree, a call to Initialize (this is not the same as InitializeComponent) is made, that will try to connect to the service and retrieve any pending notifications:

 public void Initialize()
{
    if (!string.IsNullOrWhiteSpace(ZumoKey))
    {
        if (!string.IsNullOrWhiteSpace(ZumoUrl))
        {
            MobileService = new MobileServiceClient(ZumoUrl, ZumoKey);

            GetCurrent();
        }
        else
        {
            throw new InvalidOperationException("Missing ZUMO URL.");
        }
    }
    else
    {
        throw new InvalidOperationException("Missing ZUMO key.");
    }
}

When it comes to GetCurrent, it will simply populate the Notifications collection with the data returned by AMS:

 public async void GetCurrent()
{
    if (MobileService != null)
    {
        try
        {
            var data = await MobileService.GetTable().ToListAsync();
            Notifications = new ObservableCollection(data);
        }
        catch
        {
            // Failed to obtain the list of current notifications.
        }
    }
}

Post-initialization, we want to let the user know that the control is ready, so I’ve added the Ready event handler. Here is how it will be invoked once the control has finished the first iteration of the loading routine:

 void NotificationCenter_Loaded(object sender, RoutedEventArgs e)
{
    Initialize();

    if (Ready != null)
    {
        Ready(this, new EventArgs());
        this.Loaded -= NotificationCenter_Loaded;
    }
}

Great. However chances are that at this point you don’t have any notifications available. CreateNotification would be exactly what you need:

 /// 
/// Allows notification insertion directly from the client app.
///
///Notification title.
///Notification content.
/// TRUE if insertion is successful. FALSE if not.
public async Task CreateNotification(string title, string content, string url)
{
    Notification notification = new Notification();
    notification.Content = content;
    notification.Title = title;
    notification.TimeStamp = DateTime.Now;
    notification.Url = url;

    if (MobileService != null)
    {
        try
        {
             await MobileService.GetTable().InsertAsync(notification);
             return true;
        }
        catch
        {
             return false;
        }
     }

     return false;
}

Thanks to the amazing work done by the Windows Azure Mobile Services team, all you really need to do is create a new instance of the Notification model and push it to the aforementioned MobileService client.

As I also mentioned earlier, we’d want the notification to be interactive and actually point to some sort of a resource, that is represented with the help of the Url property. To do this, we handle the notification item selection in the list:

 private void NotificationSelected(object sender, SelectionChangedEventArgs e)
{
    if (e.AddedItems.Count > 0)
    {
        Notification notification = (Notification)e.AddedItems[0];

        WebBrowserTask task = new WebBrowserTask();
        task.Uri = new Uri(notification.Url);
        task.Show();
    }
}

The WebBrowserTask will use the built in browser (Internet Explorer) to open the associated page. Simple as that.

What do I need to set up in the AMS dashboard?

Not a whole lot. First of all, make sure that you create a new table that has the same identifier as the DataTable attribute in the Notification class. In the example above, I am using notifications as the name, and it is used like that in production with Beem and EnTrance:

image

During development, you might also want to enable Dynamic Schema:

image

SECURITY NOTE: It is important to disable dynamic schema before your app goes in production.

How do I use the control?

Use the standard XAML syntax in one of your pages:

 <ht:NotificationCenter NotificationIcon="/Images/notification.png" ZumoUrl="YOUR_URL" Ready="NotificationCenter_Ready" ZumoKey="YOUR_KEY" AbsentNotificationsColor="White"></ht:NotificationCenter>

And there you go:

wp_ss_20131103_0001

You can download the source code for the control here (ZIP file).

 

DI.FM in a New Dimension – Beem Plus 2.0 is Out

At this point in time, Beem Plus has established itself as the de-facto DI.FM client for Windows Phone, although unofficial. With more than 45,000 downloads all over the world, I feel like this project is filling its niche pretty well. That being said, I don’t want to have the app “frozen”, so updates are a crucial part in delivering a better user experience and additional capabilities that would make the listening experience as streamlined as possible. So here it is – Beem 2.0.

I am proud to say that this release is by far the most stable and fast, but the focus was more on improving discoverability and ease-of-use. The motto for the 2.0 release was “Simplify, simplify” (quoting Thoreau on this one). Take a look at the 1.9 main page:

5716f4c2-d760-43f0-956f-37f910c859ce

Although seemingly nice and well-organized, there is no structure to where a station should be. Let’s say you want to find Dubstep. Or Trance. Or maybe Progressive. What is the first idea that comes to mind when you need to look it up? Probably just scroll through the list and hope that you are lucky enough to stumble across what you were looking for. I wanted to eliminate this pain. With 2.0, no matter what – you will always get an alphabetized list of all stations:

2013-10-02 12.40.35

Neat. Notice that it’s clear and to the point – you know what to find and where to find. The same happened to the list of favorites. For comparison purposes, 1.9 content is on the left, and 2.0 is on the right:

2013-10-02 12.50.01 2013-10-02 12.40.41

First and foremost what comes into play is consistency. I noticed that the station description does not really add much value to the UI, specifically to the Favorites section because the users that have added a specific station to the list are already well-aware of what that stream will be about. There are a couple of extra changes here too. There is no longer the tap-and-hold option for either the main station list or the Favorites list. As analytics have shown, that is a capability that is barely used, mainly because of discoverability problems – people simply don’t know that you can tap-and-hold to get the ability to pin a station to the Windows Phone start screen or to add/remove it from favorites. So instead, this ability went away. But don’t be alarmed – it is still present in playback mode. Which brings us to the next set of changes – the “now playing” screen.

Let’s compare the amateur 1.9 build versus the pro 2.0 build:

d08e8af9-b444-4a19-83e3-769ff4962f67 2013-10-02 12.41.06

Whoa! On the left, there is an absolute information overload. What does the bag icon do? Is the pin going to add this station to favorites or actually get me out of Beem Plus and pin it to the home screen? Instead, I removed all that clutter to let the user focus on what’s important – the station that’s being played and the tracks in it. You can still record and add the station to favorites from the playback bar, but the rest is now hidden in the application bar, with a bit more context sprinkled on them:

2013-10-02 12.41.11

In addition to that, Beem Plus now supports an additional sharing option – via NFC, which stems from another added feature – bookmarked tracks. If you look at one of the 2.0 screenshots above, you will notice that the list of tracks is now easier to tap on, with clearly separated data related to the artist and track name. Once you tap on the track, the user will be able to select a couple of options:

2013-10-02 12.41.21

The track can be searched for on Xbox Music or Nokia Music (even on non-Nokia Windows Phone devices), giving the user the ability to purchase a song that he or she liked on that specific station. But there is also a star “Save” button, that gives the ability to simply bookmark the track and keep it in a personalized list:

2013-10-02 12.40.45

With NFC activated, you can share the currently playing track and send it to another Windows Phone device running Beem Plus 2.0 – once tapped, the track that was just shared will become a bookmark that can be later used to find it in any of the supported stores. I’d like to mention that Beem Plus does not offer track download capabilities – it merely keeps the track metadata that later will help you identify the channels where it can be obtained.

In addition to visual changes, Beem Plus 2.0 includes multiple bug fixes, reducing the possibility of the app crashing during a stream to a minimum. It still supports Last.fm scrobbling and SkyDrive uploads of the recorded streams for backup purposes. You can get the app in the Windows Phone Store, free as always. Also keep in mind that Beem is an open-source project, available on GitHub. If you’d like to provide criticism, feedback or suggestions – feel free to stop by the Issues Hub.

A State of Trance Podcast Fans on Windows Phone – I Present You EnTrance

After a sleepless weekend, here is the final product – EnTrance. It’s not really a big secret that I am a fan of EDM and A State of Trance is, hands down, in my opinion one of the best trance shows there is. With this in mind, I realized that there is way for me to easily managed the ASOT podcast on the device. Need creates ideas, so I though about building my own client that would let me aggregate the latest and greatest podcast episodes, with information about the collected tracks as well as with the ability for me to find those on Xbox Music, Nokia Music and YouTube.

Hence, EnTrance came to life.

EnTrance

What can it do at the moment? Pretty much everything you would expect a podcast app to do – download and play ASOT episodes. What I have planned for it is another question. Here is a short breakdown:

  • Upload to SkyDrive – what if you like an episode so much that you want to have it stored on your machine as well? Simply push it to SkyDrive and the deed is done – once your PC(s) sync the changes, you will find the episode in your folder.
  • Push Notifications – get alerts when new ASOT episodes are released and when new track information is available.
  • ASOT Full Show Integration – other than the podcast, every Thursday Armin van Buuren runs his ASOT radio show. Despite the fact that the episode itself is often not available for download, it contains track metadata. I want to show you that track metadata – with the ability to find those later on Xbox Music, Nokia Music or YouTube.
  • Event Information – ASOT 650 is coming up and I need to get the app ready for it.

It would be very short-sighted to say that this list is complete. It’s not, and will never be – such is software. If you have more ideas, feel free to stop by at the Issues Hub on GitHub (did I mention EnTrance is open-source?).

For now, pick up your Windows Phone 8 and download the app!