cas_client之authenticationfilter源码分析

author author     2022-08-24     339

关键词:

packageorg.jasig.cas.client.authentication;

 

import java.io.IOException;

import java.io.PrintStream;

import java.util.Date;

import java.util.HashMap;

import java.util.Map;

import javax.servlet.FilterChain;

import javax.servlet.FilterConfig;

import javax.servlet.ServletException;

import javax.servlet.ServletRequest;

import javax.servlet.ServletResponse;

importjavax.servlet.http.HttpServletRequest;

importjavax.servlet.http.HttpServletResponse;

import javax.servlet.http.HttpSession;

import org.jasig.cas.client.util.AbstractCasFilter;

importorg.jasig.cas.client.util.CommonUtils;

importorg.jasig.cas.client.util.ReflectUtils;

importorg.jasig.cas.client.validation.Assertion;

import org.slf4j.Logger;

 

public class AuthenticationFilter

 extends AbstractCasFilter

{

 //sso中心认证服务的登录地址。

 private String casServerLoginUrl;

 private boolean renew = false;

 private boolean gateway = false;

 //网关存储解析器。

 private GatewayResolver gatewayStorage = newDefaultGatewayResolverImpl();

 //认证重定向策略,默认是直接重定向地址。

 private AuthenticationRedirectStrategy authenticationRedirectStrategy =new DefaultAuthenticationRedirectStrategy();

 //可以被忽略的url模式匹配策略。

 private UrlPatternMatcherStrategy ignoreUrlPatternMatcherStrategyClass =null;

 private static final Map<String, Class<? extendsUrlPatternMatcherStrategy>> PATTERN_MATCHER_TYPES = new HashMap();

 //默认3种模式匹配策略:包含、正则、相等。

 static

  {

   PATTERN_MATCHER_TYPES.put("CONTAINS",ContainsPatternUrlPatternMatcherStrategy.class);

   PATTERN_MATCHER_TYPES.put("REGEX",RegexUrlPatternMatcherStrategy.class);

   PATTERN_MATCHER_TYPES.put("EXACT",ExactUrlPatternMatcherStrategy.class);

  }

 

 protected void initInternal(FilterConfig filterConfig)

   throws ServletException

  {

   if (!isIgnoreInitConfiguration())

    {

     super.initInternal(filterConfig);

     setCasServerLoginUrl(getPropertyFromInitParams(filterConfig,"casServerLoginUrl", null));

     this.logger.trace("Loaded CasServerLoginUrl parameter: {}",this.casServerLoginUrl);

     setRenew(parseBoolean(getPropertyFromInitParams(filterConfig,"renew", "false")));

     this.logger.trace("Loaded renew parameter: {}",Boolean.valueOf(this.renew));

     setGateway(parseBoolean(getPropertyFromInitParams(filterConfig,"gateway", "false")));

     this.logger.trace("Loaded gateway parameter: {}",Boolean.valueOf(this.gateway));

     //忽略模式:可以自定义、根据实际情况配置,默认是正则表达式。

     String ignorePattern = getPropertyFromInitParams(filterConfig,"ignorePattern", null);

     this.logger.trace("Loaded ignorePattern parameter: {}",ignorePattern);

     //默认是正则模式,可以自定义实现UrlPatternMatcherStrategy接口。

     String ignoreUrlPatternType = getPropertyFromInitParams(filterConfig,"ignoreUrlPatternType", "REGEX");

     this.logger.trace("Loaded ignoreUrlPatternType parameter: {}",ignoreUrlPatternType);

     if (ignorePattern != null)

     {

       Class<? extends UrlPatternMatcherStrategy> ignoreUrlMatcherClass =(Class)PATTERN_MATCHER_TYPES.get(ignoreUrlPatternType);

       if (ignoreUrlMatcherClass != null) {

         this.ignoreUrlPatternMatcherStrategyClass = ((UrlPatternMatcherStrategy)ReflectUtils.newInstance(ignoreUrlMatcherClass.getName(),new Object[0]));

       } else {

         try

         {

           this.logger.trace("Assuming {} is a qualified class name...",ignoreUrlPatternType);

           this.ignoreUrlPatternMatcherStrategyClass =((UrlPatternMatcherStrategy)ReflectUtils.newInstance(ignoreUrlPatternType, newObject[0]));

         }

         catch (IllegalArgumentException e)

         {

           this.logger.error("Could not instantiate class [{}]",ignoreUrlPatternType, e);

         }

       }

       if (this.ignoreUrlPatternMatcherStrategyClass != null) {

         this.ignoreUrlPatternMatcherStrategyClass.setPattern(ignorePattern);

       }

     }

     String gatewayStorageClass = getPropertyFromInitParams(filterConfig,"gatewayStorageClass", null);

     if (gatewayStorageClass != null) {

       this.gatewayStorage =((GatewayResolver)ReflectUtils.newInstance(gatewayStorageClass, newObject[0]));

     }

     String authenticationRedirectStrategyClass =getPropertyFromInitParams(filterConfig,"authenticationRedirectStrategyClass", null);

     if (authenticationRedirectStrategyClass != null) {

       this.authenticationRedirectStrategy =((AuthenticationRedirectStrategy)ReflectUtils.newInstance(authenticationRedirectStrategyClass,new Object[0]));

     }

    }

  }

 

 public void init()

  {

   super.init();

   CommonUtils.assertNotNull(this.casServerLoginUrl,"casServerLoginUrl cannot be null.");

  }

 

 public final void doFilter(ServletRequest servletRequest,ServletResponse servletResponse, FilterChain filterChain)

   throws IOException, ServletException

  {

   HttpServletRequest request = (HttpServletRequest)servletRequest;

   HttpServletResponse response = (HttpServletResponse)servletResponse;

   //判断当前请求url是否可以被忽略模式匹配认证通过。

   if (isRequestUrlExcluded(request))

    {

     this.logger.debug("Request is ignored.");

     filterChain.doFilter(request, response);

     return;

    }

   //获取sso认证中心存储的session属性_const_cas_assertion_。

   HttpSession session = request.getSession(false);

   Assertion assertion = session != null ?(Assertion)session.getAttribute("_const_cas_assertion_") : null;

   if (assertion != null)

    {

     filterChain.doFilter(request, response);

     return;

    }

   //从request中构建需要认证的服务url。

   String serviceUrl = constructServiceUrl(request, response);

   //从request中获取票据ticket。

   String ticket = retrieveTicketFromRequest(request);

   //如果设置网关,则从session当中获取属性_const_cas_gateway,并从session中去掉此属性。

   boolean wasGatewayed = (this.gateway) &&(this.gatewayStorage.hasGatewayedAlready(request, serviceUrl));

   //如果存在认证票据ticket或者网关设置,则直接认证通过。

   if ((CommonUtils.isNotBlank(ticket)) || (wasGatewayed))

    {

     filterChain.doFilter(request, response);

     return;

    }

   this.logger.debug("no ticket and no assertion found");

   String modifiedServiceUrl;

   if (this.gateway)

    {

     this.logger.debug("setting gateway attribute in session");

    //在session中设置网关属性_const_cas_gateway=yes

     modifiedServiceUrl = this.gatewayStorage.storeGatewayInformation(request,serviceUrl);

    }

   else

    {

     modifiedServiceUrl = serviceUrl;

    }

   this.logger.debug("Constructed service url: {}",modifiedServiceUrl);

   //直接重定向sso认证中心url,进行登录认证。

   String urlToRedirectTo = CommonUtils.constructRedirectUrl(this.casServerLoginUrl,getServiceParameterName(), modifiedServiceUrl, this.renew, this.gateway);

   

 

   this.logger.debug("redirecting to "{}"",urlToRedirectTo);

   this.authenticationRedirectStrategy.redirect(request, response,urlToRedirectTo);

  }

 

 public final void setRenew(boolean renew)

  {

   this.renew = renew;

  }

 

 public final void setGateway(boolean gateway)

  {

   this.gateway = gateway;

  }

 

 public final void setCasServerLoginUrl(String casServerLoginUrl)

  {

   this.casServerLoginUrl = casServerLoginUrl;

  }

 

 public final void setGatewayStorage(GatewayResolver gatewayStorage)

  {

   this.gatewayStorage = gatewayStorage;

  }

  //根据可以忽略的URL地址匹配策略,来判断当前请求url是否可以认证:因此在配置此过滤器的时候,如果存在不需要认证的url,那么就可以根据url的形式配置ignorePattern参数和ignoreUrlPatternType参数。

 private boolean isRequestUrlExcluded(HttpServletRequest request)

  {

   if (this.ignoreUrlPatternMatcherStrategyClass == null) {

     return false;

    }

   StringBuffer urlBuffer = request.getRequestURL();

   if (request.getQueryString() != null) {

     urlBuffer.append("?").append(request.getQueryString());

    }

   String requestUri = urlBuffer.toString();

   return this.ignoreUrlPatternMatcherStrategyClass.matches(requestUri);

  }

}


