Janet Moonshot & FreeRADIUS on Microsoft Azure – An important step for Researchers for being able to use Microsoft’s Public Cloud Platform

Over the past months I’ve spent some time working with Janet the UK’s National Research and Education Network. As well as managing the operation and development of the Janet network, Janet runs a number of services for educationand research including operating eduroam(UK), the UK part of a large, global network established between all sorts of research and education facilities and institutions.

In addition to eduroam and other services, one of the most important projects Janet is leading is the development and standardization of an open platform for authentication, authorization and trust management based on existing standards:

This platform is called Project Moonshot.

Simply put, Moonshot in conjunction with FreeRADIUS is an identity provider and a security token service. Nevertheless it is primarily based on the protocols mentioned above – EAP, RADIUS and GSS-API/SSPI/SASL instead of WS-Federation, OAuth or SAML-P (although one of the token formats supported by Moonshot are SAML tokens).

What I personally think is really cool about Moonshot!?

The really cool and practical thing by being built on the protocols above, is in my personal opinion, that those protocols are supported by almost all relevant operating system platforms deeply integrated since these standards are also used by Kerberos. For example Windows as an OS has SSPI deeply built into the logon-process of Windows which means with an SSPI-provider for Moonshot, the Windows logon itself can be sourced from a federation through a variety of trust-relationships instead of the OS or a direct domain controller by itself. That is one thing that is not possible with the commonly more widely known standards such as WS-Fed, OAuth or SAML-P since they’re all web-focused.

Why is Moonshot so important for Microsoft and Microsoft Azure?

Independent of what I think the advantages are of Moonshot, the most important part for Microsoft and Microsoft Azure is, that Janet is working with NRENs, academia and research across Europe and internationally to establish Moonshot as THE prime authentication mechanism for research communities, building up trust relationships between them and thus allowing federated authentication and authorization for research projects across the world.

In other words: if Microsoft Azure wants to play an important role in research in the future, Moonshot needs to be somehow supported in Azure as a platform. Through our partnership and work with Janet we achieved a first step for this over the past months, together!

Moonshot IdP Base Image on VMDepot…

Working together with Janet we managed to get a base-image prepared, tested and published on Microsoft Open Technologies VMDepot that can be used by anyone who wants to get connected to research communities through Moonshot Trust Routers and IdPs for federated security.

You can find this image here on VMDepot for getting started.

Although it seems like a simple thing to do, we had to undergo a few steps to get this far. Moonshot was required to be updated to support the Linux-distributions officially supported on Microsoft Azure. Furthermore we had to test if the semantics of the protocols used, especially EAP, do work well on Microsoft Azure. At least for single VM deployments we did this and the image above on VMDepot contains all the bits with which we’ve tested.

Of course that’s just the first step and we know we need to take some future steps such as making the deployments ready for multi-instance deployments for the sake of high availability and eventually also performance. Nevertheless, this is a great first step which was required and enables us to move forward.

The image by itself is based on Ubuntu Linux 12.10 LTS, it has the Moonshot and FreeRADIUS package repositories configured correctly and has other useful packages installed that are required or nice to have for Moonshot and FreeRADIUS (such as “screen” for example).

Using the Moonshot/FreeRADIUS VMDepot Image

Next I’d like to summarize how you can make use of the Moonshot VMDepot image. Note that most probably you should be involved in academia or research projects for this to be useful to you J. Of course you can also setup your own, single IdP using the image, but the full power gets unleashed when you become part of the Janet Trust Router network which is what I am focusing on in this blog post right now.

Let’s start with a few assumptions / prerequisites:

  • Assumption #1:
    Since the primary target group is academia and research which is very Linux-focused, I am assuming people who’re trying this will most probably try the steps below from a Linux-machine. Therefore I am only using tools that also work on Linux (or Mac), although I am running them from a Windows machine.
  • Assumption #2:
    For the steps to complete you need an active Microsoft Azure subscription. To get one, navigate to http://azure.microsoft.com and click on the “Free Trial” button in the upper, right corner.
  • Assumption #3:
    You are able to get in touch with Janet to participate in their Moonshot pilot to get the credentials required to connect your Moonshot IdP/RP to their Trust Router Network and that way become part of the larger UK and global academia and research community implementing Moonshot.

