开发者

How to handle "Remember me" in the Asp.Net Membership Provider

Ive written a custom membership provider for my ASP.Net website.

Im using the default Forms.Authentication redirect where you simply pass true to the method to tell it to "Remember me" for the current user.

I presume that this function simply writes a cookie to the local machine containing some login credential of the user.

What does ASP.Net put in this cookie? Is it possible if the format of my usernames was known (e.g. sequential numbering) someone could easily copy this cookie and by putting it on their own machine be able to access the site as another user?

Additionally I need to be able to inercept the authentication of the user who has the cookie. Since the last time they logged in their account may have been cancelled, they may need to change their password etc so I need the option to intercept the authentication开发者_Python百科 and if everything is still ok allow them to continue or to redirect them to the proper login page.

I would be greatful for guidance on both of these two points. I gather for the second I can possibly put something in global.asax to intercept the authentication?

Thanks in advance.


For me the solution was differentiating between a browser-session auth cookie (not to be confused with the asp.net session cookie) and a persistent one - setting a low expiration will create a persistent cookie meaning it gets remembered when the browser is closed and re-opened within the expiration time. The following works for me:

public void SetAuthenticationCookie(LoginView loginModel)
    {
      if (!loginModel.RememberMe)
      {
        FormsAuthentication.SetAuthCookie(loginModel.Email, false);
        return;
      }
      const int timeout = 2880; // Timeout is in minutes, 525600 = 365 days; 1 day = 1440.
      var ticket = new FormsAuthenticationTicket(loginModel.Email, loginModel.RememberMe, timeout);
      //ticket.
      string encrypted = FormsAuthentication.Encrypt(ticket);
      var cookie = new HttpCookie(FormsAuthentication.FormsCookieName, encrypted)
        {
          Expires = System.DateTime.Now.AddMinutes(timeout),
          HttpOnly = true
        };
      HttpContext.Current.Response.Cookies.Add(cookie);
    }


FormsAuthentication and MembershipProviders are two completely different things, still they are made to work with each other very well. If you have written a persistent cookie ["Remember Me"] then next time, you can simply call Membership.GetUser() which will return you the MembershipUser instance of the currently logged in user or null if no user is logged in.

So first time when user arrives and authenticates with "Remember Me", you shall write a persistent cookie as following.

FormsAuthentication.RedirectFromLoginPage(strUserName, true);

Assuming user does not logout and leaves webpage and comes back after sometime. You can simply call MembershipUser.GetUser() as following and check if the user is already logged from the persistent cookie written by FormsAuthentication.

MembershipUser someUser = Membership.GetUser();
if(someUser == null)
{
    FormsAuthentication.SignOut();
    FormsAuthentication.RedirectToLoginPage();
}
else
{
    //Take where logged in users go.
}

You can do this check on your Login page itself or main landing page to intercept the User account to check if he needs to change the password or if the account is disabled as in your case.

EDIT

There are two ways to do this.

1.) Check for authentication as mentioned above in Session_Start event in global.asax and set a session key that becomes available on all pages for that particular session.

2.) Another way is too keep a common application wide common PageBase class that inherits from System.Web.UI.Page and acts as base page class for all your asp.net pages. On the Page Load of the common PageBase class check for the authentication as mentioned above. You will have to carefully write conditional redirection in this case since this might head towards infinite redirection with no end since it will run on Page_Load of all page from the common PageBase class.

public class PageBase : System.Web.UI.Page
{
    /// <summary>
    /// Initializes a new instance of the Page class.
    /// </summary>
    public Page()
    {
        this.Load += new EventHandler(this.Page_Load);
    }


    private void Page_Load(object sender, EventArgs e)
    {
        try
        {
            AuthenticateUser();
        }
        catch
        {
            //handle the situation gracefully.
        }
    }

    private AuthenticateUser()
    {
        MembershipUser someUser = Membership.GetUser();
        if(someUser == null)
        {
            FormsAuthentication.SignOut();
            FormsAuthentication.RedirectToLoginPage();
        }
        else
        {
            //Take where logged in users go.
        }
    }
}

//in your asp.net page code-behind

public partial class contact : PageBase
{
    protected void Page_Load(object sender, EventArgs e)
    {

    }
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