Chris Risner . Com

Windows Azure Mobile Services and iOS

Posted on: 8/30/2012 4:23:00 PM by

Update 10-16-2012 We've now released native iOS SDK for Windows Azure Mobile Services. You can read more about it here.

As mentioned yesterday by me, and half the internet, Windows Azure Mobile Services has been launched.  Already people have started talking about how fast and easy it is to use Mobile Services as a backend.  One thing that I highlighted and that others have pointed out is that official support for iOS, Android, and Windows Phone 8 is coming.  This means that if you want to download and install pre-built REST helper methods for your non-Windows 8 operating system, you’ll have to wait.  However, since all of the calls to Mobile Services are being done over HTTP and are REST based, it’s pretty easy to see what each call sends over the wire.  This means that we can take that information and write our own code that will run on iOS and Android and hit Mobile Services. 

Today, I’ll start to show you how to do just that.  In this article, we’ll walk through creating a new Mobile Service and then connecting an iOS client to it.  We’ll only use some basic data capabilities provided by Mobile Services but in the coming weeks, I’ll show you how to watch the HTTP calls made by a Windows 8 app (so you can figure out what’s going across the wire) and then how to reproduce some of the more advanced things in both iOS and Android.  By the end of this walkthrough, we’ll have reproduced in an iOS client, all of the capabilities of the initial Todos Windows 8 Mobile Services demo. You’ll be able to add new todos, list those todos, and mark todos complete.  Let’s get started. 

If you want to dive into the source code without going through the whole tutorial, you can access the source code on GitHub.

 

Creating a new Mobile Service

In order to create a Mobile Service, you first need to have a Windows Azure account.  You can sign for a free trial here.  This free trial is good for three months of access.  Once you’ve done that, log into your account, and go to the Account Center.  From there, access the preview features area of the site.  There you’ll see a button to “try it now”. 

Try Mobile Services Now

Go ahead and request access to that and you should be granted access within a short period. Once that is done, go to the portal at http://manage.windowsazure.com.  Once you’re logged in to the (awesome HTML5) portal, you’ll see a list of available offerings on the left side.  We’re specifically interested in Mobile Services:

Mobile Services in Portal

At the bottom left of the site, you’ll see a big Plus with “New” next to it.  Click on that and go to Mobile Services and then Create:

New Mobile Service

You’ll then be able to specify the subdomain of your site and choose whether you want to use an existing SQL database or create a new one.  You also get to select a region, but for now only the East US is enabled:

Create Mobile Service

You’ll then be able to specify database settings.  If you’ve already created one mobile service and a SQL Database Server, you won’t be able to create a new one.  You can create a new SQL database but you will be limited to a single server (under the free preview mode at least).  So if this is your first time through this, create a new SQL Database server, and if not, either use your existing database, or create a new SQL database.

New DB Settings

One other note about this screen.  When you create a SQL Database Server for the first time, REMEMBER YOUR USERNAME AND PASSWORD.  Write it down somewhere or store it in a password program.  If you want to add a new database to your server, you’ll need the credentials you first used to create the server.  When that’s done, click the checkmark and your new mobile service will be added to your list and will show itself as being created:

Creating the Site

After a few moments, you should see the site switch over to running:

Site Running

Now, if you tap on the URL on the right side, you’ll be taken to the default placeholder page:

Mobile Service HomePage

Now, you can’t change that page but remember that the mobile service endpoint is just an endpoint.  It’s not meant to also serve up a web page that you can change.  Going back to the portal, click on the site (where it says “mymobileservice” in the image above the web page) and you’ll go to the dashboard for your service.  The dashboard will let you know that your site is created and give you some instructions to get started.

Mobile Service Dash

Today, we’re not going to have anything to do with Windows 8.  Let’s go directly to the DATA tab in the links at the top.  When you do, you’ll be told you have no tables.  Click “Add a Table” to create a new one.  We’re going to name this table “TodoItem" and leave all the permissions as the default:

new mobile service table

When that’s done, click the checkmark and the table should show up under your list of tables.  We only have one thing left to do and that is get our app key.  In the links at the top of the portal, go to “Dashboard”.  At the bottom, you’ll see a button to “Manage Keys”.  Go ahead and click on that.

