栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

springmvc执行流程-拦截器

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

springmvc执行流程-拦截器

springmvc的拦截器 springmvc执行流程

● 客户端(浏览器)发送请求,直接请求到 DispatcherServlet .
● mvc中是否存在对应的映射,存在交给HandlerMapping返回HandlerExecutionChain对象
● 不存在查看是否配置了配置了,将请求交给tomcat,由tomcat按照静态资源进行查找
● 如果没有配置,直接返回404
● 根据HandlerExecutionChain对象获取请求拦截器的preHandle方法来得到HandleAdapter实现类对象.
● 由适配器对象来执行目标方法并返回ModelAndView对象,适配其 将其返回给DispatcherServlet
● DispatcherServlet委托给视图解析器从ModelAndView对象中解析出View对象
● 由DispatcheServlet委托给具体视图,由视图进行渲染视图的操作,并响应给客户端.
● 最终DispatcherServlet调用拦截器的进行处理

  • springmvc可以使用拦截器对请求进行拦截处理,用户可以自定义拦截器来实现特定的功能,自定义的拦截器必须实现HandlerInterceptor接口或者可以继承HandlerInterceptorAdapter(对HandlerInterceptor使用接口适配器)后的抽象类,对接口的方法做了一个空实现.继承该类可以有选择的实现这三个抽象方法.
HandlerInterceptor

package org.springframework.web.servlet;

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

import org.springframework.lang.Nullable;
import org.springframework.web.method.HandlerMethod;


public interface HandlerInterceptor {

		default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
			throws Exception {
		// 默认为true,即默认执行postHandler
		return true;
	}
	default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
			@Nullable ModelAndView modelAndView) throws Exception {
	}

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

}

  • preHandler:这个方法在业务处理器处理请求之前被调用,在该方法中用户请求的request进行处理,如果程序员决定该拦截器对请求进行拦截处理后还要调用其他的拦截器或是业务处理器取进行处理,返回true,否则返回false.
  • postHandler:在业务处理器处理完请求后,但是DispatcherServlet向客户端返回响应数据前被调用,在该方法中对用户请求的request进行处理.
  • afterCompletion:这个方法在DispatcherServlet完成处理请求后被调用,一般在该方法中进行一些资源处理操作.

DispatcherServlet源码
  • 在DispatcherServlet中的doDispatcher方法中




单个拦截器执行顺序
  • 通过preHandler方法决定是否执行目标方法及后置拦截器
  • 返回true就执行目标方法及后置处理器最后执行afterCompletion
  • 否则直接执行afterCompletion方法

image.png

多个拦截器执行顺序
  • 按照执行preHandler的倒叙执行顺序执行postHandler和afterCompletion.

  • 当我们发送请求到DispatcherServlet,会根据请求映射器,返回一个执行器链对象,该对象中包含了若干个请求拦截器对象(RequestIntecept数组类型)对象.
boolean applyPreHandle(HttpServletRequest request, HttpServletResponse response) throws Exception {
    // 获取请求拦截器
        HandlerInterceptor[] interceptors = this.getInterceptors();
        if (!ObjectUtils.isEmpty(interceptors)) {
            // 遍历,记录preHandler返回true的下标个数
            for(int i = 0; i < interceptors.length; this.interceptorIndex = i++) {
                HandlerInterceptor interceptor = interceptors[i];
                if (!interceptor.preHandle(request, response, this.handler)) {
                    // 执行AfterCompletion
                    this.triggerAfterCompletion(request, response, (Exception)null);
                    return false;
                }
            }
        }

        return true;
    }
  • 出现错误后不执行拦截器的postHandler和目标方法.
void triggerAfterCompletion(HttpServletRequest request, HttpServletResponse response, @Nullable Exception ex) throws Exception {
        HandlerInterceptor[] interceptors = this.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 var8) {
                    logger.error("HandlerInterceptor.afterCompletion threw exception", var8);
                }
            }
        }

小结
  • preHandler执行,afterCompletion一定执行.
  • preHandler返回false,该拦截器的postHandler的目标方法一定不执行
转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/274628.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号