【SpringBoot6】HandlerInterceptor拦截器的使用 ——基础

人生之路不会是一帆风顺的,我们会遇上顺境,也会遇上逆境,在所有成功路上折磨你的,背后都隐藏着激励你奋发向上的动机,人生没有如果,只有后果与结果,成熟,就是用微笑来面对一切小事。

导读:本篇文章讲解 【SpringBoot6】HandlerInterceptor拦截器的使用 ——基础,希望对大家有帮助,欢迎收藏,转发!站点地址:www.bmabk.com,来源:原文

HandlerInterceptor简介

拦截器大家都不陌生,最常用的登录拦截、或是权限校验、或是防重复提交、或是根据业务像12306去校验购票时间,总之可以去做很多的事情。
这里来介绍HandlerInterceptor的使用,从基本的使用、到自定义注解、最后到读取body中的流解决无法多次读取的问题。

1、定义实现类

定义一个Interceptor 非常简单方式也有几种,我这里简单列举两种
1、类要实现Spring 的HandlerInterceptor 接口
2、类继承实现了HandlerInterceptor 接口的类,例如 已经提供的实现了HandlerInterceptor 接口的抽象类HandlerInterceptorAdapter
 

这里用的是第二种方法继承HandlerInterceptorAdapter

2、HandlerInterceptor方法介绍


	boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
			throws Exception;

	void postHandle(
			HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
			throws Exception;

	void afterCompletion(
			HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
			throws Exception;

preHandle:在业务处理器处理请求之前被调用。预处理,可以进行编码、安全控制、权限校验等处理;
postHandle:在业务处理器处理请求执行完成后,生成视图之前执行。后处理(调用了Service并返回ModelAndView,但未进行页面渲染),有机会修改ModelAndView (这个博主就基本不怎么用了);
afterCompletion:在DispatcherServlet完全处理完请求后被调用,可用于清理资源等。返回处理(已经渲染了页面);
接下来让我们来实现一个登陆 and 访问权限校验的拦截器吧

拦截器实现

新建TestFilter

package com.xxx.core.filter;

import com.xxx.common.exception.FastRuntimeException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;


public class TestFilter extends HandlerInterceptorAdapter {
	private final Logger logger = LoggerFactory.getLogger(TestFilter.class);
	@Override
	public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
			throws Exception {
		logger.info("request请求地址path[{}] uri[{}]", request.getServletPath(),request.getRequestURI());
		//request.getHeader(String) 从请求头中获取数据
		//从请求头中获取用户token(登陆凭证根据业务而定)
		Long userId= getUserId(request.getHeader("H-User-Token"));
		if (userId != null && checkAuth(userId,request.getRequestURI())){
			return true;
		}
		//这里的异常是我自定义的异常,系统抛出异常后框架捕获异常然后转为统一的格式返回给前端, 其实这里也可以返回false
		throw new FastRuntimeException(20001,"No access");
	}

	/**
	 * 根据token获取用户ID
	 * @param userToken
	 * @return
	 */
	private Long getUserId(String userToken){
		Long userId = null;
		return userId;
	}

	/**
	 * 校验用户访问权限
	 * @param userId
	 * @param requestURI
	 * @return
	 */
	private boolean checkAuth(Long userId,String requestURI){
		return true;
	}

	@Override
	public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
						   ModelAndView modelAndView) throws Exception {}

	@Override
	public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
			throws Exception {}
}

新建WebAppConfigurer 实现WebMvcConfigurer接口

 其实以前都是继承WebMvcConfigurerAdapter类 不过springBoot2.0以上 WebMvcConfigurerAdapter 方法过时,有两种替代方案:
1、继承WebMvcConfigurationSupport
2、实现WebMvcConfigurer
但是继承WebMvcConfigurationSupport会让Spring-boot对mvc的自动配置失效。根据项目情况选择。现在大多数项目是前后端分离,并没有对静态资源有自动配置的需求所以继承WebMvcConfigurationSupport也未尝不可。

 

@Configuration
public class WebAppConfigurer implements WebMvcConfigurer {

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        // 可添加多个
        registry.addInterceptor(new TestFilter()).addPathPatterns(“/**”);
    }

    ….
}
 

其实下面还有很多方法我这里就省略了,过滤器可以添加多个,可以指定Path,这里的/**是对所有的请求都做拦截。

是否感觉配置这个地址是不特别方便?下一篇博客介绍2.0版本引入注解来协助完成一系列的拦截任务。 

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

文章由极客之家整理,本文链接:https://www.bmabk.com/index.php/post/124446.html

(0)
飞熊的头像飞熊bm

相关推荐

发表回复

登录后才能评论
极客之家——专业性很强的中文编程技术网站,欢迎收藏到浏览器,订阅我们!