Now let’s get started with the actual deployment of a Moonshot VM based on the image Janet and we have published together on VMDepot:

  • Install Node.js if on your machine if not done, yet.
    Node.js is needed since the Microsoft Azure Cross Platform Command Line Interface which we will use for setting up the Azure environment is built with Node.js.
  • Install the Azure Cross Platform Command Line Interface (xplat CLI).
    The Azure xplat CLI is a command line interface that allows you to script many management operations for services in your Azure subscription from either a Linux, Mac or also a Windows machine. For more details on setting it up, please refer to the Azure xplat CLI homepage.
  • Import your Subscription Publish Profile Settings through the xplat CLI.
    Before you an issue any operation to your Azure subscription in the cloud through the xplat CLI, you need to download and import a credentials file. This is the only operation that requires a GUI with a web browser, so if you issue the following command, you should sit on a machine with x-Windows installed or be on a Mac or Windows machine. Open a shell-window or a command prompt and execute the following command:
    • azure account download
      This will open a web browser and browse to a page where you’ll need to sign-in with the account that has access to your Azure subscription (your Microsoft account with which the subscription has been created or which is a Co-Admin of another subscription). It results in the download of a “xyz.publishsettings”-file which contains the credentials. Save that file to your local disk. Next execute the subsequent command:
    • azure account import <path & filename to xyz.publishsettings>
      This command finally makes the Azure xplat CLI aware of your credentials. After that step you can finally start with true management commands against your subscription.
    • Note: if you have multiple Azure subscriptions, you also need to select the subscription in which you want to create the VM using azure account set <subscription-id>
  • Create a VM image based on our VMDepot base image using the xplat CLI.
    Finally we can create the Virtual Machine based on the VMDepot image. For this purpose execute the following command in your previously opened shell:
    • azure vm create yourdnsprefix -o vmdepot-28998-1-16 -l “North Europe” yourusername yourpassword –ssh
    • This command creates a VM which will get a public DNS-name called “yourdnsprefix.cloudapp.net” through which you then can connect to your VM (e.g. via SSH).
    • The result of issuing the command should look similar to the following:
    • What you see here is that the script transfers the template for the virtual machine from VMDepot with the VMDepot image id 28998-1-16 to your storage account and then creates the VM from that template. Finally it does some clean-up stuff.
  • Make sure Moonshot/FreeRADIUS and SSH endpoints are open on the Azure firewall.
    The last step is to open up the required TCP-endpoints on the Azure firewall. This can happen after the VM has been created successfully. Ports required are 2083 and 12309 for Moonshot/FreeRADIUS, SSH is open by default on 22 given our previous command including the -ssh switch. Issue the following commands:
    • azure vm endpoint create-multiple DNS_PREFIX 2083:2083,12309:12309
    • The result should look similar to the following (note that I’ve added port 22 before, already, therefore you won’t see it in the screenshot):

