前言

项目中我们经常需要对RESTful api进行拦截,主流实现方法有filter、interceptor、aop,先说一下他们各自的实现。

Filter

AnimalFilter实现javax.servlet.Filter,项目启动时已初始化完成,可在控制台看到打印的初始化日志。

@Component
    public class AnimalFilter implements Filter {
     
        private Logger logger = LoggerFactory.getLogger(getClass());
     
        @Override
        public void init(FilterConfig filterConfig) throws ServletException {
            logger.info("animalFilter 初始化。。。");
        }
     
        @Override
        public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
            logger.info("animalFilter doFilter 。。。");
            chain.doFilter(request,response);//过滤器将请求往下传递
        }
     
        @Override
        public void destroy() {
            logger.info("animalFilter 销毁。。。");
        }
    }

如何调用不被component修饰的filter,将上文中的component注解去除,通过下文方式,让注解生效并设置注解生效的url请求地址信息。

@Configuration
    public class AnimalWebConfig {
     
        @Bean
        public FilterRegistrationBean animalFilter(){
            FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean();
            AnimalFilter animalFilter = new AnimalFilter();
            filterRegistrationBean.setFilter(animalFilter);
            List<String> urlPattern = new ArrayList<>();
            urlPattern.add("/animal/getAnimalById/*");
            filterRegistrationBean.setUrlPatterns(urlPattern);
            return filterRegistrationBean;
        }
     
    }

由于filter获取的参数为ServletRequest request, ServletResponse response, FilterChain chain,无法知道是哪个类的那个方法调用,更无法知道调用时的参数。

Interceptor

首先编写一个AnimalInterceptor实现HandlerInteceptor方法,实现相应的三个方法,preHandle执行方法前执行返回的结果决定是否往下执行,postHandle当方法返回值时执行,afterCompletion无论成功或失败都将执行,前提是preHandler要返回true。

@Component
    public class AnimalInterceptor implements HandlerInterceptor {
     
        private Logger logger = LoggerFactory.getLogger(getClass());
     
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
            HandlerMethod handlerMethod = (HandlerMethod) handler;
            String methodName = handlerMethod.getMethod().getName();
            logger.info("AnimalInterceptor:preHandle:methodName:" + methodName);
            logger.info("AnimalInterceptor:preHandle");
            return true;
        }
     
        @Override
        public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
            HandlerMethod handlerMethod = (HandlerMethod) handler;
            logger.info("AnimalInterceptor:preHandle:methodName:" + handlerMethod.getMethod().getName());
            logger.info("AnimalInterceptor:postHandle");
        }
     
        @Override
        public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
            logger.info("AnimalInterceptor:afterCompletion");
        }
    }

将写好的AnimalInterceptor注入到spring的interceptor注册中心即可

@Component
    public class InterceptorConfig extends WebMvcConfigurerAdapter{
     
        @Autowired
        AnimalInterceptor animalInterceptor;
     
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            registry.addInterceptor(animalInterceptor);
        }
    }

虽然interceptor可以知道调用的controller,调用的方法,但获取不到调用方法的参数。

AOP

编写AnimalAspect如下,可将传递的参数打印出来,aop拦截规则设置请查看,https://blog.csdn.net/FU250/article/details/80219415

@Aspect
    @Component
    public class AnimalAspect {
        private Logger logger = LoggerFactory.getLogger(getClass());
     
        @Around("execution(* com.imooc.security.demo.web.controller..*.*(..))")
        public Object handleAnimalController(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
            Arrays.stream(proceedingJoinPoint.getArgs()).forEach(arg -> {
                logger.info("arg:"+arg);
            });
            logger.info("AnimalAspect");
            return proceedingJoinPoint.proceed();
        }
    }

三个拦截器的比较如下,根据自己的业务功能需求选择最合适的拦截器。


   

