• Sharepoint 2010 Form认证自定义登录页面,总是自动登录问题


    说明

    关于Sharepoint表单登录自定义页面网上有好多,这里也就不重复说了,我也是从网上找的代码,使用网上的代码正常登录是没有问题的,都是很正常的,但是有一点小细节,就是都是默认记住密码的。

    这个也是客户提出来的,他们希望用户登录之后,每次关闭浏览器之后登录凭据就应该过期,让用户重新登录,网上的代码实现不了。

    解决方法

    这个问题应该怎么解决呢,Form认证一般都是把验证信息存在Cookie中,让Cookie在浏览器关闭的时候过期就可以了,我记得以前在做Asp.Net开发的时候是可以这么做的,现在都忘了,隐约记得应该是保存在Session中,可以实现关闭浏览器过期效果,方向有了,是不是在代码中可以设置把凭据保存到Session中呢?

    网上找了好长时间也没有关于sharepoint登录关闭浏览器过期怎么做。突然想到Sharepoint默认页面有一个Rember Me这个东西,我就想是不是和这个东西有关系。

    找到Sharepoint的DLL,反编译一下看看代码:默认登录的代码在”Microsoft.SharePoint.IdentityModel.DLL”中。

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

    SetPrincipalAndWriteSessionToken方法有两个重载:

    public void SetPrincipalAndWriteSessionToken(SecurityToken securityToken);
    
    public void SetPrincipalAndWriteSessionToken(SessionSecurityToken sessionToken, bool isSession);

    一般时候网上提供的都是第一个,我们可以看出,第二个方法提供了是否使用Session来保存凭据,那么好了找到方向了。直接使用第二个重载就可以了。

    当我写到“SessionSecurityToken”这个参数的时候,问题又来了,我们办法得到这个参数,参考微软的代码:

            /// <summary>
            /// 获取SessionToken
            /// </summary>
            /// <param name="_SecurityToken"></param>
            /// <returns></returns>
            private static SessionSecurityTokenCreatedEventArgs GetSessionToken(SecurityToken _SecurityToken)
            {
                GenericXmlSecurityToken genericXmlSecurityToken = _SecurityToken as GenericXmlSecurityToken;
                if (genericXmlSecurityToken != null)
                {
                    _SecurityToken = GetSecurityToken(genericXmlSecurityToken);
                }
    
                IClaimsPrincipal claimsPrincipal = AuthenticateUser(_SecurityToken);
                SessionSecurityTokenCreatedEventArgs sessionSecurityTokenCreatedEventArgs = new SessionSecurityTokenCreatedEventArgs(new SessionSecurityToken(claimsPrincipal, null, new DateTime?(tk.ValidFrom), new DateTime?(tk.ValidTo))
                {
                    IsPersistent = false
                });
                return sessionSecurityTokenCreatedEventArgs;
            }
            /// <summary>
            /// 微软方法,获取SecurityToken,不清楚微软为什么这么做
             /// </summary>
            /// <param name="token"></param>
            /// <returns></returns>
            internal static SecurityToken GetSecurityToken(GenericXmlSecurityToken token)
            {
                if (token == null)
                {
                    throw new ArgumentNullException("token");
                }
                SecurityToken result = null;
                SecurityTokenHandlerCollection securityTokenHandlerCollection = SecurityTokenHandlerCollection.CreateDefaultSecurityTokenHandlerCollection();
                using (XmlNodeReader xmlNodeReader = new XmlNodeReader(token.TokenXml))
                {
                    result = securityTokenHandlerCollection.ReadToken(xmlNodeReader);
                }
                return result;
            }
            /// <summary>
            /// 获取声明
             /// </summary>
            /// <param name="securityToken"></param>
            /// <returns></returns>
            internal static IClaimsPrincipal AuthenticateUser(SecurityToken securityToken)
            {
                if (securityToken == null)
                {
                    throw new ArgumentNullException("securityToken");
                }
                if (securityToken.SecurityKeys != null && securityToken.SecurityKeys.Count != 0)
                {
                    throw new SecurityTokenException("Bearer token required.");
                }
                GenericXmlSecurityToken genericXmlSecurityToken = securityToken as GenericXmlSecurityToken;
                if (genericXmlSecurityToken != null)
                {
                    securityToken = GetSecurityToken(genericXmlSecurityToken);
                }
                ServiceConfiguration serviceConfiguration = FederatedAuthentication.ServiceConfiguration;
                ClaimsIdentityCollection identityCollection = serviceConfiguration.SecurityTokenHandlers.ValidateToken(securityToken);
                string resourceName = null;
                if (HttpContext.Current != null)
                {
                    resourceName = HttpContext.Current.Request.RawUrl;
                }
                return serviceConfiguration.ClaimsAuthenticationManager.Authenticate(resourceName, new ClaimsPrincipal(identityCollection));
            }

    最后正确调用方法:

    SPFederationAuthenticationModule fam = SPFederationAuthenticationModule.Current;
    fam.SetPrincipalAndWriteSessionToken(sessionSecurityTokenCreatedEventArgs.SessionToken, true);

    总结

    要想实现关闭浏览器凭据过期我们需要把凭据存储在Session中,根据上面提供的代码获取SessionToken。

    这个连接下的方法也不错。

    https://social.msdn.microsoft.com/Forums/en-US/06ec9060-4b98-412c-b6d5-7a7139b36839/autologin-with-forms-authentication?forum=sharepointdevelopmentprevious

  • 相关阅读:
    367 Valid Perfect Square 有效的完全平方数
    365 Water and Jug Problem 水壶问题
    363 Max Sum of Rectangle No Larger Than K 最大矩阵和不超过K
    357 Count Numbers with Unique Digits 计算各个位数不同的数字个数
    SpringBoot (四) :thymeleaf 使用详解
    SpringBoot(三) :Spring boot 中 Redis 的使用
    SpringBoot(二) :web综合开发
    SpringBoot (一) :入门篇
    程序员最核心的竞争力是什么?
    Java面试题:多继承
  • 原文地址:https://www.cnblogs.com/qiumc/p/4835614.html
Copyright © 2020-2023  润新知