After you’ve completed those steps and the VM has been created, successfully, you need to connect to the VM and perform the final Moonshot/FreeRADIUS-configuration steps. These are pretty much the same as those you’d need to do on an on-premise machine in your own data center, we’ve prepared anything in that image in a way that it should work smooth in Azure.

  • SSH into the newly created VM.
    Make sure you connect as root so you can perform all administrative tasks. All subsequent steps are to be executed in that SSH-session to your newly created VM!
  • Update to the latest package versions.
    Since the image is Ubuntu-based, use apt-* to update to the latest version of the packages. Issue the following commands:
  • Update the FreeRADIUS certificate files to match your organizational values.
    As part of the bootstrapping process, Moonshot and FreeRADIUS generate certificate files required for setting up trust relationships between your RP/IdP and other RP/IdPs. These are generated through openssl based on settings-files prepared in the bootstrap-image from VMDepot. You should customize those to match your organizational values, for example such as the common name to be used for your organization and IdP. Perform the following steps:
    • Switch to the directory /etc/freeradius/certs.
    • Open the file ca.cnf and update the following values to match your own values:
      • emailAddress
      • commonName

    It should look similar to the following if you’re using VI, if you’re really taking it serious, then also update the other values (e.g. passwords for private key files):

    • Open the file server.cnf and update the following values to match your own values:
      • emailAddress
      • commonName
      • It should look similar to the following if you’re using VI:
    • Finally update the same values also in the file client.cnf to match your own values:
    • Execute the command sudo /etc/freeradius/certs/bootstrap. This produces a lot of output, but at the end your screen will look similar to the following after executing this command:
  • Fine-tune Client Private Key Files:
    Next you need to “fine-tune” the private key files for the clients. This is supposed to be something that will be fixed/made easier in future versions of Moonshot and FreeRADIUS. Perform the following steps:
    • Change to the directory /etc/freeradius/certs.
    • Run the following command: cat client.crt client.key > client.txt
    • Now overwrite client.key with client.txt by executing the following command:
      mv client.both client.key
    • Open client.key in VI and delete all lines until the first —- BEGIN CERTIFICATE —- appearance as shown below:
  • Realm configuration – Part #1
    Now that all certificates are configured, you need to configure your “realm”-settings such as the name of your realm and other options Moonshot and FreeRADIUS allows you to set. For this blog-post we keep it with the simple creation of a realm for your setup:
    • Switch to the directory /etc/freeradius.
    • Open the file proxy.conf in VI and add the following section anywhere in the file:
      realm yourrealm.com
      {
      }
    • The realm you select should match the DNS-name you’re planning to use for setup. This DNS-name should then be mapped using a DNS CNAME-alias or DNS A-Record to your xyz.cloudapp.net setup in Azure.
    • You can look at the sample-realm configurations in the file so that you can decide which other options you’d prefer to set for your setup. For this post we keep things at a default-setup.
  • Realm configuration – Part #2:
    For the next realm-setting perform the following steps in the SSH-session:
    • Open the file /etc/freeradius/mods-enabled/realm in VI for editing.
    • Add the following section at any place in the file:
      realm suffix {
      change rp_realm = “yourserver.yourrealm.com”
      }
    • Make sure you use the same domain-name as before (e.g. yourrealm.com) and that the name you specify here (yourserver.yourrealm.com) is a resolvable DNS-name.
    • The results should look similar to the following:
  • Modify post-authentication step that issues the SAML assertion.
    Next you need to modify the post-authentication steps. One action that happens in those post-authentication steps is the definition of SAML-assertions that get issued as a token after a successful authentication. We prepared the image with a default-template that you can customize based on your need. But even if you don’t customize the assertions, there’s one step you need to complete and that’s bringing your realm into the context of the post-authentication steps.
    • Open the file /etc/freeradius/sites-enabled/default with VI.
    • Search for a configuration section starting with post auth { … }.
    • Modify it to issue the SAML-assertion for your realm as follows:
      post-auth {
          if (Realm == LOCAL) …
      change to
          if (Realm == “cloudapp.net”) (same as above)
      }
    • The result should look similar as the following:
  • Request and setup Trust Router Credentials (through Janet).
    As mentioned most use of a Moonshot/FreeRADIUS install is given when you connect it to a research community. For this purpose get in touch with Janet to join their pilot via https://www.ja.net/products-services/janet-futures/moonshotOnce accepted onto the pilot, Janet  will send you Trust Router credentials which allow you to get into a federation with the research network Janet operates.
    • Janet (or other Trust Router operators) will send you the trust router credentials for setting up the trust relationship as an XML file. Put that XML-file on your Moonshot VM created earlier.
    • Next execute the following commands (assuming the XML-file with the Trust Router credentials is called mytrustcreds.xml):
          su –shell /bin/bash freerad
          unset DISPLAY
          moonshot-webp -f mytrustcreds.xml
    • With those credentials your IdP/RP will be able to connect and federate with the Trust Router network Janet operates for academia and research (or the one you’ve received the credentials for).

