• springboot学习四:Spring Boot2.x 拦截器基础入门&实战项目场景实现


    导言

    SpringBoot 拦截器和过滤器区别及应用

    一、拦截器

    1. 拦截器是什么?
      简单的来说,就是一道阀门,在某个方法被访问之前,进行拦截,然后在之前或之后加入某些操作,拦截器是AOP 的一种实现策略。
    2. 拦截器主要做什么?
      • 对正在运行的流程进行干预。
    3. 拦截器的代码实现。拦截器也主要有三个方法:
      • 其中preHandle是在请求之前就进行调用,如果该请求需要被拦截,则返回false,否则true;
      • postHandle是在请求之后进行调用,无返回值;
      • afterCompletion是在请求结束的时候进行调用,无返回值。

    二、创建项目 springboot-interceptor

    1. 根据 springboot 学习二:springboot 第一次创建 web 项目,打包项目并测试成功 博文,快速创建本项目:springboot-interceptor
    2. 项目依赖仅勾选web即可。
    3. 项目结构如下:(记得修改application配置文件的后缀为 yml)
      在这里插入图片描述

    三、Interceptor 快速入门

    那么在 springBoot 中如何使用拦截器呢?
    步骤:

    1. 创建一个类实现 HandlerInterceptor 接口
    2. 再创建一个配置类实现 WebMvcConfigurer接口 ,重写 addInterceptors 方法

    1. 创建拦截器类

    创建我们自己的拦截器类并实现 HandlerInterceptor 接口。

    package com.feng.springboot_interceptor.interceptor;
    
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.web.servlet.HandlerInterceptor;
    import org.springframework.web.servlet.ModelAndView;
    
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    
    
    public class MyInterceptor implements HandlerInterceptor {
    
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
            System.out.println("MyInterceptor....在请求处理之前进行调用(Controller方法调用之前)");
            String requestUrl = request.getRequestURI();
            System.out.println("过滤器MyFilter拦截了请求为" + requestUrl);
            return true;
        }
    
        @Override
        public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
            System.out.println("MyInterceptor...请求处理之后进行调用,但是在视图被渲染之前(Controller方法调用之后)");
            //HandlerInterceptor.super.postHandle(request, response, handler, modelAndView);
        }
    
        @Override
        public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
            System.out.println("MyInterceptor....在整个请求结束之后被调用,也就是在DispatcherServlet 渲染了对 应的视图之后执行(主要是用于进行资源清理工作)");
            //HandlerInterceptor.super.afterCompletion(request, response, handler, ex);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32

    2. 修改 application.yml

    修改 application.properties 加入开发接口通配地址

    #凡是请求地址层级带有 open 都放行
    open:
      url: /**/open/**
    
    • 1
    • 2
    • 3

    3. 实现 WebMvcConfigurer

    创建一个 Java 实现 WebMvcConfigurer , 并重写 addInterceptors 方法。

    package com.feng.springboot_interceptor.config;
    
    import com.feng.springboot_interceptor.interceptor.MyInterceptor;
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
    import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
    
    @Configuration
    public class WebAppConfig implements WebMvcConfigurer {
        @Value("${open.url}")
        private String openUrl;
    
        @Bean
        public MyInterceptor getMyInterceptor() {
            return new MyInterceptor();
        }
    
        @Override
        public void addInterceptors(InterceptorRegistry registry) {
            // 拦截以 /api 开头的请求,但是排除  openUrl:/**/open/**。 即 :匹配这个(/**/open/**)URL的所有请求不拦截
            registry.addInterceptor(getMyInterceptor()).addPathPatterns("/api/**").excludePathPatterns(openUrl);
            // WebMvcConfigurer.super.addInterceptors(registry);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26

    4. 创建接口Interceptorcontroller

    package com.feng.springboot_interceptor.controller;
    
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    @RestController
    @RequestMapping("/api")
    public class InterceptorController {
    
        @GetMapping("/home/open/info")
        public String home() {
            return "欢迎来到首页";
        }
    
        @GetMapping("/user/interceptor")
        public String interceptor() {
            return "我被拦截了并通过了拦截器";
        }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21

    5. 项目结构

    在这里插入图片描述

    5. 测试

    1. 带有open http://localhost:8080/api/open/home/info 不拦截
      在这里插入图片描述
    2. 不带open http://localhost:8080/api/user/interceptor 拦截
      在这里插入图片描述
      在这里插入图片描述

    四、拦截校验用户是否登录实战

    1. 加入需要权鉴接口、未登录接口

    a、加入接口

        @GetMapping("/open/unLogin")    // 带 open 放行
        public String getUnauthorized() {
            return "登录失效,请重新登录";
        }
    
    • 1
    • 2
    • 3
    • 4

    b、全部接口

    package com.feng.springboot_interceptor.controller;
    
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    @RestController
    @RequestMapping("/api")
    public class InterceptorController {
    
        @GetMapping("/home/open/info") // 带 open 放行
        public String home() {
            return "欢迎来到首页";
        }
    
        @GetMapping("/user/interceptor")
        public String interceptor() {
            return "我被拦截了并通过了拦截器";
        }
    
        @GetMapping("/open/unLogin")    // 带 open 放行
        public String getUnauthorized() {
            return "登录失效,请重新登录";
        }
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26

    2. 修改拦截器校验逻辑

    package com.feng.springboot_interceptor.interceptor;
    
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.util.StringUtils;
    import org.springframework.web.servlet.HandlerInterceptor;
    import org.springframework.web.servlet.ModelAndView;
    
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    
    
    public class MyInterceptor implements HandlerInterceptor {
    
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
            System.out.println("MyInterceptor....在请求处理之前进行调用(Controller方法调用之前)");
            String requestUrl = request.getRequestURI();
            System.out.println(requestUrl + "被 MyInterceptor 拦截了"); //判断是否携带凭证就可以了
    
            String token = request.getHeader("token");
            if (StringUtils.isEmpty(token)) {
                request.getRequestDispatcher("/api/open/unLogin").forward(request, response);
                return false;
            }
            return true;
        }
    
        @Override
        public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
            System.out.println("MyInterceptor...请求处理之后进行调用,但是在视图被渲染之前(Controller方法调用之后)");
            //HandlerInterceptor.super.postHandle(request, response, handler, modelAndView);
        }
    
        @Override
        public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
            System.out.println("MyInterceptor....在整个请求结束之后被调用,也就是在DispatcherServlet 渲染了对 应的视图之后执行(主要是用于进行资源清理工作)");
            //HandlerInterceptor.super.afterCompletion(request, response, handler, ex);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39

    3. 测试

    a. 首先访问 开放接口

    http://localhost:8080/api/home/open/info
    在这里插入图片描述
    在这里插入图片描述

    b. 访问 需权鉴接口

    1. 带 token
      http://localhost:8080/api/user/interceptor
      在这里插入图片描述

    在这里插入图片描述

    1. 不带 token:http://localhost:8080/api/user/interceptor
      在这里插入图片描述

    在这里插入图片描述

  • 相关阅读:
    Linux查看日志比较实用的几个命令
    基础算法:习题
    javaee springMVC日期类型转换之通过注解的方式
    CSS处理器-Less/Scss
    blender boxCutter插件
    个人练习- Leetcode1664-Ways to Make a Fair Array
    英语单词(6)
    基于labview滑动轴承压力测量软件搭建
    【OAuth2】十八、OIDC的认识应用
    权威敏捷产品经理(CSPO)企业培训
  • 原文地址:https://blog.csdn.net/qq_40036754/article/details/126059642