Click here to Skip to main content
Click here to Skip to main content

Handle Session Timeouts on DotNetNuke Through an HttpModule

, 15 Jul 2008 CPOL
Rate this:
Please Sign up or sign in to vote.
This article provides an HttpModule that tackles the session-timeout problem on DotNetNuke (DNN) platform. It will redirect users’ subsequent requests to a page that prompts some informative messages after session timeouts occur.

Introduction

This article provides an HttpModule that tackles the session-timeout problem on DotNetNuke (DNN) platform. It will redirect users’ subsequent requests to a page that prompts some informative messages after session timeouts occur.

Background

The issue of session timeout is due to the implementation that data storing at Session[“key”] will be swept by ASP.NET Framework (Figure 1) after specified periods recorded at web.config shown in Listing 1. A new session id (stored at browser’s cookie) will be sent to clients upon a request made by browsers to Web server after session timeout. If the request with expired session id (the blue arrow) tries to retrieve data storing at Session[“key”], it will lead to the exception: Object reference not set to an object because Session[“key”] of the old session has been cleared.

image003.jpg
Figure 1. The scenario of Session Timeouts.

Listing 1. Set the Period of a Session

<system.web>
    <sessionState timeout="20" />     <!--<span class="code-comment"> timeout specifies the period of a session --></span>
</system.web>

The author of “Detecting ASP.NET Session Timeouts1” presents a trick to let developers check to see if a user's session has expired. Moreover, the author suggests encapsulating the checking logic into a base page class, and once session timeouts occur, the subsequent request will be redirected to a page showing some informative messages to tell users what happened. In this way, all pages which use sessions can inherit this base page for reusing the code logic. However, this solution cannot be directly adopted by DNN Web application.

Problem

Under the DNN Framework, there is only one page, Default.apsx, available to the whole Web application. From a user's perspective, clicking a hyperlink seems to go to an individual page. However, DNN merely uses Default.apsx to dynamically populate all of the page's content from a database for all requests. The Default.apsx.cs has inherited a base page class provided by the DNN Framework so we cannot adopt the solution mentioned in the preceding section (multiple inheritance is not supported in C# and VB.NET). One may think of intrusively inserting the checking logic of session timeouts into Default.apsx.cs. This is not an appropriate solution because if you want to upgrade your DNN Web site, you must re-insert the code logic again. Having described the problem, let us discuss the refactored solution.

Solution

We begin with the review of the basic process of HTTP requests in ASP.NET. Each HTTP request is handled by an HttpApplication, which is created by aspnet_wp.exe (the process of ASP.NET). During the course of handling requests, HttpApplications will emit a number of events whereby you can add your custom logic to impact a normal HTTP-processing flow. Exploring the HttpApplication in details along with all its events is beyond the scope of this brief article. For further details, please refer here3. The relevant event about this article is the PreRequestHandlerExecute event which is fired before a System.Web.UI.Page instance (i.e. the *.aspx where you drop the controls and write the logic in the code-behind file) is created by HttpApplication to present the final HTML markup in the consequence of .aspx to the browser.

If we can use the checking logic in “Detecting ASP.NET Session Timeouts1” in a PreRequestHandlerExecute event handler to redirect a request to a “SessionTimeout” alarm page on DNN, we are not required to modify the Default.apsx.cs. And yes, HttpModule2 comes to the rescue. HttpModule allows you to hook any events emitted by HttpApplication as described next.

The checking logic provided by “Detecting ASP.NET Session Timeouts1” is intended to be wrapped in an HttpModule2, namely SessionTimeModule, to circumvent the intrusive interpolation of source code. The codes of the SessionTimeModule in Listing 2 is pretty self-explanatory. SessionTimeoutModule implements an IHttpModule interface where two methods, Init() and Dispose(), have to be implemented. Init() will be executed each time a request comes in so you can initialize what you want to do in this method. Dispose() is used to clear the hold resource by HttpModule when finishing the process of requests. Note that the parameter, context, of Init() is of an HttpApplication, by which you can hook the intended events to go about your customization. Also, through HttpApplication, we can refer to any server variables such as Session, Server, etc. As we described in the preceding paragraph, the PreRequestHandlerExecute event is an ideal occasion to execute the “Detecting ASP.NET Session Timeouts1” logic. So we write a handler of the PreRequestHandlerExecute event, app_PreRequestHandlerExecute() where the logic to detect Session Timeouts is employed. Because we are again in the DNN platform, we must use DNN API to redirect a Session-Timeouts request to an informative DNN page (or Tab in DNN terminology), also named “SessionTimeout”. Noted the final if-condition that is to check if the current page name is equal to “SessionTimeout”, which indicates this request has been a redirected request to the “SessionTimeout” page. Thus, the request should not be redirected again, plunging into an endless loop.

Listing 2. SessionTimeoutModule

public class SessionTimeoutModule:IHttpModule
{
    private HttpApplication app;
 
    public void Init(HttpApplication context)
    {
        app = context;
        app.PreRequestHandlerExecute += new EventHandler(app_PreRequestHandlerExecute);
    }
 
    void app_PreRequestHandlerExecute(object sender, EventArgs e)
    {
        if(app.Context.Session != null)
        {
            if (app.Context.Session.IsNewSession)
            {
                string szCookieHeader = app.Context.Request.Headers["Cookie"];
 
                if (szCookieHeader != null && szCookieHeader.IndexOf(
                    "ASP.NET_SessionId") >= 0)
                {
// Get current TabInfo
                    PortalSettings portalSettings = (
                        PortalSettings)app.Context.Items["PortalSettings"];
                    TabInfo tabInfo = portalSettings.ActiveTab;
 
                    // If this tab is not "SessionTimeout" tab
                    if (tabInfo.TabName != "SessionTimeout")
                    {
                        TabController tabController = new TabController();
 
                        tabInfo = tabController.GetTabByName("SessionTimeout",
                            portalSettings.PortalId);
 
                        app.Context.Response.Redirect(pageUrl,true);
                    }                
                }
            }
        }
    }
 
    public void Dispose()
    {
 
    }
}

Install SessionTimeoutModule

Copy the SessionTimoutModule.cs to the App_Code and open web.config to insert a new item in section shown as Listing 3. Since we simply put SessionTimoutModule in App_Code, we can just set the type attribute to its class name, SessionTimeoutModule as in Listing 3. If you build it into some library (i.e. *.dll), you have to set type attribute as the value for PersonalizationModule. The prior value (before comma) is the full-qualified class name, and the latter is the assembly name. Finally, make up a new page called SessionTimeout in DNN as the redirected destination.

Listing 3. Install SessionTimeoutModule in web.config

 <httpmodules>
<add name="Personalization"
     type="DotNetNuke.HttpModules.Personalization.PersonalizationModule,
     DotNetNuke.HttpModules">
  <add name="SessionTimeout" type="SessionTimeoutModule">
</add>
</add></httpmodules>

Conclusion

We have gone through the issue of tackling session timeouts on DNN, and provided a solution that implements a previous work with an HttpModule. The best advantage of the solution is that you do not need to intrusively modify the core codes within DNN, thus totally separating the checking-session-timeout functionality from DNN. When upgrading DNN, you just need to take care of the setting in the web.config (Listing 3).

References

  1. Detecting ASP.NET Session Timeouts, Robert Boedigheimer HttpModules, MSDN
  2. Understanding the HttpApplication Class, Steve Eichert
  3. ASP.NET Request Processing, MSDN

History

  • 14th May, 2008: Initial article submitted
  • 21st May, 2008: Sample code updated
  • 9th June, 2008: Article updated
  • 15th July, 2008: Article updated

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

Share

About the Author

Ricky Wang
Software Developer ITCAC(數位協進)
Taiwan Taiwan
No Biography provided

Comments and Discussions

 
Generallogin.aspx PinmemberAjay Kale New27-Sep-10 1:12 
AnswerYou don't need a VB version Pinmemberhenslecd11-Aug-09 11:44 
GeneralWeb.config giving an error PinmemberKForKing31-Jul-09 12:14 
hi,
for me after adding the "Personalization" tag in web.config, I am getting an error saying "The element add can not contain a child element 'add' because the parent element's content model is empty".
 
Thanks,
GeneralI need a VB version of the file as the CS version is giving an error. Pinmembermnongkhlaw27-Jun-08 2:12 
GeneralRe: I need a VB version of the file as the CS version is giving an error. Pinmembermnongkhlaw27-Jun-08 3:22 
GeneralRe: I need a VB version of the file as the CS version is giving an error. PinmemberRicky Wang27-Jun-08 4:52 
GeneralRe: I need a VB version of the file as the CS version is giving an error. Pinmembermnongkhlaw1-Jul-08 0:21 
GeneralRe: I need a VB version of the file as the CS version is giving an error. PinmemberRicky Wang1-Jul-08 16:03 
GeneralRe: I need a VB version of the file as the CS version is giving an error. PinmemberRicky Wang1-Jul-08 17:58 
GeneralRe: I need a VB version of the file as the CS version is giving an error. PinmemberRicky Wang7-Jul-08 15:45 
GeneralRe: I need a VB version of the file as the CS version is giving an error. PinmemberMember 9627408-Aug-09 12:29 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Terms of Use | Mobile
Web01 | 2.8.141216.1 | Last Updated 15 Jul 2008
Article Copyright 2008 by Ricky Wang
Everything else Copyright © CodeProject, 1999-2014
Layout: fixed | fluid