本文出自 “12664863” 博客,请务必保留此出处http://12674863.blog.51cto.com/12664863/1904233

cas_client之代理配置

本环境基于cas3.4.2进行配置,3个tomcat环境:单点登录tomcat、代理tomcat和被代理tomcat。目的是通过代理app1访问被代理app2,此配置完全根据源代码分析而来(因此基础好的直接读源代码研究更好)。1、单点登录tomcat发布配置,网上... 查看详情

shiroapacheshiro架构之身份认证(authentication)

...  本文参考自ApacheShiro的官方文档:http://shiro.apache.org/authentication.html。  本文遵循以下流程:先介绍Shiro中的身份认证,再通过一个实例来具体说明一下(基于ma 查看详情

asp.netcore框架探索之authentication(代码片段)

...证,我们首先需要在容器中注入认证服务,使用services.AddAuthentication。进入该方法的源码,最重要的其实就是AddAuthenticationCore方法,他向容器中注入了认证体系中很重要的对象:IAuthenticationService、IAuthenti 查看详情

shiro系列之shiro+mysql实现用户认证(authentication)(代码片段)

网上大多数介绍ApacheShiro的资料都是使用ini文件的简单配置为例,很少用讲到如何配合数据库来实现用户认证的。我也是刚刚开始接触Shiro,在这里介绍一个入门级别的Shiro+Mysql的配置方法,这个方法仅仅是个开始&#... 查看详情