Manage Keys

In the modal that pops open, you’ll see the “Application Key”.  Copy that value down for later.

access keys

That’s all you need to do on the server side.  Now we can start working on the good stuff!

The Windows 8 Client?

If you have a computer running Windows 8 as well, I would suggest following the instructions for creating “a new Windows 8 application” seen above.  We’ve already created the table, but following those steps will enable you to download a Visual Studio solution that is 100% ready to run and you can see how the basic todos app runs.  It’s not necessary for proceeding with the iOS client, but it means that you can already have a few todos in your database.  Either way, we can proceed to the iOS client now.

Starting the iOS Client

Start up Xcode and create a new project.  For this demo, we’ll just create a Single View Application.  You can name your project whatever you want (I’ve named mine, “mymobileservice”).  Start by going into the MainStoryboard.storyboard.  You should see the default storyboard with a single view controller. 

Storyboard Starting

Let’s start by dragging a table view from the control selector in the bottom right of Xcode, into the center of the view.  With that done, drag a table view cell onto your table view.  When you’re done, your view should now look like this:

tableview with cell

Next, while still in the storyboard, click on the assistant editor button (the tuxedo or alien face button) to see both the storyboard and the code behind.  Now control click on the table view and drag over to the area between @interface and @end.  This should enable you to create a new outlet for your tableview:

new outlet in storyboard

We’ll name our outlet “tableView”.  Now, close the assistant editor and control click and drag on the table view again, but this time go to the View Controller inside of the View Controller Scene and let go. 

Connecting the table view delegate

This will enable you to specify that the view controller will handle the datasource and delegate methods for the tableview.  Make sure you do this twice and select both.  The last step in the storyboard for now is to click on the prototype cell you’ve added to the tableview and change it’s Identifier property in the Attributes Inspector to be “Cell” and the Accessory to “Disclosure Indicator”.  Next, let’s open up ViewController.h.  Here, you need to note that ViewController will implement UITableViewDelegate, UITableViewDataSource, and NSURLConnectionDelegate.  Finally, we’ll add a private NSMutableData field to our class.  When you’re done, your class header will now look like this:

 

Now before we switch over to the ViewController.m file, let’s create a separate file to store some constants.  Go to the File menu, choose New and then File.  Select Objective-C class and name the class Constants and have it subclass NSObject.  We’ll use this class for storing some URL and app specific constants that we’ll use throughout the project.  Open the Constants.h file and edit it to match the following:

 

Next let’s define those values in Constants.m:

 

You’ll want to replace “yoursubdomain” with the URL you’ve set up for your site and the app ID with the key you pulled out of the Manage Keys modal earlier on.  Let’s stop for a second and take a look at these URLs.  This is our first insight into how Mobile Services works.  kGetAllUrl has at the end /tables/TodoItem which corresponds to the TodoItem table we created earlier.  After there is a query string parameter to specify a filter.  Here, we’re telling it to only pull back todo items which have a complete flag of false.  If we dropped the filter, we’d get back all the todo items.  kAddUrl and kUpdateUrl are the nearly the same, however, the update url has the slash at the end.  The reason for this is that when we  create, we just need to specify which table we’re going to create something in.  If we update, we need to include the ID of the item we’re updating in the query (after the slash).  Now, we can switch over to the ViewController.m file and make some magic happen.  The first method we need to change is viewDidLoad. Here, we’ll just call another method that will handle loading our todos.

 

Now we'll implement that method:

 

The only thing really interesting here is that we’re sending over the application key as a header named X-ZUMO-APPLICATION.  If you don’t send this to Mobile Services (code named Zumo prior to launch) then you’ll receive back a 401 unauthorized error from the server.  The next set of methods we need to implement are those required by implementing the NSURLConnectionDelegate delegate.  First, let’s jump over to AppDelegate.h and add a property to keep track of our todos. 

 

Here, we’ve added a NSArray property to store our todos.  In the AppDelegate.m we just need to synthesize that property. 

 

Now let’s hop back over to ViewConnection.m and add the NSURLConnectionDelegate methods.

 

