shiro过滤器详解分析

1 篇文章 0 订阅


shiro最核心的2个操作,一个是登录的实现,一就是过滤器了。(认证跟授权是最核心的功能)这里分析下shiro过滤器怎样玩的。

1,目标

这里会按如下顺序逐一看其实原理,并尽量找出其出处。

先看一下shiro过滤器有哪些及它们的别名分别对应哪些类: 点这里.
在这里插入图片描述
这里只分析平时用的最多的一个:authc过滤器,对应的处理器的类是FormAuthenticationFilter。

2、继承关系及结构

authc: 1.AbstractFilter > 2.NameableFilter > 3.OncePerRequestFilter > 4.AdviceFilter > 5.PathMatchingFilter > 6.AccessControlFilter > 7.AuthenticationFilter > 8.AuthenticatingFilter > 9.FormAuthenticationFilter
在这里插入图片描述
根据这个结构关系可以清楚的知道,接下来要分析的FormAuthenticationFilter上面还有8个。

3、Filter过滤器简介

tomcat中的自定义过滤器必需实现Filter接口,过滤器的实现方法为Filter中的

doFilter(ServletRequest request, ServletResponse response, FilterChain filterChain)

如果一个请求被该过滤器拦截,想要到达用户最后请求的地址,那么一定得有:filterChain.doFilter(request, response);这个方法的调用,表示通过过滤,请求可以到达用户的请求地址。否则用户的请求地址不会被调用,用户的请求被过滤器拦截。

4、shiro过滤器分析

1、AbstractFilter在这里插入图片描述

位于shiro过滤器最顶层,是个抽象方法,直接继承了Filter,
在这里插入图片描述
它只做了一些其本的初始化操作,并没有实现Filter中的doFilter方法。

总结:AbstractFilter只做了一些基本的初始化,并没有过多的逻辑在里面。

2、NameableFilter

在这里插入图片描述
允许通过getName和setName方式给过滤器命名。如果没有给该过滤器命名,那么默认将会使用web.xml中给定的名称(FilterConfiger的filterName)

在这里插入图片描述
该类可以理解为为过滤器命名用的,也没有实现Filter中的doFilter方法。

总结:NameableFilter是用于给过滤器命名使用的。

3、OncePerRequestFilter

在这里插入图片描述
filter的基类(说白了,就是正真实现了Filter中的doFilter方法的类),它用来保证在每个servlet容器上,第个请求都只会被过滤一次,不会重复过滤。

通过getAlreadyFilteredAttributeName()方法来鉴别请求是否已经被过滤过。默认的实现基于具体过滤的实例名称。

接下来看看具体逻辑:
在这里插入图片描述

  1. 判断过滤器是否已经执行过,如果执行过,调用filterChain.doFilter(request, response)直接放行,不再重复执行该过滤器的处理逻辑,直接走下一个过滤器或者通过该过滤进入到实际请求方法中。
  2. 判断过滤器是否开启,该类有个成员变量eabled,默认为true(注释给的解释是大多数的过滤器都是希望开启的,所以默认值为true),过滤器为开启状态,如果该过滤器没有被开启中,也同上面的逻辑一样,直接走下一个过滤器或者通过该过滤进入到实际请求方法中。
    在这里插入图片描述
  3. 这里又分3步,
    1、 设置一个已经执行过滤器的属性名称在request中。
    2、 调用doFilterInternal方法,执行真正的过滤器处理逻辑。
    3、 这个过滤器处理完后,将过滤器的属性名称从request中移出。这样如果程序执行到第2步,过滤又被调用了,它将会走到第一个if中,直接略过这个过滤器的处理,这样就保证了,每个过滤器在处理一个请求的时候只会被执行一次。

总结:OncePerRequestFilter提供了一个实际处理过滤业务的方法doFilterInternal,并且保证每个请求只会被该过滤器过滤一次。

4、AdviceFilter

在这里插入图片描述
这个过滤器,类似于开启了AOP环绕通知,提供了preHandle,postHandle和afterCompletion这三个方法。
其过滤逻辑为:doFilterInternal方法。

在这里插入图片描述
executeChain方法中的实现为:chain.doFilter(request, response);

所以如果preHandle方法返回false,则说明过滤器不会执行chain.doFilter,意味着请求被拦截掉了,不会进入到用户请求的地址上去。如果为true,表示过滤器放行了过滤的逻辑通过。

然后会执行postHandle方法(该类中的postHandle方法为空实现),

最后会执行一个,这个方法用于对一些异常进行处理(目前也是空实现)。

通过以上可以看出,过滤的逻辑代码实际上是在preHandle这个方法中处理的,这个方法的返回值true和false决定了请求放行和请求被拦截。

总结:AdviceFilter提供了类似于AOP环绕通知式的编程方式,其处理拦截的逻辑是在preHandle方法中完成的。preHandle方法返回true和false代表了通过过滤,请求可以到达用户的请求地址和过滤器拦截掉了用户的请求。

不完整,继续更新中。
博客引用地址.

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值