Finally that’s it, we’ve completed all steps for configuring the Moonshot/FreeRADIUS setup. Now it’s up to test the environment or start using it for your single-sign-on and authentication purposes. A simple test for your environment together with Janet could look as follows:

  • Open up three terminal sessions to your Moonshot/FreeRADIUS VM you just created.
  • In Terminal #1 perform the following steps:
    • Open /etc/freeradius/users using VI.
    • Look for the following line: testuser Cleartext-Password := “testing”
    • Leave it for the test or modify it as per your needs. Also that’s where you could add your own users of your IdP. If you leave it as above that’s the credentials you can use for testing.
    • Now execute the following commands:
      • su –shell /bin/bash freerad (runs a shell under the FreeRADIUS user)
      • freeradius -fxx -l stdout (runs freeradius for debugging with logging to stdout)
  • In Terminal #2 perform the following steps:
    • moonshot-webp -f <path to previously received trust router credentials XML>
    • tids <your-external-ip> trustrouter@apc.moonshot.ja.net /var/tmp/keys
      • The external IP for your Azure VM is visible in the Azure Management portal (manage.windowsazure.com) for your virtual machine.
      • trustrouter@apc.moonshot.ja.net is an example for a trusted trust router. In case you federate with Janet, that’s most likely the one you’ll use.
  • In Terminal #3 perform the following step:
    • tidc tr1.moonshot.ja.net {your rp-realm} apc.moonshot.ja.net apc.moonshot.ja.net
  • Important Note: for the commands above to succeed, you need to have valid Janet Trust Router credentials and Janet needs to have your IdP/RP configured in their trust-settings as a trusted party! Otherwise later when executing the tidc-command the test will fail!
  • Finally to complete the test someone needs to use Moonshot and its identity selector on a client machine to authenticate using your IdP. The best way to do that is using the LiveDVD for Moonshot provided by Janet.

That’s it, now you have your Moonshot / FreeRADIUS IdP to get yourself connected with a huge community of researchers, scientists and students across the world… for further questions it’s best to get in touch with the people from Janet and Moonshot via moonshot-community@jiscmail.ac.uk. And go to the Moonshot home page to find more details here:

https://community.ja.net/groups/moonshot

https://www.ja.net/products-services/janet-futures/moonshot

ASP.NET 4.5.1 WebAPI, “general” integration with OAuth2 and OAuth Authentication Servers

Over the past weeks I did work with several software vendors all having the same question: how does the integration of OAuth2 really look like in ASP.NET 4.5.1?

Well, although that sounds like a simple question to answer with point to http://www.asp.net/identity (which is btw. a good starting-point to dig deeper to better understand what I am writing in this post), it is not, indeed!

What you’ll quickly see is that the walk-through samples on the official ASP.NET homepage show all sorts of code and how-to for integrating either with social identity providers (e.g. Facebook, Microsoft Account, Google, Yahoo) or with Windows Azure Active Directory (short WAAD).

That is cool, but what if you’re really interested in the native OAuth-integration in ASP.NET? What if you’re interested to understand, how-to integrate your WebAPI with any OAuth authorization server, e.g. your own or a 3rd-party authorization server?

Questions that nearly all of the partners and customers I talked to over the past 3 weeks had these questions and the official docs did not really provide an easy-to-understand answer. With this blog-post I try to give that answer and an how-to for you.

First – Understanding OAuth Implicit Grant-Flow

First of all, you need to understand, how OAuth implicit grant approximately works. In essence it is just a bunch of browser-redirects that do take place. The following picture stolen from MSDN explains, what’s going on:

Whenever a users browses to a secured site (= resource provider, relying party) anonymously, then that secured site redirects the user to the authentication service. The user then authenticates against this service and assuming that was successful, the authentication service responds with a browser-page that contains an access token (typically signed, eventually encrypted). That browser page returned then posts the token to a target URL on the resource provider that is registered with the authentication service. The resource provider then decrypts and validates the signature of the token and then the user is authenticated against the resource/site. If the resource/site is a web page, it can then issue its own authentication cookie as usual, if it is a web API, the client (mostly an app on a device or a JavaScript client) can post the token to the WebAPI with every request as long as the token is valid (simplified!).

If that process takes place in an app, a very typical approach is to “host” a browser control that performs this process of browser-redirects, but instead of posting the token back to the resource provider, the client/app intercepts that post and grabs the token to include it in the authentication header for HTTP requests to the WebAPI. The following picture shows that:

For example, for Windows 8 store apps, the WebAuthenticationBroker-class encapsulates the basic process outlined in the previous image for you. It hosts a browser control to do the following:

1. Open an authentication URL on the authentication server
2. Perform all browser requests required for the authentication
3. When the authentication server responds with a redirect URL the broker knows, it
4. intercepts this redirect URL and gives it to you so you can grab the token.
5. Finally it posts the token in the HTTP Authorization-header when calling the WebAPI (resource provider)

For this process to work, the client-app must be registered as a valid client at the authentication server and of course the WebAPI must also be registered as a valid resource provider in the authentication server. Typically auth-servers such as Windows Azure AD or Thinktecture Identity Server do provide these kind of configurations. If you build your own authentication/authorization server, you should follow the same approach for security reasons.

Second – Get up2speed with ASP.NET 4.5.1 and OWIN/Katana

It helps to understand, what OWIN and Katana are all about to fully understand the code that configures the OAuth2-providers for ASP.NET WebAPIs. But to be honest, if you’re not interested in these details and just want to get it working, you can skip this as well and accept code as it is:)

So I keep it short as well: if you want to understand OWIN and Katana, watch this video on Channel9 – it really explains the strategy very well: http://channel9.msdn.com/Shows/Web+Camps+TV/The-Katana-Project-OWIN-for-ASPNET

In essence one of the important aspects of OWIN/Katana is to decouple the integrated ASP.NET components a bit so that the whole framework gets less “monolithic” and can be easily composed of re-usable, small and slim modules as needed without loading always a big System.Web.dll into memory.

NOW Rock – Connect your WebAPI with any OAuth2 Provider

All OAuth2-functionality starting with ASP.NET 4.5.1 and Visual Studio 2013 is implemented in OWIN/Katana-Modules. That said, when you want to integrate your WebAPI with an OAuth Authentication/Authorization server, you need the following NuGet-package which do contain the generic OWIN-implementation:

Microsoft.Owin.Security.OAuth
Newtonsoft.Json
Microsoft.Owin
Owin
JSON Web Token Handler For the Microsoft .NET Framework

Note that when installing Microsoft.Owin.Security.OAuth that you get all packages as dependencies except the JSON Web Token Handler which you then need to add manually. The JSON Web Token Handler is required to implement the token validation functionality which is not part of the OWIN OAuth module.

After you have added that, you can register the OAuth-provider as shown in the code below in your OWIN configuration class – with the default ASP.NET templates in Visual Studio 2013 that is in App_Start\Startup.Auth.cs whereas if you do things by yourself you could add that code in your OWIN Startup-Class, directly:

app.UseOAuthBearerAuthentication
    (
        new OAuthBearerAuthenticationOptions()
        {
            Realm = "http://mysimpletest",
            Provider = new OAuthBearerAuthenticationProvider(),
            AccessTokenFormat = new JwtFormat
                                    (
                                        allowedAudience: "http://mysimpletest/",
                                        issuerCredentialProvider: new SymmetricKeyIssuerSecurityTokenProvider
                                                                    (
                                                                        issuer: "http://identityserver.v2.thinktecture.com/trust/changethis",
                                                                        base64Key: "iGROpg/Q+8oFSihQKJ6+D6Vsu+GOyfEC4qcGKzY4qNQ="
                                                                    )
                                    )
        }
    );

The code above registers the OAuth Bearer Authentication OWIN module on the IAppBuilder passed into the startup-class for ASP.NET OWIN. It specifies the following parameters:

– the realm for which it expects the token to be issued from the auth-server
– the authentication provider, which is OAuthBearer as we expect a bearer token
– the token access format with a token provider used for validating the token

In the sample above we use the SymmetricKeyIssuerTokenProvider which means the authentication server should use the symmetric key specified in the code above to validate the token.

To understand these values better, it is now time to look at the configuration of the Authentication Server. For implementing my sample I used the ThinkTecture Identity Server which (still) supports OAuth implicit grant (note that this functionality is expected to be moved to the ThinkTecture Authorization server – see their homepage for further details). Since in my sample I am using a Windows 8 Store App as a client to call my web API, I also need to register that store app as a valid client with the authentication server as shown below:

As you can see in this picture, the Web API symmetric key and the realm do match what we have used in the code, above. The configured redirect-URL is not used since we’re accessing the WebAPI from a store app. The store APP is registered as a client as you can see from the second screen.

In the Windows 8 Store App I am using the WebAuthenticationBroker from WinRT to kick-off the authentication flow. The WebAuthenticationBroker ecnapsulates a browser-control that performs the required process as shown in the first image of this blog post including all browser redirects. The process stops when that hosted browser control tries to post to the redirect URI entered in the client configuration as shown in the Thinktecture Identity Server screen-shot above.

In case of a Windows 8 app that “redirect URL” is not a physical URL, but it is something the browser-control hosted in the WebAuthenticationBroker will intercept. Many authentication servers use that URL with the access token provided as a query string parameter as shown below:

ms-app://s-1-15-2-210097793-3234850793-3288079826-3013899094-2116512904-1639073252-2090501734/#access_token=eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJodHRwOi8vaWRlbnRpdHlzZXJ2ZXIudjIudGhpbmt0ZWN0dXJlLmNvbS90cnVzdC9jaGFuZ2V0aGlzIiwiYXVkIjoiaHR0cDovL215c2ltcGxldGVzdC8iLCJuYmYiOjEzODcxODc2ODMsImV4cCI6MTM4NzIyMzY4MywibmFtZWlkIjoidGVzdCIsInVuaXF1ZV9uYW1lIjoidGVzdCIsImF1dGhtZXRob2QiOiJodHRwOi8vc2NoZW1hcy5taWNyb3NvZnQuY29tL3dzLzIwMDgvMDYvaWRlbnRpdHkvYXV0aGVudGljYXRpb25tZXRob2QvcGFzc3dvcmQiLCJhdXRoX3RpbWUiOiIyMDEzLTEyLTE2VDA5OjU0OjQwLjM3N1oiLCJlbWFpbCI6InRlc3RAdGVzdGluZy5jb20ifQ.SmXI42aNXy6bwk8plObHK7vHUndqXDh1xsd14-PCPt0&token_type=urn:ietf:params:oauth:token-type:jwt&expires_in=35998

The WebAuthenticationBroker just waits for the hosted browser control to try to post to this URL, intercepts that process and then returns to your code so that you can extract the access token out of that:

string thinktectureUrl = "https://mszspro8/idsrv/issue/oauth2/authorize";
string webApiUriForOauth = "http://mysimpletest/";
string thinktectureClientId = "testclient";

var endpoint = new Uri("https://mszw81-devvm/idsrv2/issue/oauth2/authorize");
var callbackUri = WebAuthenticationBroker.GetCurrentApplicationCallbackUri();
            
var startUri = new Uri(
        string.Format(
        "{0}?client_id={1}&scope={2}&redirect_uri={3}&response_type=token",
            endpoint.AbsoluteUri,
            Uri.EscapeDataString(thinktectureClientId),
            Uri.EscapeDataString(webApiUriForOauth),
            callbackUri.AbsoluteUri));

var success = await WebAuthenticationBroker.AuthenticateAsync
                    (
                        WebAuthenticationOptions.None,
                        startUri
                    );

