【阅读SpringMVC源码】手把手带你debug验证SpringMVC执行流程
✿ 阅读源码思路:
先跳过非重点,深入每个方法,进入的时候可以把整个可以理一下方法的执行步骤理一下,也可以,理到某一步,继续深入,回来后,接着理清除下面的步骤。
✿ 阅读本文的准备工作,预习一下SpringMVC的执行流程
■ 解释一下,为什么标题是验证SpringMVC执行流程:
不知道小伙伴有没有做过物理实验的验证实验,道理是一样的,举个高中生都做过的物理实验吧----自由落体实验,这个实验是通过小钢球做抛物运动,验证重力加速度的g值是9.8。对于本文,咱的做法是通过调试来验证SpringMVC的执行流程是:
1、前端控制器接收到客户端的请求后,通过处理器映射器handlerMappings,根据路径urlPath去匹配选择处理器handler,最终返回一个处理器执行链对象HandlerExcutionChain。
2、前端控制器通过处理器适配器,调用处理器的方法,然后处理器执行后返回模型视图对象给处理器适配器,适配器再将模型视图对象返回给前端对象。
3、前端控制器通过视图解析器,将模型视图进行解析,然后将模型数据填充到View,并渲染到视图,然后返回响应。
SpirngMVC执行流程图(图片来源于叩丁狼)

一、执行流程前的次要源码
● 开始debug的时候,对HttpMethod感到好奇,点进去查看一下HttpMethod究竟是何物?

HttpMethod 是请求方法的枚举类,结合咱浏览器地址栏的参数是直接输入,
可以知道咱的HttpMethod的值是Get

果然咱的HttpMethod的值是Get,所以下一步会执行super.service(request, response);
ctr进入该方法看一下,究竟是何物,发现按ctr没有反应【
解决:重新打开该类的文件】

进入super.service(request, response);内部一探究竟:
发现这个service方法做的是请求分发操作,结合咱的请求方法是GET,所以下一步咱是到doGet方法去一探究竟~

再进入processRequest方法~

进入发现重点是doService(request, response);那咱就进入该方法内部一探究竟吧~

进入发现重点是doDispatch(request, response);那咱就进入该方法内部一探究竟吧~

二、真正的springMVC执行流程的源码分析
1、验证:前端控制器接收到客户端的请求后,通过处理器映射器handlerMappings,根据路径urlPath去匹配选择处理器handler,最终返回一个处理器执行链对象HandlerExcutionChain。
● 获取处理器映射器返回处理器执行链对象,getHandler(processedRequest);方法
【咱提前了解到的springMVC的执行过程:前端控制器接收请求,通过处理器映射器寻找处理器,返回一个处理器执行链对象】。

● 发现了 this.handlerMappings 处理器映射器-观察它的值为:
[org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping@40851021]【咱提前了解到的springMVC的执行过程:前端控制器接收请求,通过处理器映射器寻找处理器,返回一个处理器执行链对象】。

● 进入 mapping.getHandler(request); 方法内部:

● 进入返回处理器对象的getHandlerInternal方法内部:Object handler = lookupHandler(lookupPath, request);
【咱提前了解到的springMVC的执行过程:前端控制器接收请求,通过处理器映射器依据路径进行匹配来寻找处理器,返回一个处理器执行链对象】。

● 进入lookupHandler方法内部:验证了通过处理器映射器依据路径进行匹配来寻找处理器。还观察到urlPath的值,正是咱配置的处理器的路径


---- 按照阅读源码观察步骤,到这一步,你已经理清楚了,可以调试回去,回去到:

......
✿ 至此,验证了SpringMVC的执行流程:前端控制器接收到客户端的请求后,通过处理器映射器handlerMappings,根据路径urlPath去匹配选择处理器handler,最终返回一个处理器执行链对象HandlerExcutionChain。
2、验证:前端控制器通过处理器适配器,调用处理器的方法,然后处理器执行后返回模型视图对象给处理器适配器,适配器再将模型视图对象返回给前端对象.
● 获取处理器适配器对象HandlerAdapter

● 进入getHandlerAdapter获取处理器适配器方法内部:
看到了this.handlerAdapters 处理器映射器-观察它的值为:
[org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter@60038152]

- 非重点:判断与“被修改”相关的
- 非重点:前置拦截器相关的

● 进入ha.handle方法内部观察:

看到了(Controller) handler-观察它的值为:
com.shan.hello.HelloController@591b274