The first few methods (didReceiveResponse, didReceiveData, and didFailWithError), don’t really do anything special (in comparison with any other call to NSURLConnection).  In connectionDidFinishLoading we actually do something with the data that we’re pulling back.  Specifically, we use NSJSONSerialization to deserialize the data into a NSArray.  We then get a reference to the AppDelegate and set the previously created todos property to be equal to the array we pulled back.  Finally, we tell the tableview to reload it’s data.  Our last step, for displaying the todos, is to implement the UITableViewDataSource and UITableViewDelegate methods.  These methods are called when we reload the tableview. 

 

Now if you run your application, you won’t see anything (unless you also ran the Win8 program first and created Todos).  Before we can see any todos, we need to be able to add  them.  Let’s next work on the view controller that will allow us to add and mark todos complete.  Then we’ll come back and wire it up to ViewController.m.  Go to the File menu and choose New and then File.  Pick Objective-C class and click next.  Name it TodoDetailsViewController and make it subclass UIViewController.  Before we do the code behind, let’s go back to MainStoryboard.storyboard and set up our UI.  Drag a new View Controller from the control window on to the storyboard.  We’re going to add two subviews: one for adding a new todo, and one for showing the details and marking a todo complete.  Then we’ll add a few controls to that.  Let’s see what the finished version looks like:

Todo Details View

Note that the top half and bottom half both have a View on them.  We’ll hide or show each view depending on if we’re looking at the details of a todo or if we’re adding a new one.  On the top half (for adding a new todo) we have a label just to display some information (like “Todo Text”), a text field for entering the todo’s text, and a button for saving the todo.  In the second half (for viewing details) we have a label for displaying the todo text and a button for marking the todo complete.  Before you can open the Assistant Editor, you need to connect this with the TodoDetailsViewController we created a moment ago.  Select the view in the storyboard editor and open the Identity Inspector, select the drop down for class and choose TodoDetailsViewController.

setting view controller class

Now that that is done, open the Assistant Editor.  We need to create IBOutlets for both of the views, the text field in the top half, and the label in the bottom half.  We also need to create IBActions for both buttons. We are also going to create a new TodoDetailsViewControllerDelegate protocol.  We’ll use this as a way to make a call back into the original ViewController later.  TodoDetailsViewController will make use of NSURLConnection, so it will also implement NSURLConnectionDelegate.  Lastly, we’ll add a few private fields and three other properties for the todo text, a bool for indicating if we’re adding a new todo or not, and a delegate instance of TodoDetailsViewControllerDelegate.  When we’re done, our TodoDetailsViewController.h should look like this:

 

Next we’ll go and wire things up in the TodoDetailsViewController.m file.  First we need to synthesize a few of the properties we added to the .h:

 

Next, we’ll add some code to the viewDidLoad method.  Here, we’ll check to see if we’re adding a new todo or looking at an existing one.  Depending on which one it is, we’ll hide one of our subviews.  If we’re looking at an existing todo, we’ll look up the todo ID and set the text in the label.

 

Next, let’s implement the tapSaveTodo method.  Again, you’ll see we’re setting the X-ZUMO-APPLICATION header.  We’re also specifying the ACEEPT and Content-Type headers.  This is because we’re going to both send and receive JSON.  We create a NSDictionary and put the JSON data into it for our todo item which includes the text and a complete flag (to specify that the item isn’t complete).  Beyond that we’re doing a NSURLConnection and NSMutableURLRequest  to send data to the server.  Now, let’s implement the NSURLConnectionDelegate methods:

 

Here we need to look at two method (the rest are the same as the earlier NSURLConnectionDelegate methods): didReceiveResponse and connectionDidFinishLoading.  In the didReceiveResponse method, we’re setting the private httpResponse variable to be equal to the response variable sent into the method.  In conectionDidFinishLoading, we look at that status code.  If it’s a 200 or a 201, we pop off the view controller (this view will be in a NavigationController so popping will work) and call the didFinishTodo method on the delegate.  We’re calling this in case of both a 200 or a 201 because we want to handle the response for creating a new todo or updating one.  In the case that we didn’t receive either a 200 or 201, we show a UIAlertView.  Now we only have one method left to define:  tapMarkTodoComplete.  This method will handle updating a todo to be complete:

 

