Connecting to Live with the C++ REST SDK

Hi, I’m Andy Rich, a QA on the C++ team.  Last week, the C++ team released the C++ REST SDK (codename “Casablanca”) on CodePlex (http://casablanca.codeplex.com).  This blog post will walk you through using the C++ REST SDK to connect your Windows Store apps to Windows Live services.  This example demonstrates how to grab information about the user’s photo albums, but it can be applied to the other Live REST APIs as well.

Prerequisites

In order to connect a Windows Store app to Live Services, you will need:

  • A Windows Store Developer account (sign up here: http://msdn.microsoft.com/en-US/windows).  Note that you will need to provide a credit card to open a developer account. (MSDN subscribers are eligible for a one-time 12-month developer account.)
  • A Visual Studio Project which is associated with a Windows Store app in the Windows Dev Center.  In order to connect to Live, your application will need a real store signing key and package identity, so you must complete the first few steps of the store submission process and associate your project with that app, even if you’re just experimenting with the functionality. I outline the required steps in “Setting up your App,” below.
  • The C++ REST SDK for Visual Studio 2012 (express or full)

Setting up your App

To create a new app in your Dashboard within the Windows Dev Center, click “Submit an app”.  (This will begin the submission process, but your app doesn’t need to be ready for submission just yet!)  You will be asked to reserve a name; this may be changed later, so don’t worry about finding the perfect name for your app right now.

Next, click “Advanced Features” in your app’s dashboard entry and choose “Save.”  You want to ensure that the Advanced Features step shows as “Complete” in your dashboard.

Next, you will need to associate your Visual Studio project with the app entry you made on your developer account.  To do this, right-click your project in Visual Studio, and select Store->Associate an App with the Store.  You will be prompted to log into your developer account, and then shown a list of apps you have started; select the appropriate one, click “next” and then “associate.”

It is vital that you complete this step – without a proper package identity and a store-signed key, Live Services will reject all login requests from your app.

Finally, right-click your project and choose “References,” then click “Add New Reference.”  Select Windows->Extensions and the check the box next to “C++ REST Extension SDK for Windows Store apps” and click “Ok”.  This will add the necessary includes/libs for the C++ REST SDK to your project.  (If you cannot find the necessary reference in the dialog, make sure you have installed the appropriate SDK and try restarting Visual Studio.)

Logging into Live

Let’s work on logging into Live.  This is done by using the Windows Runtime (WinRT) OnlineIdAuthenticator API, which presents users with a consistent and trusted login view across multiple apps.  The user’s consent will be cached with your app, so the login/consent dialog will only appear the first time a user accesses you’re app on a particular computer, unless the login expires or the user logs out.

Include <collection.h> and <ppltasks.h> in your source file and add the following using declarations:

using namespace Platform::Collections;
using namespace Windows::Security::Authentication::OnlineId;
using namespace concurrency;

This code will log the user into Live using the OnlineIdAuthenticator:

       auto auth = ref new OnlineIdAuthenticator();

       auto request = ref new OnlineIdServiceTicketRequest(“wl.signin wl.basic wl.photos”, “DELEGATION”);

       auto request_vec = ref new Vector<OnlineIdServiceTicketRequest^>();

       request_vec->Append(request);

 

       create_task(auth->AuthenticateUserAsync(request_vec, CredentialPromptType::PromptIfNeeded))

       .then([](UserIdentity^ ident){

              auto ticket = ident->Tickets->GetAt(0);

              //token is a global std::wstring
              token = std::wstring(ticket->Value->Data());
       });

We start by creating the OnlineIdAuthenticator object, and then create a request to log into Windows Live.  In this case, we are requesting the wl.signin, wl.basic, and wl.photos scopes.  You can view the full list of Windows Live scopes (and what they permit your app to access) here

The OnlineIdAuthenticator allows you to submit multiple login requests simultaneously, but for our purposes, a single login request is sufficient.  However, to match the AuthenticateUserAsync function’s parameters, we will need to pass our request inside a single-element vector (request_vec).

AuthenticateUserAsync may take over the user’s screen to display the login prompt and gain the user’s consent, so naturally this will be an asynchronous action.  In the code above, we are using a PPL task continuation to inspect the login ticket after the user has consented.  Note that we are not handling error cases where the user has not consented or the authentication fails (for example, due to an incorrect app association).  These cases should be handled using a task-based continuation to catch the error and handle it appropriately.  To learn more about using PPL, I recommend this article.

When the user has logged in and given their consent for your app to access their information, the continuation will be called back.  Interestingly, most of the properties on the UserIdentity that gets returned to you are actually unavailable (unless you are a “Microsoft application partner”).  However, the only property we care about at this point is the security token which is found in the collection of tickets included in the UserIdentity.

The token returned after successful login is required in later steps, and so needs to be stored somewhere for later access.  In the example above, the token is being stored in a global variable; in a full application, this would more appropriately be stored in a member variable and protected against concurrent access and race conditions.

Understanding the Live REST Endpoint

It can be helpful to understand what the Live REST endpoint returns when it is used correctly, and the Live Interactive SDK can be very helpful here.  To use the Interactive SDK, you need to click the small ‘Sign in’ link in the upper right-hand corner of the page and log in using a Windows Live account.  For the following walkthrough, you should use an account which has some pictures stored in the user’s SkyDrive.

After logging in, expand “SkyDrive API” and select “Albums, photos, videos, and tags” and choose “REST” on the right-hand side.  The Request path will be preloaded with “/me/albums,” which will get a list of the logged-in user’s photo albums.  If you click the “Run” button, the Interactive SDK will call to the Live REST API and show the results of the API call in the “Response” section.

The Live REST API returns text formatted as JSON (JavaScript Object Notation). This is a simple web-standard format to return structured data, which many different languages and frameworks have the ability to parse.  Both Windows Runtime (through the Windows::Data::Json namespace) and the C++ REST API (through the web::json namespace) have the ability to parse JSON into object hierarchies which can be inspected and manipulated in code.  We will use the C++ REST API’s JSON parsing in this example.

By viewing the structure of the response in the Interactive SDK, we can understand how the Live REST API returns information about the user’s albums:

{ // top-level object

    “data”: [ // array, 1 element per album

    {  //object, 1st element in the array

        “id”: “<folder id>”,

        “from”:

        { //object containing two members:

            “name”: “<friendly name of album owner>”,

            “id”: “<owner’s id>”

        },

        “name”: “<album’s friendly name>”,

        “description”: “<friendly description of album>”,

        “parent_id”: “<folder id of parent>”,

        “size”: 405466,

        “comments_count”: 0,

        “comments_enabled”: true,

        “count”: 26,

        “link”: “<direct URL to the album>”,

        “type”: