views:

30

answers:

3

I have a site that is using Forms Auth. The client does not want the site session to expire at all for users. In the login page codebehind, the following code is used:

// user passed validation
FormsAuthentication.Initialize();

// grab the user's roles out of the database 
String strRole = AssignRoles(UserName.Text);

// creates forms auth ticket with expiration date of 100 years from now and make it persistent
FormsAuthenticationTicket fat = new FormsAuthenticationTicket(1,
  UserName.Text, DateTime.Now,
  DateTime.Now.AddYears(100), true, strRole,
  FormsAuthentication.FormsCookiePath);

// create a cookie and throw the ticket in there, set expiration date to 100 years from now
HttpCookie cookie = new HttpCookie(FormsAuthentication.FormsCookieName, 
  FormsAuthentication.Encrypt(fat)) { Expires = DateTime.Now.AddYears(100) };

// add the cookie to the response queue
Response.Cookies.Add(cookie);

Response.Redirect(FormsAuthentication.GetRedirectUrl(UserName.Text, false));

The web.config file auth section looks like this:

<authentication mode="Forms">
      <forms name="APLOnlineCompliance" loginUrl="~/Login.aspx" defaultUrl="~/Course/CourseViewer.aspx" />
</authentication>

When I log into the site I do see the cookie correctly being sent to the browser and passed back up:

HttpFox output

However, when I walk away for 20 minutes or so, come back and try to do anything on the site, the login window reappears. This solution was working for a while on our servers - now it's back. The problem doesn't occur on my local dev box running Cassini in VS2008.

Any ideas on how to fix this?

+1  A: 

Session timeout and Forms Authentication timeout are two separate things. Is the Session timeout set to 20 minutes, and would it be logging your users out in the Session_End event in Global.asax file by any chance?

womp
A: 

Well I do have the following in Global.asax:

protected void Application_AuthenticateRequest(Object sender, EventArgs e)
    {
        //Fires upon attempting to authenticate the use
        if (!(HttpContext.Current.User == null))
        {
            if (HttpContext.Current.User.Identity.IsAuthenticated)
            {
                if (HttpContext.Current.User.Identity.GetType() == typeof(FormsIdentity))
                {
                    FormsIdentity fi = (FormsIdentity) HttpContext.Current.User.Identity;
                    FormsAuthenticationTicket fat = fi.Ticket;

                    String[] astrRoles = fat.UserData.Split('|');
                    HttpContext.Current.User = new GenericPrincipal(fi, astrRoles);
                }
            }
        }
    }

Is that what you're referring to? Also, we're in an IIS6 environment if that makes any difference.

Rob
That looks fine. I mean that there are two separate timeouts - one for your authentication ticket, which is set to 100 years. But there is a Session timeout as well, which by default is set to 20 minutes, so it sounds to me like it is affecting something. A common pattern is to hook up the Session_End event to a handler in Global.asax that will log a user out of their formsauth ticket when their session expires.
womp
Right - I don't have that type of thing. Is there a way to force Session timeout to nothing or infinity so it defaults to the HTTPCookie?
Rob
The Session timeout can be set in the web.config: http://msdn.microsoft.com/en-us/library/h6bb9cz9.aspx. <sessionState timeout="525600" /> It can't be set for longer than 1 year, however.
womp
Added <sessionState mode="InProc" timeout="525600" /> to the web.config - still dumps out after 20 minutes :-(
Rob
A: 

By default, app pools in IIS 6 are set to shut down after 20 minutes of inactivity. If there's nothing in your app configuration that's causing your app to shut down that quickly, check the app pool configuration in the IIS Manager. There are lots of wonderful knobs you can set in there.

Andrej Marjan