This is very similar to what we did in the tapSaveTodo method.  The only two differences are that when we generate the URL, we are putting the Todo ID at the end of it, and we’re setting the complete flag to be true when we put it in JSON.  When this call to NSURLConnection is complete, it calls the same NSUrlConnectionDelegate methods we already generated.  Now we’re ready to wire this view controller up in the storyboard so open up MainStoryboard.storyboard.  Select the initial view controller and go to the Editor menu, choose Embed In, and select Navigation Controller.  Here we’re going to generate two segues from the first view controller and the TodoDetailsViewController.  Zoom in on the first view controller and select the cell in the table view.  Control + Click and drag over to the second view controller.  When given the option to select a segue, choose Push

Segue Selection

Select the segue icon (it should be in the middle of the line running between your two view controllers) and in the Attributes Inspector, give it an Identifier of “viewExistingTodo”.  This segue will be for when a todo in our list is tapped on.  Go back to the first view controller and drag a Bar Button Item from the control selector (bottom right of the screen) onto the top right of your view controller (inside the Navigation Bar).  In the Attributes Inspector choose the Identifier drop down and select “Add”.  Control + Click and drag from that button over to your second view controller again.  Choose push and give this one an Identifier of “AddNewTodo”.  When you’re done, you’re storyboard will look a bit like this:

Updated Storyboard

Now we need to handle what happens when a segue occurs.  Open ViewController.m and add the following code:

 

The last thing we need to do is implement the TodoDetailsViewControllerDelegate inside the ViewController.  First open the ViewController.h file and add the delegate to the list of implemented classes:

 

Next, go to ViewController.m and add the following code to the bottom of your class to define the didFinishWithTodo method.

 

Now if you run your application and hit the plus in the navigation bar, you should be able to add a new todo.  When you do, it should take you back to your list.

Todo Added

If you tap on a todo, you should be taken to the screen where you can mark it complete.  After doing so, you should return to the tableview and have that todo removed.  We’ve just duplicated all of the initial data capabilities of the Todos Mobile Services tutorial. 

 

Source Code

You can access the source code from this walk through on GitHub.  Just remember that after you’ve pulled it down, you’ll need to change a few things in the Constants.m file.  Specifically, you need to enter your subdomain in the three URLs and your app ID in the fourth constant. 

 

Conclusion

While official support for anything except Windows 8 is coming, you don’t have to wait to make use of Windows Azure Mobile Services.  As seen here, the Mobile Services end points are just looking for data to come across in JSON format and only expect you to send over a single additional header (X-ZUMO-APPLICATION).  Today we’ve only looked at a small piece of what you can do with data, as there is much more.  I’ll tackle some of those more advanced things in the coming weeks.  I’ll also go through how to inspect the HTTP traffic going across the wire from a Windows 8 app so you can see what’s going and how to call into Mobile Services.  As a reminder, if you’re looking to test out Mobile Services, sign up for a free Windows Azure account here.

Bookmark and Share
First Article

iOS and Windows Azure Communication using SignalR

Posted on: 8/2/2012 7:53:00 PM by

Windows AzureUPDATE: Get a free trial for Windows Azure Websites here.

A few weeks ago, I was talking with one of my teammates, Brady, about server to client communication and he introduced me to SignalR.  SignalR is a library to facilitate asynchronous communication from a server to a client (as opposed to from a client to a server).  If you haven’t heard about SignalR yet, I would highly recommend watching Brady’s presentation from a DevCamp in Arizona.  If you’d rather skip the video, we can just say that the goal of SignalR is to make persistent HTTP connections super easy.  What that means is that instead of just one way communications from a client to the server, the server would be able to communicate with the client really easily.  Today we’ll look at how to create the server side component in .NET and how to consume it from either JavaScript or, more importantly, Objective-C.

An Example Hub