spring-security-文档笔记之认证组件

...是调用静态方法.其策略有三种:获取用户信息:类图:存储Authentication对象.在成功调用AuthenticationManager.authenticate(Authentication)方法后,用于存储已认证用户的信息.如果其authenticated属性值为false,SpringSecurity都将会对其进行验证.Collection&l... 查看详情

shiro之身份验证身份认证流程

...b;2.SecurityManager负责真正的身份验证逻辑;它会委托给Authenticator进行身份验证;3.Authenticator才是真正的身份验证者,ShiroAPI中核心的身份认证入口点,此处可以自定义插入自己的实现;4.Authenticator可能会委托给... 查看详情

django之用户认证组件(代码片段)

...用的是Django自带一个表:auth_user  一、auth模块  1,authenticate()判断用户是否存在方法user=authenticate(username=‘xxx‘,password=‘xxxx‘)#需要提供两个参数,username,password关键字参数如果auth_user表中存在这个用户,会返回一个us... 查看详情

django-rest-framework框架总结之认证权限限流过滤分页及异常处理(代码片段)

认证AuthenticationREST框架提供了几种即用的身份验证方案,并且支持实现自定义认证。我们需要在setting.py文件中设置DEFAULT_AUTHENTICATION_CLASSES全局默认身份验证方案。例如。REST_FRAMEWORK='DEFAULT_AUTHENTICATION_CLASSES':['rest_f... 查看详情

django之权限和分组(代码片段)

##登录、注销和登录限制:###登录:在使用authenticate进行验证后,如果验证通过了。那么会返回一个user对象,拿到user对象后,可以使用django.contrib.auth.login进行登录。示例代码如下:user=authenticate(username=username,password=password)ifuserisn... 查看详情

django之用户认证auth模块(代码片段)

一、auth模块fromdjango.contribimportauth1、authenticate() :验证用户输入的用户名和密码是否相同提供了用户认证,即验证用户名以及密码是否正确,一般需要username password两个关键字参数如果认证信息有效,会返回一个 User&nbs... 查看详情

django之auth认证组件(代码片段)

...rpythonmanage.pycreateuser-模块的导入:fromdjango.contribimportauth1.authenticate()提供了用户认证功能,即验证用户名以及密码是否正确,一般需要username、password两个关键字参数。如果认证成功(用户名和密码正确有效),便会返回一个User... 查看详情

drf之三大认证(代码片段)

...从之前对drf的源码分析可以看到,三条语句。self.perform_authentication(request)self.check_permissions(request)self.check_throttles(request)这就是drf的三大认证。二、用户认证1.drf的用户认证?我们的某些接口需要对用户进行辨别,那么我们该如何区... 查看详情

三大认证之认证组件和权限组件(代码片段)

...:代表校验失败,抛出异常,返回403权限异常结果self.perform_authentication(request)#权限组件:校验用户权限-必须登录,所有用户,登录读写游客只读,自定义用户角色#认证通过:可以进入下一步校验(频率认证)#认证失败:抛出异常,返回403权限... 查看详情

认证之匿名用户(代码片段)

...r访问返Tuer,匿名用户必须返回None,即不处理#认证类classAuthentication(object):defauthenticate(self,request):token=request.GET.get(‘token‘)obj=models.Token.objects.filter(token=token).first()ifobj:#returnobj.user.username,obj.tokenreturnobj.user,obj.tokenelse:#raiseexceptions.... 查看详情

核心组件之userdetailservice

简介:UserDetails=>SpringSecurity基础接口Authentication=>认证对象,可通过SecurityContext获得principal=>用户信息对象,是一个Object,通常可转为UserDetails UserDetails  用于表示一个principal,但是一般情况下是作为(你所使用的... 查看详情

细说shiro之组件架构

...e.org/如图所示,Shiro主要组件包括:Subject,SecurityManager,Authenticator,Authorizer,SessionManager,CacheManager,Cryptography,Realms。1.SubjectSubject表示与系统交互的对象,可以是登录系统的操作用户,也可能是另外一个软件系统。Subje 查看详情

openstack组件之keystone

一、概念1、keystone的作用作为OpenStack的基础支持服务,Keystone做下面这几件事情:    管理用户及其权限    维护OpenStackServices的Endpoint(短点)    Authentication(认证)和Authorization(鉴权 查看详情

django之用户认证组件

...ntrib.auth中提供了许多方法,这里主要介绍其中的三个:1.authenticate()提供了用户认证,即验证用户名以及密码是否正确,一般需要username password两个关键字参数如果认证信息有效,会返回一个User对象 查看详情