springMVC 拦截器的原理

           **springMVC 拦截器的原理**
  今天突然有些时间,打算把拦截器这块捋一下源码,以下就是我总结的拦截器的核心方法。当然,整个实现是离不开Spring Ioc 以及Aop 的,有兴趣的可以看看Spring的整体设计理念以及方法,阅读源码会更加轻松。
  我们可以通过继承HandlerInterceptorAdapter类或者实现  HandlerInterceptor接口来添加相应的拦截器。推荐使用继承HandlerInterceptorAdapter方式来实现拦截器的功能,原因是不用实现多余的方法。
  拦截器的核心类DispatcherServlet,核心方法是org.springframework.web.servlet.DispatcherServlet.doDispatch(HttpServletRequest, HttpServletResponse);
  其中doDispatch 方法有以下的关键核心方法:
	mappedHandler = getHandler(processedRequest);//获取请求的hanlder;
HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());//获取所对应的适配器的对象。
mappedHandler.applyPreHandle(processedRequest, response);//判断是否存在拦截;
	boolean applyPreHandle(HttpServletRequest request, HttpServletResponse response) throws Exception {
		HandlerInterceptor[] interceptors = getInterceptors();
		if (!ObjectUtils.isEmpty(interceptors)) {
			for (int i = 0; i < interceptors.length; i++) {
				HandlerInterceptor interceptor = interceptors[i];
				if (!interceptor.preHandle(request, response, this.handler)) {
					triggerAfterCompletion(request, response, null);
					return false;
				}
				this.interceptorIndex = i;
			}
		}
		return true;
	}
 说明:这是拦截的核心所在,在执行handler前执行,是用来是否拦截的中心所在,只要一个为false,整个就不通过。这是拦截器调用如果存在多个拦截器,依次从前往后执行,其中一个返回false,那么整个拦截器链就直接返回,但是triggerAfterCompletion 依就会执行全部的拦截器链,并且是倒序执行。
	void applyPostHandle(HttpServletRequest request, HttpServletResponse response, ModelAndView mv) throws Exception {
		HandlerInterceptor[] interceptors = getInterceptors();
		if (!ObjectUtils.isEmpty(interceptors)) {
			for (int i = interceptors.length - 1; i >= 0; i--) {
				HandlerInterceptor interceptor = interceptors[i];
				interceptor.postHandle(request, response, this.handler, mv);
			}
		}
	}
说明:这个方法是在返回modelAndView时会调用的,通过代码可以看出,存在多个拦截器时会倒序执行,前提是mappedHandler.applyPreHandle(processedRequest, response);这个方法不能为false;
	void triggerAfterCompletion(HttpServletRequest request, HttpServletResponse response, Exception ex)
			throws Exception {

		HandlerInterceptor[] interceptors = getInterceptors();
		if (!ObjectUtils.isEmpty(interceptors)) {
			for (int i = this.interceptorIndex; i >= 0; i--) {
				HandlerInterceptor interceptor = interceptors[i];
				try {
					interceptor.afterCompletion(request, response, this.handler, ex);
				}
				catch (Throwable ex2) {
					logger.error("HandlerInterceptor.afterCompletion threw exception", ex2);
				}
			}
		}
	}
 说明:这个方法你会发现最后的方法都会走他,不管是前面applyPreHandle 方法结果如何,还是正常走下去,或者有异常,都会走这个方法,不难发现,这个方法就是为了方便记录日这或者排查问题用的。
 以上就是SpringMvc 拦截器的核心所在,具体怎么实现大家可以网上索罗一番。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值