So let’s take a look at this in action.  If you navigate to http://msdpe-signalrconnect.azurewebsites.net/HitCounter.html you’ll see an example of SignalR in action.  I’ll warn you, at the time of writing, SignalR runs a little slow in Windows Azure Websites (as opposed to Cloud Services or a VM) but remember that all of this stuff is in preview / pre-release.  So open that URL in a few different browser windows.  If you want the full affect, then cascade each browser window so you can see the text update as you refresh one of them.  This site is just a simple hit counter that keeps track of how many times the web page has been hit.  Hit it once and it will say “This site has had 1 hit.”  Hit it again and that updates to 2.  If you’ve cascaded a few browsers with that page open, then you’ll see that when you refresh one of them, it will update them all.  The code for this is actually incredibly simple and can be found on GitHub.  This is actually the sample code that Brady made for the presentation mentioned above.  Opening this (in Visual Studio 2012 Beta), you will see several solution folders.  The only thing we’re concerned with is the Basics/BasicExamples project.  There are actually two “endpoints” here:  UserCounterConnection and HitCounterHub.  Today we’re just going to look at the hit counter.  If you open up Hubs/HitCounterHub.cs you’ll see the following code:

    [HubName("hitCounter")]
    public class HitCounterHub : Hub
    {
        static int _hitCount;

        public void addHit()
        {
            _hitCount += 1;
            Clients.showHitCount(_hitCount);
        }
    }

Once you’ve included the proper libraries, that’s all you need to do to set up a SignalR Hub.  This hub has one method that clients can call on it: addHit.  That method adds to an internal counter and then calls showHitCount on all of the connected clients.  Now all we have to do is implement a client that uses this.  Let’s start with JavaScript.

The JavaScript Client

If you open up HitCounter.html, you’ll see how amazingly simple it is to connect to the hub:

    <div id="currentHitCount"></div>

    <script type="text/javascript">
        $(function () {
            var hub = $.connection.hitCounter;
            $.extend(hub, {
                showHitCount: function (hitCount) {
                    if (hitCount > 1) {
                        $('#currentHitCount')
                            .html("This site has had " + hitCount + " hits.");
                    }
                    else {
                        $('#currentHitCount')
                            .html("This site has had " + hitCount + " hit.");
                    }
                }
            });
            $.connection.hub.start(function () {
                hub.addHit();
            });
        });
    </script>

First you get an instance of the hitCounter hub.  Then you extend that hub to handle the showHitCount method.  That method just updates the currentHitCount div which is above the javascript.  Last, you start the hub and call addHit on the hub once it’s finished starting.  There really isn’t much more to say about this but that it’s easy. 

For the purposes of this demo, I created a new website in the Windows Azure portal.  Once that site is provisioned, you just need to publish the BasicsExample project to the website.  For an example on setting up a new Windows Azure Website and pushing a site up to it, check out this walkthrough I posted a couple weeks ago.  The walkthrough uses GIT to push the code to the server, however, since this is a .NET site, you could more easily do it using Web Deploy (look for “Deploy the application to Windows Azure”).  With that done, we can  get into the iOS stuff now.

The iOS Client

Now if you had to implement the SignalR backend in Objective-C, you wouldn’t be reading this article because I wouldn’t have written it.  Thankfully, someone has already gone through the hard work of doing that for us.  Released by a team from a company named DyKnow, SignalR-ObjC is an active project on GitHub that facilitates making SignalR connections from an iOS or OSX client.  The documentation on the Git site does leave something to be desired but you should be able to stumble your way through connecting SignalR to a project.  Or you can just follow these steps.  First, install Cocoapods.  This can be done from the command line by executing this:

     $ [sudo] gem install cocoapods
     $ pod setup

Now that Cocoapods is installed, you need to add a podfile to your project directory.  Navigate to the root of your XCode project and create a new file named podfile and fill it with the following contents:

  platform :ios, '5.0'
  pod 'SignalR-ObjC'

If you leave off the “, ‘5.0’” and try to install the pods, you’ll end up getting this error:

     [!] SignalR-ObjC (0.5.2) is not compatible with iOS 4.3.

