以 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) {
...
}
}