By default a WIF security token is only valid for a certain time. However this token does not work with a sliding expiration out-of-the-box. This means that, no matter if the users is actively using the application or not, once the time interval has expired, the token is invalidated and the user has to login again.
Although this seems logical from a security standpoint, it’s not very user friendly. Users expect that as long as they are using the application, their authentication session remains valid.
Although this seems logical from a security standpoint, it’s not very user friendly. Users expect that as long as they are using the application, their authentication session remains valid.
So how can we achieve sliding expiration in WIF?
- Create a new class that inherits from SessionAuthenticationModule:
public class SlidingAuthenticationModule : SessionAuthenticationModule { }
- Register for the SessionSecurityTokenReceived event in the constructor:
public SlidingAuthenticationModule { this.SessionSecurityTokenReceived += SessionSecurityTokenReceived; } void SessionSecurityTokenReceived(object sender, SessionSecurityTokenReceivedEventArgs e) { }
- Add code to the event handler to implement the sliding expiration:
void SessionSecurityTokenReceived(object sender, SessionSecurityTokenReceivedEventArgs e) { var sessionToken = e.SessionToken; SymmetricSecurityKey symmetricSecurityKey = null; if (sessionToken.SecurityKeys != null) symmetricSecurityKey = sessionToken.SecurityKeys.OfType<SymmetricSecurityKey>().FirstOrDefault(); if (sessionToken.ValidTo > DateTime.UtcNow) { var slidingExpiration = sessionToken.ValidTo - sessionToken.ValidFrom; e.SessionToken = new SessionSecurityToken( sessionToken.ClaimsPrincipal, sessionToken.ContextId, sessionToken.Context, sessionToken.EndpointId, slidingExpiration, symmetricSecurityKey); e.ReissueCookie = true; } else { var sessionAuthenticationModule = (SessionAuthenticationModule) sender; sessionAuthenticationModule.DeleteSessionTokenCookie(); e.Cancel = true; } }
- Inside your web.config, replace the default SessionAuthentication module with the new module you’ve created:
<modules> <add name="SessionAuthenticationModule" type="SlidingAuthenticationModule" preCondition="managedHandler"/> </modules>