// Pick the token out of the response
if (success.ResponseStatus == WebAuthenticationStatus.Success)
{
    var parametersString = success.ResponseData.Substring(success.ResponseData.IndexOf("/#") + 2);
    var parameters = parametersString.Split('&');
    var token = parameters[0].Substring("access_token=".Length);

    // Now call the web API with the bearer header
    httpClient.DefaultRequestHeaders.Authorization =
        new AuthenticationHeaderValue("Bearer", token);

    var response = await httpClient.GetAsync("https://localhost:44304/api/values");

    await PrintWebAPISuccess(response);
}
else
{
    throw new Exception(success.ResponseData);
}

The code above is part of a Button-Click-Handler in a Windows Store App that calls the WebAPI. As you can see, the first thing it does is composing a URL to start the authentication process with as well as a redirect-URL to intercept for token posting (which is the ms-app:// URI retrieved with a utility function of the broker as follows: WebAuthenticationBroker.GetCurrentApplicationCallbackUri()).

The start-URL is one that is specified by the authentication server and the one used above is specific to the Thinktecture Identity Server. Windows Azure AD or other authentication servers will have a different start-URL.

But the process then is always the same – the WebAuthenticationBroker hosts a browser and starts kicking off the process with this start URL. And it stops processing by intercepting a post to the redirect / callback URI.

After that process is completed, we take the response from the web authentication broker and parse the JWT-token out of the intercepted URL. Then we add the token to the HTTP header and call the web API. The following screen-shot shows that in action using the Thinktecture Identity Server from within our Windows Store App:

The “.UseOAuthBearerAuthentication”-call we made in the WebAPI ensures that a token must be posted to the API so that it can be callend and it also sets the System.Threading.Thread.CurrentPrincipal so that we can query properties of the user contained in the token as follows:

[Authorize]
public class ValuesController : ApiController
{
    // GET api/values
    public IEnumerable<string> Get()
    {
        // Claims APIs are abstract APIs that provide user information etc. independent of the Identity Provider used

        var claimsId = (ClaimsIdentity)System.Threading.Thread.CurrentPrincipal.Identity;
        foreach (var claim in claimsId.Claims)
        {
            // A claim is an attribute of a user, e.g. email, age/birthdate
            Debug.WriteLine(
                    string.Format(
                        "-) {0} = {1}",
                            claim.Type,
                            claim.Value
                    )
                );
        }

        return new string[] { "value1", "value2" };
    }
}

Please note the [Authorize]-attribute which ensures that the API cannot be called without a token.

The APIs used to query the attributes of a user are the “new Windows Identity Foundation” APIs which are now part of the .NET Framework.

Other OAuth OWIN Providers in ASP.NET 4.5.1

Now you might ask why we have other providers in the form of NuGet-packages if the Microsoft.Owin.Security.OAuth provider solves the problem in a general way. The answer is: simplicity!!! You have to admit that e.g. the following Code for Facebook or Windows Azure AD or Google is much simpler than the code above:

app.UseWindowsAzureActiveDirectoryBearerAuthentication(
    new WindowsAzureActiveDirectoryBearerAuthenticationOptions
    {
        Audience = ConfigurationManager.AppSettings["ida:Audience"],
        Tenant = ConfigurationManager.AppSettings["ida:Tenant"]
    });

app.UseGoogleAuthentication();

app.UseFacebookAuthentication(appId: "yourappid", appSecret: "yourappsecret");

All of these providers are doing nothing else but encapsulating what we’ve done manually using Microsoft.Owin.Security.Oauth in our WebAPI above. With Windows Azure AD and Windows Server AD / ADFS you have a few other neat libraries on the client (Active Directory Authentication Libraries (ADAL)) which do make things much simpler as outlined on Vittorio’s blog:

http://www.cloudidentity.com/blog/2013/09/12/active-directory-authentication-library-adal-v1-for-net-general-availability/

Sample Code Download:

I’ll continue with a 2nd post on Windows Azure AD and OAuth with ASP.NET WebAPIs after Christmas and then also post my sample code of which I’ve taken the fragments above.

So stay tuned on more details, but I think the details above are exactly those which are not very well documented and I hope with this post I do fill that gap appropriately.

Merry Christmas!