locked
How to create both persistent and session cookies ? RRS feed

  • Question

  • Is it possible to use both Session and Persistent cookies in SharePoint 2010 Claims based (FBA authenticated) sites ? My requirement is very simple:

    • When a user selects remember me on the login page, they should NEVER be timed out (atleast 1 year) [persistent cookie needs to written to the disk ?]
    • When a user does not select remember me, the user should login after closing the browser or after session times out

    This was very easy to do in MOSS 2007 with FBA persistent cookies. But in 2010 with CBA and Security Token Service, I am not even sure if this is possible. Any guidance or suggestions ?

    Wednesday, December 29, 2010 7:04 PM

Answers

  • In short, with the OOTB form authentication login page, the rememberMe checkbox is hidden if the UseSessionCookies is set to True; And the rememberMe checkbox work as expected if the UseSessionCookies is set to False. that may answer your original question.

    With Reflector, you can find in:

    private void AuthenticateEventHandler(object sender, AuthenticateEventArgs formAuthenticateEvent);
    Declaring Type: Microsoft.SharePoint.IdentityModel.Pages.FormsSignInPage
    Assembly: Microsoft.SharePoint.IdentityModel, Version=14.0.0.0


    the following code:

                SPSessionTokenWriteType writeDefaultCookie = SPSessionTokenWriteType.WriteDefaultCookie;
                if (!SPSecurityTokenServiceManager.Local.UseSessionCookies && !formsSignInControl.RememberMeSet)
                {
                    writeDefaultCookie = SPSessionTokenWriteType.WriteSessionCookie;
                }
                base.EstablishSessionWithToken(securityToken, writeDefaultCookie);


    And in:

    internal void EstablishSessionWithToken(SecurityToken securityToken, SPSessionTokenWriteType sessionCookie);
    Declaring Type: Microsoft.SharePoint.IdentityModel.Pages.IdentityModelSignInPageBase
    Assembly: Microsoft.SharePoint.IdentityModel, Version=14.0.0.0
     
    The following code:

        SecurityContext.RunAsProcess(() => fam.SetPrincipalAndWriteSessionToken(securityToken, sessionCookie));


    However, my test yesterday with the custom login page calls the SetPrincipalAndWriteSessionToken without the sessionCookie parameter, so does many online sample as http://blogs.technet.com/b/speschka/archive/2010/07/21/writing-a-custom-forms-login-page-for-sharepoint-2010-part-1.aspx

                    SPFederationAuthenticationModule fam = SPFederationAuthenticationModule.Current;
                    fam.SetPrincipalAndWriteSessionToken(token);



    • Marked as answer by GuYuming Tuesday, November 29, 2011 3:44 AM
    • Edited by GuYuming Friday, December 23, 2011 7:01 AM
    Thursday, November 10, 2011 2:18 AM
  • I dont know about Forms Authentication. Here is my Solution for a Claims enabled Site:

    based on examples to implement  Sliding Sessions in Sharepoint 2010  (http://blogs.southworks.net/fboerr/2011/04/15/sliding-sessions-in-sharepoint-2010/)

     

    I set UseSessionCookies to true

     $sts.UseSessionCookies=$True

    and create a helper Cookie "mypersist" the user can set or not (using a webpart to do so)

    And a custom Http Module hooking into sam.SessionSecurityTokenReceived

    if (!e.SessionToken.IsPersistent && ctx.Request.Cookies["mypersist"] != null){
    
    SPSessionAuthenticationModule spsam = sender as SPSessionAuthenticationModule;
    
    e.SessionToken = spsam.CreateSessionSecurityToken(e.SessionToken.ClaimsPrincipal, e.SessionToken.Context,
                            validFrom, newValidTo, true);
    e.ReissueCookie = true;
    }
    

    regards

    --

    Markus

    • Marked as answer by GuYuming Tuesday, March 13, 2012 1:26 AM
    Tuesday, November 29, 2011 12:47 AM

All replies

  • The SharePoint 2010 Security Token Service (STS) maintains a session in which the same token is reused. This session defaults to 10 hrs and is on the server. You can use PowerShell command to update this value, please read http://www.shillier.com/archive/2010/10/25/authorization-failures-with-claims-based-authentication-in-sharepoint-2010.aspx for detail.

    And for persistent cookie, if you check the "sign me in automatically" on the default FBA login page, it will be created. You can find the cookie with IE8 Developer tools->Cach->View Cookie Information (search for the cookie "FedAuth").

    Friday, December 31, 2010 8:46 AM
  • Thank you for the reply GuYuming. You are correct about the session cookies and after updating the value appropriately, I can set up the session cookie.

    However, for the persistent cookie I have a custom login page which does some additional verification. Can I do the same thing in the custom login page ? Using reflector, I was able to look at the code which creates persistent cookies but some of the classes are internal and it would be too much of work to recreate them. Any suggestions here ? Thanks in advance.

    Monday, January 3, 2011 3:16 AM
  • I did try out the sample. But even after using the code, the cookie seems to be based of a setting in the SecurityTokenServiceManager class.

    Specifically, SPSecurityTokenServiceManager.UseSessionCookies Property. If this property is set to true, then NO persistent cookies are created. If this is set to false, then persistent cookies are created with a lifetime associated with the property SPSecurityTokenServiceManager.FormsTokenLifetime.

    Do I need to modify these properties everytime a session cookie or a persistent cookie is created ? There is a high chance that every other user might select remember me while logging in and this will impact the performance heavily.

    Can we do something like below:

    token = SPSecurityContext.SecurityTokenForFormsAuthentication(
        appliesTo,
        authProvider.MembershipProvider,
        authProvider.RoleProvider,
        formsLoginControl.UserName,
        formsLoginControl.Password, RememberMe);

    If rememberme is true, then it would create a persistent cookie(from the token ofcourse) otherwsie it would create a session cookie.

    Thanks for all your help.

    Monday, January 3, 2011 3:09 PM
  • This still does NOT answer my question.
    Friday, January 7, 2011 8:04 PM
  • Did you find any solution? i am facing similar issue.
    Tuesday, August 9, 2011 1:44 PM
  • I'm having the same issue.  Any solution out there?
    Tuesday, November 8, 2011 8:16 PM
  • According to http://msdn.microsoft.com/en-us/library/aa289495(v=vs.71).aspx ,if you do not set the cookie's expiration, the cookie is created but it is not stored on the user's hard disk. Instead, the cookie is maintained as part of the user's session information. When the user closes the browser or if the session times out, the cookie is discarded.

     


    • Edited by GuYuming Wednesday, November 9, 2011 6:14 AM
    • Proposed as answer by Sjoukje ZaalMVP Wednesday, November 9, 2011 7:15 AM
    Wednesday, November 9, 2011 4:42 AM
  • My test result is that if i set UseSessionCookies to True with PowerShell:

    $sts = Get-SPSecurityTokenServiceConfig
    $sts.UseSessionCookies=$True
    $sts.Update()


    token = SPSecurityContext.SecurityTokenForFormsAuthentication(
         appliesTo,
         authProvider.MembershipProvider,
         authProvider.RoleProvider,
         formsLoginControl.UserName,
         formsLoginControl.Password, True);


    still create session cookie.

    If i set UseSessionCookies to be False. And the RememberMe to False, persistent cookie is still created.

    That is, the RememberMe, or the isPersistent parameter in SPSecurityContext.SecurityTokenForFormsAuthentication cannot meet your requirement. I have applied 2011 Oct CU.


    • Edited by GuYuming Wednesday, November 9, 2011 9:42 AM
    Wednesday, November 9, 2011 9:28 AM
  • And my test result is that if the UseSessionCookies is set to False, for the default form authentication page (_forms/default.aspx), the sign in my automatically works as you expected.

    if the UseSessionCookies is set to True, the checkbox is hidden.

    following is from the onload of the default.aspx:

        CheckBox box = null;
        if (SPSecurityTokenServiceManager.Local.UseSessionCookies && ((box = this.signInControl.FindControl("RememberMe") as CheckBox) != null))
        {
            box.Enabled = false;
            box.Visible = false;
        }

    Wednesday, November 9, 2011 11:30 AM
  • OK.  I'm still confused.  It seems to me that the only thing that works is the SPSecurityTokenServiceManager.UseSessionCookies attribute.  If it's set to TRUE, then all cookies are valid for that session only.  So the "Remember Me" check box does NOT work.  If it's set to FALSE, then all cookies are persistent.  So the "Remember Me" check box always behaves as if it were true.  What I really want is for each user to decide whether it should be TRUE or FALSE for his/her Session.  Is that possible to do?

    Thanks.

    Wednesday, November 9, 2011 2:45 PM
  • In short, with the OOTB form authentication login page, the rememberMe checkbox is hidden if the UseSessionCookies is set to True; And the rememberMe checkbox work as expected if the UseSessionCookies is set to False. that may answer your original question.

    With Reflector, you can find in:

    private void AuthenticateEventHandler(object sender, AuthenticateEventArgs formAuthenticateEvent);
    Declaring Type: Microsoft.SharePoint.IdentityModel.Pages.FormsSignInPage
    Assembly: Microsoft.SharePoint.IdentityModel, Version=14.0.0.0


    the following code:

                SPSessionTokenWriteType writeDefaultCookie = SPSessionTokenWriteType.WriteDefaultCookie;
                if (!SPSecurityTokenServiceManager.Local.UseSessionCookies && !formsSignInControl.RememberMeSet)
                {
                    writeDefaultCookie = SPSessionTokenWriteType.WriteSessionCookie;
                }
                base.EstablishSessionWithToken(securityToken, writeDefaultCookie);


    And in:

    internal void EstablishSessionWithToken(SecurityToken securityToken, SPSessionTokenWriteType sessionCookie);
    Declaring Type: Microsoft.SharePoint.IdentityModel.Pages.IdentityModelSignInPageBase
    Assembly: Microsoft.SharePoint.IdentityModel, Version=14.0.0.0
     
    The following code:

        SecurityContext.RunAsProcess(() => fam.SetPrincipalAndWriteSessionToken(securityToken, sessionCookie));


    However, my test yesterday with the custom login page calls the SetPrincipalAndWriteSessionToken without the sessionCookie parameter, so does many online sample as http://blogs.technet.com/b/speschka/archive/2010/07/21/writing-a-custom-forms-login-page-for-sharepoint-2010-part-1.aspx

                    SPFederationAuthenticationModule fam = SPFederationAuthenticationModule.Current;
                    fam.SetPrincipalAndWriteSessionToken(token);



    • Marked as answer by GuYuming Tuesday, November 29, 2011 3:44 AM
    • Edited by GuYuming Friday, December 23, 2011 7:01 AM
    Thursday, November 10, 2011 2:18 AM
  • I dont know about Forms Authentication. Here is my Solution for a Claims enabled Site:

    based on examples to implement  Sliding Sessions in Sharepoint 2010  (http://blogs.southworks.net/fboerr/2011/04/15/sliding-sessions-in-sharepoint-2010/)

     

    I set UseSessionCookies to true

     $sts.UseSessionCookies=$True

    and create a helper Cookie "mypersist" the user can set or not (using a webpart to do so)

    And a custom Http Module hooking into sam.SessionSecurityTokenReceived

    if (!e.SessionToken.IsPersistent && ctx.Request.Cookies["mypersist"] != null){
    
    SPSessionAuthenticationModule spsam = sender as SPSessionAuthenticationModule;
    
    e.SessionToken = spsam.CreateSessionSecurityToken(e.SessionToken.ClaimsPrincipal, e.SessionToken.Context,
                            validFrom, newValidTo, true);
    e.ReissueCookie = true;
    }
    

    regards

    --

    Markus

    • Marked as answer by GuYuming Tuesday, March 13, 2012 1:26 AM
    Tuesday, November 29, 2011 12:47 AM
  • did you ever resolve this? i have the same issue?

    thanks

    al

    Monday, March 12, 2012 5:56 PM
  • I gave up after my last post and didn't try any of the solutions posted since then.  I ended up hiding the "Remember Me" check box and asking the users to use their browser to save off User Names and Passwords if they wanted to.

    Deepak

    Tuesday, March 13, 2012 11:41 AM