Springmvc假装读源码:DispatcherServlet类解析

    DispatcherServlet的类图

Springmvc假装读源码:DispatcherServlet类解析_第1张图片

 

       DispatcherServlet的父类和实现的类还是比较复杂的。其中主要的类有HttpServlet、HttpServletBean类。这些类的作用就不过多的讲解了。

        DispatcherServlet类是springmvc最核心的一个类,整个处理过程的的顶层设计都在这里面实现的。而这个类的入口是doService()方法,doDispatch()恰恰的这个方法最为核心的请求处理的过程。所以先来分析doDispatch()方法,在分析之前借用网上分析doDispatch的一张流程图。如下:

Springmvc假装读源码:DispatcherServlet类解析_第2张图片

这张流程图便体现了doDispatch方法对于一个url请求的处理过程。

protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
	HttpServletRequest processedRequest = request;
	HandlerExecutionChain mappedHandler = null;
	boolean multipartRequestParsed = false;

	WebAsyncManager asyncManager = WebAsyncUtils.getAsyncManager(request);

	try {
		ModelAndView mv = null;
		Exception dispatchException = null;

		try {
			//检查请求是否是Multipart(文件上传),如果是文件上传,通过resolveMultipart解析
			processedRequest = checkMultipart(request);
			multipartRequestParsed = (processedRequest != request);

			// 步骤2、请求到处理器(页面控制器)的映射,通过HandlerMapping进行映射 ,解析对应的url 
			mappedHandler = getHandler(processedRequest);
			if (mappedHandler == null || mappedHandler.getHandler() == null) {
				noHandlerFound(processedRequest, response);
				return;
			}

			///步骤3、处理器适配,即将我们的处理器包装成相应的适配器(从而支持多种类型的处理器)
			HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());

			// Process last-modified header, if supported by the handler.
			String method = request.getMethod();
			boolean isGet = "GET".equals(method);
			if (isGet || "HEAD".equals(method)) {
				long lastModified = ha.getLastModified(request, mappedHandler.getHandler());
				if (logger.isDebugEnabled()) {
					logger.debug("Last-Modified value for [" + getRequestUri(request) + "] is: " + lastModified);
				}
				if (new ServletWebRequest(request, response).checkNotModified(lastModified) && isGet) {
					return;
				}
			}

			//拦截器的预处理
			if (!mappedHandler.applyPreHandle(processedRequest, response)) {
				return;
			}

			// 4.5 由适配器执行处理器(调用处理器相应功能处理方法),并且返回ModelAndView
			mv = ha.handle(processedRequest, response, mappedHandler.getHandler());

			
			if (asyncManager.isConcurrentHandlingStarted()) {
				return;
			}
			//view为空的时候 设置request默认的view
			applyDefaultViewName(processedRequest, mv);
			//拦截器的后置处理
			mappedHandler.applyPostHandle(processedRequest, response, mv);
		}
		catch (Exception ex) {
			dispatchException = ex;
		}
		//5,6 处理返回结果。视图渲染、视图解析,异常通知
		processDispatchResult(processedRequest, response, mappedHandler, mv, dispatchException);
	}
	catch (Exception ex) {
		triggerAfterCompletion(processedRequest, response, mappedHandler, ex);
	}
	catch (Error err) {
		triggerAfterCompletionWithError(processedRequest, response, mappedHandler, err);
	}
	finally {
		if (asyncManager.isConcurrentHandlingStarted()) {
			// 判断是否执行异步请求
			if (mappedHandler != null) {
				mappedHandler.applyAfterConcurrentHandlingStarted(processedRequest, response);
			}
		}
		else {
			// 判断是否清楚上传的资源
			if (multipartRequestParsed) {
				cleanupMultipart(processedRequest);
			}
		}
	}
}

doDispatch的整个处理的核心就是只要四句:

  • 根据request查找Handle:  mappedHandler = getHandler(processedRequest)
  • 进而通过这个Handle查找对应的HandlerAdapter适配器:HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler())
  • 通过这个HandlerAdapter执行处理器,产生相应的ModelAndView:mv = ha.handle(processedRequest, response, mappedHandler.getHandler())
  • 对执行的结果进行处理,渲染视图,返回view等:processDispatchResult(processedRequest, response, mappedHandler, mv, dispatchException)。

 

你可能感兴趣的:(springmvc)