Spring MVC 流程源码解析【java进阶笔记十一】

http://localhost:8080/hello 为例,请求分析:

1. 从一个 GET 请求开始,doGet(...) 里只要一个处理请求的方法 processRequest(...)

// FrameworkServlet.java
protected final void doGet(HttpServletRequest request, HttpServletResponse response)
		throws ServletException, IOException {
	processRequest(request, response);
}

2. processRequest(...)

// FrameworkServlet.java
protected final void processRequest(HttpServletRequest request, HttpServletResponse response)
		throws ServletException, IOException {
	// 抛开一些赋值、初始化的代码,看重点:
	try {
		doService(request, response);
	}

3. doService(...)

// DispatcherServlet.java
protected void doService(HttpServletRequest request, HttpServletResponse response) throws Exception {
	// 同样抛开一些赋值、初始化的代码,看重点:
	try {
		doDispatch(request, response);
	}

4. doDispatch(...)

// DispatcherServlet.java
protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
    // 链式处理
    HandlerExecutionChain mappedHandler = null;
	try {
		...
		try {
             // check 是否是上传下载
             processedRequest = checkMultipart(request);
			...
			// Determine handler for the current request.
			mappedHandler = getHandler(processedRequest);
             ...

5. DispatcherServlet.getHandler(...)

// DispatcherServlet.java
protected HandlerExecutionChain getHandler(HttpServletRequest request) throws Exception {
	if (this.handlerMappings != null) {
		for (HandlerMapping mapping : this.handlerMappings) {
			HandlerExecutionChain handler = mapping.getHandler(request);
			if (handler != null) {
				return handler;
			}
		}
	}
	return null;
}

有 5 个 Mapping ,查看 RequestMappingHandlerMapping ,可以查看请求映射的注册:/error、/hello,这里就可以找到对应的处理方法:com.yuyu.demo.controller.DemoController.test()

 6. AbstractHandlerMapping.getHandler(...)

// AbstractHandlerMapping.java

/** 上层调用:
*   DispatcherServlet.getHandler(...){
*		HandlerExecutionChain handler = mapping.getHandler(request);
*	}
**/

public final HandlerExecutionChain getHandler(HttpServletRequest request) throws Exception {
	Object handler = getHandlerInternal(request);
	...
}

 7. RequestMappingInfoHandlerMapping.getHandlerInternal(...)

// RequestMappingInfoHandlerMapping.java

/** 上层调用:
*   AbstractHandlerMapping.getHandler(...){
*		Object handler = getHandlerInternal(request);
*	}
**/

protected HandlerMethod getHandlerInternal(HttpServletRequest request) throws Exception {
    ...
	try {
		return super.getHandlerInternal(request);
	}
    ...
}

8. AbstractHandlerMethodMapping.getHandlerInternal(...)

// AbstractHandlerMethodMapping.java

/** 上层调用:
*   RequestMappingInfoHandlerMapping.getHandlerInternal(...){
*		return super.getHandlerInternal(request);
*	}
**/

protected HandlerMethod getHandlerInternal(HttpServletRequest request) throws Exception {
	String lookupPath = initLookupPath(request);
	...
}

9. AbstractHandlerMethodMapping.initLookupPath(...)

// AbstractHandlerMethodMapping.java
protected String initLookupPath(HttpServletRequest request) {
	...
	else {
		return getUrlPathHelper().resolveAndCacheLookupPath(request);
	}
}

10. UrlPathHelper.class -> resolveAndCacheLookupPath(...)

// UrlPathHelper.class
public String resolveAndCacheLookupPath(HttpServletRequest request) {
      String lookupPath = this.getLookupPathForRequest(request);
      ...
      return lookupPath;
  }

11. UrlPathHelper.class -> getLookupPathForRequest(...)

// UrlPathHelper.class
public String getLookupPathForRequest(HttpServletRequest request) {
      String pathWithinApp = this.getPathWithinApplication(request);
      ...
  }

得到查找路径 /hello,然后返回 10.resolveAndCacheLookupPath(...),再返回 9.resolveAndCacheLookupPath(...),然后回到 8.initLookupPath(...)

回到 8. AbstractHandlerMethodMapping.getHandlerInternal(...)

// AbstractHandlerMethodMapping.java

protected HandlerMethod getHandlerInternal(HttpServletRequest request) throws Exception {
	String lookupPath = initLookupPath(request);
    // 加锁
	this.mappingRegistry.acquireReadLock();
	try {
		HandlerMethod handlerMethod = lookupHandlerMethod(lookupPath, request);
		return (handlerMethod != null ? handlerMethod.createWithResolvedBean() : null);
	}
	finally {
        // 解锁
		this.mappingRegistry.releaseReadLock();
	}
}

12. AbstractHandlerMethodMapping.lookupHandlerMethod(...)

将通过 9/10/11 返回来的路径,用来查找到对应的方法

// AbstractHandlerMethodMapping.java

protected HandlerMethod lookupHandlerMethod(String lookupPath, HttpServletRequest request) throws Exception {
	List<Match> matches = new ArrayList<>();
    // 通过 路径 从映射注册器里找到对应的映射
	List<T> directPathMatches = this.mappingRegistry.getMappingsByDirectPath(lookupPath);
	if (directPathMatches != null) {
		addMatchingMappings(directPathMatches, matches, request);
	}
	...
         // 返回找到的最匹配的 处理方法
		return bestMatch.getHandlerMethod();
	}
	...
}

将找到的方法返回到 8. AbstractHandlerMethodMapping.getHandlerInternal(...),再返回到 7.RequestMappingInfoHandlerMapping.getHandlerInternal(...),最后返回到 6.getHandler(...)

回到 6. AbstractHandlerMapping.getHandler(...)

// AbstractHandlerMapping.java

public final HandlerExecutionChain getHandler(HttpServletRequest request) throws Exception {
	Object handler = getHandlerInternal(request);
	...
	HandlerExecutionChain executionChain = getHandlerExecutionChain(handler, request);
	...
	return executionChain;     
}

将找到的方法和链式处理封装好后,返回到 5.DispatcherServlet.getHandler(...),再返回到 4.DispatcherServlet.doDispatch(...)

回到 4. DispatcherServlet.doDispatch(...)

// DispatcherServlet.java
protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
    // 链式处理
    HandlerExecutionChain mappedHandler = null;
	try {
		...
		try {
             // check 是否是上传下载
             processedRequest = checkMultipart(request);
			...
			// Determine handler for the current request.
			mappedHandler = getHandler(processedRequest);
             ...
             // Determine handler adapter for the current request.
			HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());
            ...

13. DispatcherServlet.getHandlerAdapter(...)

protected HandlerAdapter getHandlerAdapter(Object handler) throws ServletException {
	if (this.handlerAdapters != null) {
		for (HandlerAdapter adapter : this.handlerAdapters) {
			if (adapter.supports(handler)) {
				return adapter;
	...
}

至此,分别通过 ① mappedHandler = getHandler(...) 获得了 mappedHandler ;② HandlerAdapter ha = getHandlerAdapter(...) 获得了 HandlerAdapter

回到 4. DispatcherServlet.doDispatch(...)

// DispatcherServlet.java
protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
    // 链式处理
    HandlerExecutionChain mappedHandler = null;
	try {
		...
		try {
             // check 是否是上传下载
             processedRequest = checkMultipart(request);
			...
			// Determine handler for the current request.
			mappedHandler = getHandler(processedRequest);
             ...
             // Determine handler adapter for the current request.
			HandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());
             ...
             // Actually invoke the handler.
			mv = ha.handle(processedRequest, response, mappedHandler.getHandler());
             ...

14. AbstractHandlerMethodAdapter.hadle(...)

上面映射等准备好了,下面进行处理

// AbstractHandlerMethodAdapter.java

/** 上层调用:
*   DispatcherServlet.doDispatch(...){
*		// Actually invoke the handler.
		mv = ha.handle(processedRequest, response, mappedHandler.getHandler());
*	}
**/

public final ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler)
		throws Exception {
	return handleInternal(request, response, (HandlerMethod) handler);
}

15. RequestMappingHandleAdapter.handleInternal(...)

// RequestMappingHandleAdapter.java

/** 上层调用:
*   AbstractHandlerMethodAdapter.handle(...){
*		return handleInternal(request, response, (HandlerMethod) handler);
*	}
**/

protected ModelAndView handleInternal(HttpServletRequest request,
			HttpServletResponse response, HandlerMethod handlerMethod) throws Exception {
	ModelAndView mav;
	...
	else {
		// No synchronization on session demanded at all...
		mav = invokeHandlerMethod(request, response, handlerMethod);
	}
	...
	return mav;
}

16. RequestMappingHandleAdapter.invokeHandlerMethod(...)

// RequestMappingHandleAdapter.java

/** 上层调用:
*   RequestMappingHandleAdapter.handleInternal(...){
*		mav = invokeHandlerMethod(request, response, handlerMethod);
*	}
**/

protected ModelAndView invokeHandlerMethod(HttpServletRequest request,
			HttpServletResponse response, HandlerMethod handlerMethod) throws Exception {
	...
	try {
		...
		ServletInvocableHandlerMethod invocableMethod = createInvocableHandlerMethod(handlerMethod);
		if (this.argumentResolvers != null) {
			invocableMethod.setHandlerMethodArgumentResolvers(this.argumentResolvers);
		}
		if (this.returnValueHandlers != null) {
			invocableMethod.setHandlerMethodReturnValueHandlers(this.returnValueHandlers);
		}
		...
}

27 个参数解析器:

public interface HandlerMethodArgumentResolver {
  //判断 parameter 是不是 xxArgumentResolver 解析器可以解析
  boolean supportsParameter(MethodParameter parameter);
    
  // 进⾏解析!解析的主要逻辑
  @Nullable
  Object resolveArgument(MethodParameter parameter, @Nullable ModelAndViewContainer mavContainer,NativeWebRequest webRequest, @Nullable WebDataBinderFactory binderFactory) throws Exception;}

 15 个结果处理器:

public interface HandlerMethodReturnValueHandler {
 //判断 xxMethodReturnValueHandler 结果处理器是否能处理这个returnType
 boolean supportsReturnType(MethodParameter returnType);
    
 // 进⾏处理
 void handleReturnValue(@Nullable Object returnValue, MethodParameter returnType,ModelAndViewContainer mavContainer, NativeWebRequest webRequest) throws Exception;}

 回到 16. RequestMappingHandleAdapter.invokeHandlerMethod(...)

// RequestMappingHandleAdapter.java

protected ModelAndView invokeHandlerMethod(HttpServletRequest request,
			HttpServletResponse response, HandlerMethod handlerMethod) throws Exception {
	...
	try {
		...
		ServletInvocableHandlerMethod invocableMethod = createInvocableHandlerMethod(handlerMethod);
		if (this.argumentResolvers != null) {
			invocableMethod.setHandlerMethodArgumentResolvers(this.argumentResolvers);
		}
		if (this.returnValueHandlers != null) {
			invocableMethod.setHandlerMethodReturnValueHandlers(this.returnValueHandlers);
		}
		...
         invocableMethod.invokeAndHandle(webRequest, mavContainer);
}

17. ServletInvocableHandlerMethod.invokeAndHandle(...)

上面映射、参数、结果什么都准备好了,下面进行最后的处理

// ServletInvocableHandlerMethod.java

/** 上层调用:
*   RequestMappingHandleAdapter.invokeHandlerMethod(...){
*		invocableMethod.invokeAndHandle(webRequest, mavContainer);
*	}
**/

public void invokeAndHandle(ServletWebRequest webRequest, ModelAndViewContainer mavContainer,
		Object... providedArgs) throws Exception {
	Object returnValue = invokeForRequest(webRequest, mavContainer, providedArgs);
	...

18. InvocalbeHandlerMethod.class -> invokeForRequest(...)

// InvocalbeHandlerMethod.class   

/** 上层调用:
*   ServletInvocableHandlerMethod.invokeAndHandle(...){
*		Object returnValue = invokeForRequest(webRequest, mavContainer, providedArgs);
*	}
**/

public Object invokeForRequest(NativeWebRequest request, @Nullable ModelAndViewContainer mavContainer, Object... providedArgs) throws Exception {
    // 获得⽅法的参数
    Object[] args = this.getMethodArgumentValues(request, mavContainer, providedArgs);
    ...
      
    // 真正的⽅法调⽤了
    return this.doInvoke(args);
  }

19. InvocalbeHandlerMethod.class -> doInvoke(...)

// InvocalbeHandlerMethod.class   

/** 上层调用:
*   InvocalbeHandlerMethod.invokeForRequest(...){
*		return this.doInvoke(args);
*	}
**/

protected Object doInvoke(Object... args) throws Exception {
    // 获得被桥接的⽅法
	Method method = getBridgedMethod();
    // 开打访问权限
	ReflectionUtils.makeAccessible(method);
	try {
         ...
         // 通过反射,调⽤ Controller 中响应的⽅法
		return method.invoke(getBean(), args);
	}
	catch (IllegalArgumentException ex) {
	...
	}
	catch (InvocationTargetException ex) {
		...
	}
}

猜你喜欢

转载自blog.csdn.net/qq_42183414/article/details/124868195