`执行完((Controller) handler).handleRequest(request, response);即调用咱自己书写的处理器类的方法~``
返回,
继续观察,发现ModelAndView对象,观察它的值:
ModelAndView [view="/WEB-INF/views/welcome.jsp"; model={msg=你好,easyMVC}]

这个深入进去,设置视图名称

非重点:后置拦截器

继续观察---观察到:处理分发的结果,深入进去观察:

非重点:错误异常相关的
重点:渲染方法

。。。。。。跟视图有关的重点。。。。。
至此,验证了SpringMVC的执行流程:前端控制器通过处理器适配器HandlerAdapter,调用处理器HelloController的方法,然后处理器执行后返回模型视图对象ModelAndView给处理器适配器,适配器再将模型视图对象返回给前端控制器.
3、验证:前端控制器通过视图解析器,将模型视图进行解析,然后将模型数据填充到View,并渲染到视图,然后返回响应.
- 非重点:国际化
- 非重点:视图名称

● 重点:渲染视图


- 观察到返回一个模型对象,根据方法调用的先后顺序,先调用了view.render(mv.getModelInternal(), request, response);的mv.getModelInternal()方法,需要重新深入一次


● 在渲染视图render方法内部,观察到mergedModel,观察它的值:
{msg=你好,easyMVC}

- 非重点:预响应
● 重点:renderMergedOutputModel【符合咱提前了解的SpringMVC的执行流程中渲染视图的数据】

● 深入,发现是将共享数据设置到请求中去

● 接着往下,跳过非重点,来到请求转发

至此,验证:前端控制器通过视图解析器,将模型视图进行解析,然后将模型数据填充到View,并渲染到视图,然后返回响应.
【阅读SpringMVC源码】手把手带你debug验证SpringMVC执行流程的更多相关文章
- SpringMVC源码分析(3)DispatcherServlet的请求处理流程
<springmvc源码分析(2)dispatcherservlet的初始化>初始化DispatcherServlet的多个组件. 本文继续分析DispatcherServlet解析请求的 ...
- SpringMVC源码剖析(三)- DispatcherServlet的初始化流程
在我们第一次学Servlet编程,学Java Web的时候,还没有那么多框架.我们开发一个简单的功能要做的事情很简单,就是继承HttpServlet,根据需要重写一下doGet,doPost方法,跳转 ...
- springmvc 源码分析(二)-- DiapartcherServlet核心调用流程分析
测试环境搭建: 本次搭建是基于springboot来实现的,代码在码云的链接:https://gitee.com/yangxioahui/thymeleaf.git 项目结构代码如下: 一: cont ...
- spark 源码分析之二十一 -- Task的执行流程
引言 在上两篇文章 spark 源码分析之十九 -- DAG的生成和Stage的划分 和 spark 源码分析之二十 -- Stage的提交 中剖析了Spark的DAG的生成,Stage的划分以及St ...
- SpringMVC源码分析系列
说到java的mvc框架,struts2和springmvc想必大家都知道,struts2的设计基本上完全脱离了Servlet容器,而springmvc是依托着Servlet容器元素来设计的,同时sp ...
- SpringMVC源码
SpringMVC源码分析系列 说到java的mvc框架,struts2和springmvc想必大家都知道,struts2的设计基本上完全脱离了Servlet容器,而springmvc是依托着Serv ...
- 【Spring专场】「IOC容器」不看源码就带你认识核心流程以及运作原理
这是史上最全面的Spring的核心流程以及运作原理的分析指南 [Spring核心专题]「IOC容器篇」不看繁琐的源码就带你浏览Spring的核心流程以及运作原理 [Spring核心专题]「AOP容器篇 ...
- SpringMVC源码情操陶冶-FreeMarker之web配置
前言:本文不讲解FreeMarkerView视图的相关配置,其配置基本由FreeMarkerViewResolver实现,具体可参考>>>SpringMVC源码情操陶冶-ViewRe ...
- 手把手带你阅读Mybatis源码(三)缓存篇
前言 大家好,这一篇文章是MyBatis系列的最后一篇文章,前面两篇文章:手把手带你阅读Mybatis源码(一)构造篇 和 手把手带你阅读Mybatis源码(二)执行篇,主要说明了MyBatis是如何 ...
随机推荐
- JVM内存模型(五)
一.JVM内存模型 1.1.与运行时数据区 前面讲过了运行时数据区那接下来我们聊下内存模型,JVM的内存模型指的是方法区和堆:在很多情况下网上讲解会把内存模型和运行时数据区认为是一个东西,这是 ...
- 从服务之间的调用来看 我们为什么需要Dapr
Dapr 相关的文章我已经写了20多篇了[1] . 当向其他人推荐Dapr 的时候,需要回答的一个问题就是: Dapr 似乎并不是特别令人印象深刻.它提供了一组"构建块",解决了与 ...
- react-motion 动画案例介绍
第一个案例:Motion组件 import React,{Component} from 'react'; import {Motion,spring,presets} from 'react-mot ...
- 使用Docker快速搭建Halo个人博客到阿里云服务器上[附加主题和使用域名访问]
一.前言 小编买了一个服务器也是一直想整个网站,一直在摸索,看了能够快速搭建博客系统的教程.总结了有以下几种方式,大家按照自己喜欢的去搭建: halo wordpress hexo vuepress ...
- BIMFACE 二次开发 SDK 之歌
<BIMFACE SDK 之歌>讲述了作者与 BIMFACE 从相识.相知.相爱.相守的艳遇之爱唯美故事 我是一个小小的程序员 穿行在人来人往的IT行业之间 编程工作与建筑信息化相关 ...
- js-小知识点
强类型定义语言和弱类型定义语言1)强类型定义语言: 强制数据类型定义的语言.也就是说,一旦一个变量被指定了某个数据类型,如果不经过强制转换,那么它就永远是这个数据类型了.举个例子:如果你定义了一个整型 ...
- 微信h5下拉隐藏网页,还有取消页面滑动
需求: 网页下拉太丑了,如下 度娘了一下, 发现一篇相关文档 基本解决了问题 https://juejin.cn/post/6844903940190896135#heading-2 加入如下代码即可 ...
- JSP中的请求转发与重定向
在说请求转发和重定向之前,得了解下JSP九大内置对象中的response和request response:将服务器端数据发送到客户端,可通过在客户端浏览器中显示,用户浏览页面的重定向以及在客户端创建 ...
- PHP中的一些常用函数收集
<?php //===============================时间日期=============================== //y返回年最后两位,Y年四位数,m月份数字 ...
- MyBatis加强(1)~缓存机制(一级缓存、二级缓存、第三方缓存技术redis、ehcache)
一.缓存机制 使用缓存可以使应用更快地获取数据,避免频繁的数据库交互操作,尤其是在查询越多,缓存命中率越高 的情况下,缓存的作用就越明显. 1.缓存原理:Map ■ 查询时,先从缓存区查询:找到,返回 ...