Spring 梳理 - filter、interceptor、aop实现与区别 -第一篇的更多相关文章

  1. spring boot: filter/interceptor/aop在获取request/method参数上的区别(spring boot 2.3.1)

    一,filter/interceptor/aop在获取参数上有什么区别? 1,filter可以修改HttpServletRequest的参数(doFilter方法的功能), interceptor/a ...

  2. Spring 梳理 - filter、interceptor、aop实现与区别 -第二篇

    spring mvc中的Interceptor可以理解为是Spring MVC框架对AOP的一种实现方式.一般简单的功能又是通用的,每个请求都要去处理的,比如判断token是否失效可以使用spring ...

  3. Filter ,Interceptor,AOP

    一.Filter: Filter也称之为过滤器,它是Servlet技术中比较激动人心的技术,WEB开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp, Servlet, 静态 ...

  4. Spring整合AspectJ的AOP

    学而时习之,不亦说乎!                              --<论语> 看这一篇之前最好先看前面关于AOP的两篇. http://www.cnblogs.com/z ...

  5. Spring框架IOC和AOP介绍

    说明:本文部分内容参考其他优秀博客后结合自己实战例子改编如下 Spring框架是个轻量级的Java EE框架.所谓轻量级,是指不依赖于容器就能运行的.Struts.Hibernate也是轻量级的. 轻 ...

  6. Spring切面编程之AOP

    AOP 是OOP 的延续,是Aspect Oriented Programming 的缩写,意思是面向切面编程.可以通过预编译方式和运行期动态代理实现在不修改源代码的情况下给程序动态统一添加功能的一种 ...

  7. Spring的IOC和AOP之深剖

    今天,既然讲到了Spring 的IOC和AOP,我们就必须要知道 Spring主要是两件事: 1.开发Bean:2.配置Bean.对于Spring框架来说,它要做的,就是根据配置文件来创建bean实例 ...

  8. Spring(6)—— AOP

    AOP(Aspect-OrientedProgramming)面向切面编程,与OOP完全不同,使用AOP编程系统被分为切面或关注点,而不是OOP中的对象. AOP的引入 在OOP面向对象的使用中,无可 ...

  9. spring+mybatis利用interceptor(plugin)兑现数据库读写分离

    使用spring的动态路由实现数据库负载均衡 系统中存在的多台服务器是"地位相当"的,不过,同一时间他们都处于活动(Active)状态,处于负载均衡等因素考虑,数据访问请求需要在这 ...

随机推荐

  1. PythonWeb框架Django:虚拟环境安装(virtualenv)

    虚拟环境的用处: 当我们有多个项目要使用不同的第三方类库的时候,就会发生冲突,因为Python的环境内只允许一个版本的第三方类库. 比如说 有A,B两个Web项目,但是A项目的Django的环境为2. ...

  2. Spring框架核心知识介绍

    一:spring框架介绍   1.spring框架是为了解决复杂的企业级应用而创建的, 使用Spring可以让简单的JavaBean实现之前只有EJB才能完成的事情.但是Spring不仅仅局限于服务器 ...

  3. 01 Python 基础数据类型

    基础数据类型,有7种类型,存在即合理. 1.int 整数 主要是做运算的 .比如加减乘除,幂,取余  + - * / ** %...2.bool 布尔值 判断真假以及作为条件变量3.str 字符串 存 ...

  4. 从入门到入土的JS 随笔day02 新手向

    讲讲自增自减和循环语句及三元一次表达式: 一.自增自减实际上就是按照顺序来解读代码, 例如,a++;代表了a先进行了计算,运算完毕后,才进行增加: ++a呢,则是先进行了自增,值加一后再进行运算: 如 ...

  5. Installing the JMeter CA certificate for HTTPS recording

    参考: http://jmeter.apache.org/usermanual/component_reference.html#HTTP(S)_Test_Script_Recorder User m ...

  6. 2018宁夏邀请赛K题Vertex Covers(高维前缀和 状压 折半

    https://vjudge.net/problem/Gym-102222K 题意:给定N点M边的无向图,每个点有点权.  点覆盖表示某个点集S{}覆盖了所有的边,其贡献是S中点权之积. 现在让你求所 ...

  7. JOBDU 1193 矩阵转置

    啊!!!这道题目今天竟然写错了!!!这道题目巨坑,说不能用数组,结果竟然是用数组做的,吐血!!! 看的所有有关博文,都是用数组做的,晕倒!真的出题人有毛病,出这种题,又不限制运行!!! 以后再遇到这种 ...

  8. 51 nod 石子归并 + v2 + v3(区间dp,区间dp+平行四边形优化,GarsiaWachs算法)

    题意:就是求石子归并. 题解:当范围在100左右是可以之间简单的区间dp,如果范围在1000左右就要考虑用平行四边形优化. 就是多加一个p[i][j]表示在i到j内的取最优解的位置k,注意能使用平行四 ...

  9. SQL数据同步到ELK(二)- Elastic Search 安装

    开篇废话 没错,前面扯了一堆SQL SERVER,其实我连Elastic Search根本没动手玩过(是不是与时代有点脱节了?),那今天我就准备尝试安装一个ELK的简单集群出来(这个集群是使用我的小米 ...

  10. C、C++格式化字符串

    引言 在C和C++开发中,我们经常会用到printf来进行字符串的格式化,例如printf("format string %d, %d", 1, 2);,这样的格式化只是用于打印调 ...