I’m not exactly sure why that is.  If you create a new project in XCode (today) it isn’t set to compile for 4.3.  There must be some specification in the pod that doesn’t like how a default project is set up.  Fixing this is as easy as leaving the “, ‘5.0’” in your podfile as part of the platform.  After that, execute this command in the terminal (after you’ve navigated to your root directory):

          $pod install

You should see something like this for the output:

    Updating spec repo `master'
    Installing AFNetworking (1.0RC1)
    Installing SignalR-ObjC (0.5.2)
    Generating support files
    [!] From now on use `projectname.xcworkspace'.
    -> Integrating `libPods.a' into target `projectname' of Xcode project `projectname.xcodeproj'.

This installs both the SIgnalR-ObjC dependency and the AFNetworking library which the SignalR one depends on.  Also, note that it has created a new workspace (in this case named projectname.xcworkspace) and instructs you to use that from now on.  If you had your project open in XCode, close that and open the newly generated workspace.  That workspace will contain a Pods project and your original project.  For my sample project, I’ve just created a simple Single View Application.  To the storyboard for my single view controller, I’ve added a label and a button:

The storyboard with controls

After adding your UI elements, you’ll need to tie the button to an IBAction and the label to an IBOutlet.  After doing so, here’s the code in my ViewController.h:

    @interface ViewController : UIViewController
        - (IBAction)tapAddHit:(id)sender;
        @property (weak, nonatomic) IBOutlet UILabel *txtHitCount;
    @end

Flipping over to the ViewController.m you’ll need to add an import for SignalR:

    #import "SignalR.h"

After the txtHitCount has been synthesized, we’ll add an instance of SRHubProxy to keep track of our hub:

    @implementation ViewController
    @synthesize txtHitCount;
    SRHubProxy *myHub;

Now in the viewDidLoad method, we’ll create a new connection, get a hub for the hit counter, specify handlers for client side methods and then start the connection:

    - (void)viewDidLoad
    {
        [super viewDidLoad];
        // Do any additional setup after loading the view, typically from a nib.
        SRHubConnection *connection = [SRHubConnection connectionWithURL:
                                       @"http://msdpe-signalrconnect.azurewebsites.net"];
        myHub = [connection createProxy:@"HitCounter"];
        [myHub on:@"showHitCount" perform:self selector:@selector(notificationReceived:)];
        connection.started = ^{
            [myHub invoke:@"addHit" withArgs:nil];
        };
        [connection start];
    }

Notice that the connection just specifies the root URL of our site.  The hub proxy then specifies the hub name.  Note the capitalization here as it’s a little different than the javascript in the html page (that had “hitCount” and starts with a lower letter).  The on call in between createProxy and start is how well tell it what method should be called whenever showHitCount is called by the server.  Finally, we set the connection’s started property to be a block that will be called when start is finished.  Last, we call start on the connection.  Now we need to implement that notificationReceived method that will be called whenever showHitCount is called by the server:

    - (void)notificationReceived:(id)message
    {
        //do something with the message
        NSLog(@"%@",message);
        txtHitCount.text = [@"There have been " stringByAppendingFormat:@"%@ views", message];
    }

All we’re doing is logging what is sent by the server and then using the same value to set the text of our label.  The server just sends a number over when it calls showHitCount so we’ll do a little formatting and show it.  Now we could be done, but so you can see things in action a little bit better, let’s make tapping the “Add Hit” button add another hit to the server:

    - (IBAction)tapAddHit:(id)sender {
        [myHub invoke:@"addHit" withArgs:nil];
    }

Now when your app runs, after you tap the button, you should see the hit count increase in the app as well as in any browsers that are connected (it may take a few seconds):

Hit Count Increasing

 

And that’s it.  Now we have a simple iOS app connecting to a server side hub with SignalR.  I completely glazed over discussing any of the internals of how SignalR works, so if you’d like to know more about that, I’d start by reading this article by Scott Hanselman.  The guys working on SignalR have some pretty ambitious plans for the technology (think 100k persistent connections when they release 1.0) so its bound to get faster and better at doing what it does.  I’m hoping to follow this up with a more advanced sample in the next few weeks.

 

You can download the iOS client source code from this article here.

Bookmark and Share
First Article