Implementing WIF Session Mode with a distributed token cache

The WIF runtime provides a nice feature named Session Mode. When set to true, it allows the security tokens to be cached to the server. This feature is particularly useful if you are dealing with the large set of claims in the token. In this recipe, we will explore the steps to enable WIF Session Mode in an ASP.NET Web Application and write a SecurityTokenCache(Microsoft.IdentityModel.Tokens) implementation that allows the tokens to be stored in Memcached distributed cache.

Getting ready

If you are not familiar with the Memcached distributed cache, you can learn more about it in the First round playing with Memcached article by Shaun Xu at http://geekswithblogs.net/shaunxu/archive/2010/04/07/first-round-playing-with-memcached.aspx.

You can download memcached.exe from http://www.splinedancer.com/memcached-win32/memcached-1.2.4-Win32-Preview-20080309_bin.zip and follow the steps specified in the article to configure the distributed cache in an ASP.NET Web Application.

How to do it...

To enable WIF Session Mode and create custom SecurityTokenCache, perform the following steps:

  1. Create a Visual Studio 2010 C# ASP.NET MVC 3 Web Application project, and name it as SessionSecurityTokenCache. Use the Federation Utility wizard tool to create an STS reference.
  2. Configure the SessionSecurityTokenCache project for Memcached support by referring to the article mentioned under the Getting ready section.
  3. Open the Global.asax.cs file, and implement a handler for the SessionSecurityTokenCreated event:
    void WSFederationAuthenticationModule_SessionSecurityTokenCreated(object sender,
    Microsoft.IdentityModel.Web.SessionSecurityTokenCreatedEventArgs e)
    {
    FederatedAuthentication.SessionAuthenticationModule. IsSessionMode = true;
    }
    

    Inside the event handler, set the SessionAuthenticationModule.IsSessionMode to true.

  4. Create a MemCachedSecurityTokenCache class and implement the SecurityTokenCache abstract class. Use the implementation to store SecurityToken in the Memcached distributed cache:
    public class MemCachedSecurityTokenCache : SecurityTokenCache
    {
    private object _syncRoot;
    public MemCachedSecurityTokenCache()
    {
    this._syncRoot = new object();
    }
    public override void ClearEntries()
    {
    lock (this._syncRoot)
    {
    DistCache.RemoveAll();
    }
    }
    public override bool TryAddEntry(object key, System.IdentityModel.Tokens.SecurityToken value)
    {
    bool flag;
    lock (this._syncRoot)
    {
    SecurityToken token;
    flag = this.TryGetEntry(key, out token);
    if (!flag)
    {
    DistCache.Add(key.ToString(), value);
    }
    }
    return !flag;
    }
    public override bool TryGetAllEntries(object key, out IList<System.IdentityModel.Tokens.SecurityToken> tokens)
    {
    //TODO: No implementation necessary for the sample
    tokens = new List<SecurityToken>();
    return true;
    }
    public override bool TryGetEntry(object key, out System.IdentityModel.Tokens.SecurityToken value)
    {
    bool flag = false;
    lock (this._syncRoot)
    {
    value = DistCache.Get(key.ToString()) as SecurityToken;
    if (value != null)
    flag = true;
    }
    return flag;
    }
    public override bool TryRemoveAllEntries(object key)
    {
    if (key != null)
    {
    lock (this._syncRoot)
    {
    DistCache.RemoveAll();
    return true;
    }
    }
    return false;
    }
    public override bool TryRemoveEntry(object key)
    {
    if (key != null)
    {
    lock (this._syncRoot)
    {
    SecurityToken entry;
    if (TryGetEntry(key, out entry))
    {
    DistCache.Remove(key.ToString());
    return true;
    }
    }
    }
    return false;
    }
    public override bool TryReplaceEntry(object key, System.IdentityModel.Tokens.SecurityToken newValue)
    {
    lock (this._syncRoot)
    {
    return (this.TryRemoveEntry(key) && this.TryAddEntry(key, newValue));
    }
    }
    }
    
  5. Under the Microsoft.IdentityModel section in the Web.config file, use the<securityTokenHandlers> element to register the distributed SecurityTokenCache implementation:
    <securityTokenHandlers>
    <add type="Microsoft.IdentityModel.Tokens.SessionSecurityTokenHandler, Microsoft.IdentityModel, Version=3.5.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35">
    <sessionTokenRequirement securityTokenCacheType="SessionSecurityTokenCache.MemCachedSecurityTokenCache, SessionSecurityTokenCache"/>
    </add>
    </securityTokenHandlers>
    

How it works...

The WSFederationAuthenticationModule HTTP module triggers the SessionSecurityTokenCreated event. The handler allows us to enable the WIF Session Mode. The SecurityTokenCache implementation is then used to store the issued tokens in a distributed cache. Now, the cookie only stores the session identifier, which is very lightweight, so the cost of re-serializing the cookie every time is saved.

There's more...

The WIF runtime provides an implementation of SecurityTokenCache named as MRUSecurityTokenCache that accommodates new tokens by removing the least recently accessed item.

See also

The complete source code for this recipe can be found in the Chapter 2Recipe 6 folder.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset