SpringMVC组件原理剖析

这篇具有很好参考价值的文章主要介绍了SpringMVC组件原理剖析。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

SpringMVC组件原理剖析

主要剖析DispatcherServlet(前端控制器 )初始化的过程,还有DispatcherServlet执行主流程

一、 前端控制器初始化

DispatcherServlet初始化做了两件事情

  • 获得了一个 SpringMVC 的 ApplicationContext容器
  • 注册了 SpringMVC的 九大组件

SpringMVC组件原理剖析

1.1 初始化SpringMVC容器

前端控制器DispatcherServlet是SpringMVC的入口,也是SpringMVC的大脑,主流程的工作都是在此完成的

DispatcherServlet 本质是个Servlet,当配置了 load-on-startup 时,会在服务器启动时就执行创建和执行初始化init方法,每次请求都会执行service方法

找一下init方法,发现DispatcherServlet类中没有,就去找他爹FrameworkServlet类,爹也没有,就一直找,直到HttpServletBean类中有一个init方法

找到init方法,看到调用了一个initServletBean方法,点进去看看

SpringMVC组件原理剖析

initServletBean方法如下所示,发现啥也没有,说明是子类实现的,也就是FrameworkServlet类

SpringMVC组件原理剖析

在FrameworkServlet类中找到initServletBean方法,然后发现有下面一条语句,获取web环境下的Spring容器

SpringMVC组件原理剖析

点进去看看,发现创建了一个Spring的容器

SpringMVC组件原理剖析

还是此方法,再往下看,把Spring容器的引用作为参数放入了下面的方法中

传入Spring容器有什么作用?

​ 将Spring容器的引用设置为SpringMVC的一个属性,通过这个地方体现出一个父子容器的关系

SpringMVC组件原理剖析

父子容器有什么作用?

当SpringMVC在获取Bean的时候,首先会从自己的容器中获取,如果自己容器没有的话会使用parent找到父容器,也就是Spring容器,再从里面看看有没有对应的Bean

Spring中能不能获取到SpringMVC中的Bean?

不能,因为SpringMVC是子容器

SpringMVC组件原理剖析

1.2 注册了 SpringMVC的 九大组件

没太屡明白141-SpringMVC框架-组件原理剖析-前端控制器初始化-注册九大组件_哔哩哔哩_bilibili

当我们把SpringMVC容器创建出来后,会执行到下面标红的语句

configureAndRefreshWebApplicationContext,配置和刷新SpringMVC容器

SpringMVC组件原理剖析

继续往下走,如果没有的话就进行创建

SpringMVC组件原理剖析

点进上图中的方法,一直点到下图

发现也有configureAndRefreshWebApplicationContext方法的调用

SpringMVC组件原理剖析

经过上面两个过程,不管是新创建的SpringMVC容器还是只有就有的SpringMVC容器,都会执行configureAndRefreshWebApplicationContext方法




点进方法configureAndRefreshWebApplicationContext

发现此方法中有一个refresh方法

SpringMVC组件原理剖析

点进refresh方法,发现最后调用了一个finishRefresh方法,完成刷新

SpringMVC组件原理剖析

点进去finishRefresh方法看一下,此方法中发布了一个事件

我们设置上这个事件,事件对应的监听都会执行

SpringMVC组件原理剖析




此时再回到FrameworkServlet类

找到下面这个方法,是一个监听器,监听的东西就是泛型ContextRefreshedEvent,也就是我们发布的事件的类型(上图)

这段FrameworkServlet.this.onApplicationEvent(event);代码会执行

为什么会被执行?

在另一个地方会发布事件

SpringMVC组件原理剖析

​ 其中在FrameworkServlet类中有一个监听器就是监听上面的事件的

​ 监听到后这段FrameworkServlet.this.onApplicationEvent(event);代码会执行

SpringMVC组件原理剖析

看一下onApplicationEvent方法,里面有一个onRefresh方法,

SpringMVC组件原理剖析

看一下onRefresh方法,但是内部什么也没写,说明是子类进行实现

SpringMVC组件原理剖析

看一下FrameworkServlet类的子类DispatcherServlet类中的onRefresh方法

SpringMVC组件原理剖析

最后完成注册SpringMVC九大组件

SpringMVC组件原理剖析

1.3 处理器映射器初始化细节

注册了九个组件,我们可以选一个我们比较熟悉的initHandlerMappings进行查看

这一步的操作就是看看Spring容器之中有没有类型是HandlerMapping的组件,如果有的话,matchingBeans参数就不是空了

SpringMVC组件原理剖析

那此时就进不去下面这个if判断了,就不会加载默认配置文件中的组件

SpringMVC组件原理剖析

打断点之后发现,为什么会有四个HandlerMapping类型的参数?

SpringMVC组件原理剖析

我们之前配置了一个注解@EnableWebMVC

SpringMVC组件原理剖析

或者说spring-mvc.xml文件中的

SpringMVC组件原理剖析

MVC注解驱动的作用有很多,会帮我们向SpringMVC中注入一些组件,其中HandlerMapping就是在这个地方注册的

上面这几句话的操作都是@EnableWebMVC注解帮我们完成的

如果我们把@EnableWebMVC注解注释掉调后,matchingBeans参数的大小就是0,最终会加载默认配置文件中的组件,就是下图框起来的

SpringMVC组件原理剖析

四个HandlerMapping类型的组件,我们点开看一个

但是我们只手动配置了一个拦截器,为什么会显示两个呢?

Spring本身提供了两个

SpringMVC组件原理剖析

再看一下MappingRegistery参数

SpringMVC组件原理剖析

随便点进去一个看看

SpringMVC组件原理剖析

二、前端控制器执行主流程

当服务器启动时,DispatcherServlet 会执行初始化操作,接下来,每次访问都会执行service方法,我们先宏观的看一下执行流程,在去研究源码和组件执行细节

SpringMVC组件原理剖析

2.1 定位doDispatcher方法

在DispatcherServlet类中找service方法,但是没有,那就找他爹FrameworkServlet类,发现有Service方法,但是此方法不是最原生的,最原生的方法是ServletRequest参数

SpringMVC组件原理剖析

再找FrameworkServlet类的爹HttpServletBean类,但是没有Service方法

再找HttpServlet类,发现有Service方法,并且是原生的(参数前面没有http)

SpringMVC组件原理剖析

上图中的service方法又调用了下面的service方法(这个service进行重载了)

内部根据请求方式,看看是调用dopost还是doGet

SpringMVC组件原理剖析

我们可以看一下doPost方法,但是此方法左边有一个小标志,说明已经被子类覆盖了

SpringMVC组件原理剖析

点一下小标志,然后进入到FrameworkServlet类中,并看到doPost方法

SpringMVC组件原理剖析

doPost方法中又调用了一个processRequest方法

SpringMVC组件原理剖析

processRequest方法中又调用了doService方法,但是我们发现doService是一个抽象方法,我们需要找到对应的实现

SpringMVC组件原理剖析

看一下doService抽象方法的具体实现,就到了DispatcherServlet类

doService方法中调用了另外一个方法doDispatch

SpringMVC组件原理剖析

看一下doDispatch方法,最核心的主流程就在这里

2.2 验证HandlerExecutionChain

从DispatcherServlet类中的doDispatch开始找

此方法中有一个参数HandlerExecutionChain,这个参数内部包括Interceptor、目标对象

此方法中 this.getHandler(processedRequest)的调用对HandlerExecutionChain的参数mappedHandler进行初始化

SpringMVC组件原理剖析

我们看一下getHandler方法是什么,如下所示

如果参数handlerMappings不是空,就对其进行循环

SpringMVC组件原理剖析

那handlerMappings参数是什么呢?点进去看看

发现就是最终装HandlerMapping的集合

HandlerMapping的的填充在前面1.3进行讲解了

SpringMVC组件原理剖析

再回到getHandler方法,其中遍历集合的时候又调用了mapping.getHandler(request)方法

SpringMVC组件原理剖析

我们再看一下mapping.getHandler方法是干嘛的

SpringMVC组件原理剖析

找对应的实现,选择第一个

SpringMVC组件原理剖析

然后再这个类中对应的实现又调用了getHandlerExecutionChain方法

SpringMVC组件原理剖析

再看一下getHandlerExecutionChain方法

SpringMVC组件原理剖析

最终这个chain参数就返回到doDispatcher方法,如下标红的位置

SpringMVC组件原理剖析

上面的过程,就是下图中标红的地方

SpringMVC组件原理剖析

2.3 HandlerAdapter执行目标方法

doDispatcher方法还没有完成,继续往下看

再往下走会调用getHandlerAdapter方法

SpringMVC组件原理剖析

继续往下走,会执行拦截器的preHandle前置方法

SpringMVC组件原理剖析

执行目标方法

SpringMVC组件原理剖析

执行后置方法

SpringMVC组件原理剖析

然后我们发现执行前置方法和后置方法的时候并不是HandlerAdapter对象执行的

但是执行目标方法的时候是HandlerAdapter对象执行的

然后我们可以看一下handle方法,执行目标方法

发现没有实现,我们看一下子类的实现

SpringMVC组件原理剖析

选择下图中的第一个

SpringMVC组件原理剖析

顺着截图向下走

SpringMVC组件原理剖析

SpringMVC组件原理剖析

最终到了下面这个地方

SpringMVC组件原理剖析

继续执行,会进入到下面标红的方法中

SpringMVC组件原理剖析

继续点进去

SpringMVC组件原理剖析

SpringMVC组件原理剖析

到了下面这个地方,看一下参数

SpringMVC组件原理剖析

上图的参数就是在我们访问时对应的参数

SpringMVC组件原理剖析

再点进doInvoke方法

SpringMVC组件原理剖析

然后发现了执行method.invoke(this.getBean(), args)方法

反射代码,最终通过反射执行目标方法

SpringMVC组件原理剖析文章来源地址https://www.toymoban.com/news/detail-481451.html

到了这里,关于SpringMVC组件原理剖析的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 15、SpringMVC之常用组件及执行流程

    DispatcherServlet 是前端控制器,由框架提供,不需要工程师开发; 作用:统一处理请求和响应,整个流程控制的中心,由它调用其它组件处理用户的请求。 HandlerMapping 是处理器映射器,由框架提供,不需要工程师开发; 作用:根据请求的 url、method 等信息去查找 Handler(即控制

    2024年02月05日
    浏览(58)
  • Flutter原理篇:GestureDetector原理深度剖析及手势原理(上)

    今天我们来讲讲GestureDetector的深度剖析,只有了解原理了,才能知道手势冲突如何解决以及如何更灵活的运用手势。 我们先来看看GestureDetector的内部结构 1. GestureDetector 只是一个包装类,最终还是由 Listener 的 RenderPointListener 执行事件的操作 2.点击事件开始时会首先执行 RawG

    2024年04月27日
    浏览(36)
  • Hbase基本原理剖析

    数据存储使用HBase来承接,HBase是一个开源的、面向列(Column-Oriented)、适合存储海量非结构化数据或半结构化数据的、具备高可靠性、高性能、可灵活扩展伸缩的、支持实时数据读写的分布式存储系统。更多关于HBase的信息,请参见:https://hbase.apache.org/。 存储在HBase中的表的

    2024年02月16日
    浏览(42)
  • Elasticsearch原理剖析

    Elasticsearch集群方案由EsMaster、EsClient和EsNode1、EsNode2、EsNode3、EsNode4、EsNode5、EsNode6、EsNode7、EsNode8、EsNode9进程组成,如下图所示,模块说明如表下所示。 说明如表: 名称 说明 Client Client使用HTTP或HTTPS协议同Elasticsearch集群中的EsClient以及各EsNode实例进程进行通信,进行分布式索

    2024年02月17日
    浏览(39)
  • Hive原理剖析

    Hive是建立在Hadoop上的数据仓库框架,提供大数据平台批处理计算能力,能够对结构化/半结构化数据进行批量分析汇总完成数据计算。提供类似SQL的Hive Query Language语言操作结构化数据,其基本原理是将HQL语言自动转换成MapReduce任务,从而完成对Hadoop集群中存储的海量数据进行

    2024年02月10日
    浏览(16)
  • IoTDB原理剖析

    IoTDB(物联网数据库)是一体化收集、存储、管理与分析物联网时序数据的软件系统。 Apache IoTDB采用轻量式架构,具有高性能和丰富的功能。 IoTDB从存储上对时间序列进行排序,索引和chunk块存储,大大的提升时序数据的查询性能。通过Raft协议,来确保数据的一致性。针对时

    2024年02月13日
    浏览(33)
  • ChatGPT原理剖析

    由开发者 准备好的罐头 回应: 下面是一个问答,让ChatGPT讲一个关于人工智慧的笑话,但可以看出来,这个笑话的笑点显然和我们平常人不太一样,显得笑点非常奇怪: 你搜寻之后,ChatGPT从网上搜寻答案, 整理重组 给你想要的答案: 但实际上,多数ChatGPT的答案在网络上都

    2023年04月09日
    浏览(35)
  • Flink基本原理剖析讲解

    Flink是一个批处理和流处理结合的统一计算框架,其核心是一个提供了数据分发以及并行化计算的流数据处理引擎。它的最大亮点是流处理,是业界最顶级的开源流处理引擎。 Flink最适合的应用场景是低时延的数据处理(Data Processing)场景:高并发pipeline处理数据,时延毫秒级

    2024年02月16日
    浏览(37)
  • HDFS原理剖析

    HDFS是Hadoop的分布式文件系统(Hadoop Distributed File System),实现大规模数据可靠的分布式读写。HDFS针对的使用场景是数据读写具有“一次写,多次读”的特征,而数据“写”操作是顺序写,也就是在文件创建时的写入或者在现有文件之后的添加操作。HDFS保证一个文件在一个时

    2024年02月12日
    浏览(27)
  • IDDPM原理和代码剖析

    Improved Denoising Diffusion Probabilistic Models(IDDPM) 是上一篇 Denoising Diffusion Probabilistic Models(DDPM)的改进工作。 之前一些重要的公式已在上一篇博客 DDPM原理与代码剖析说过, 这里将不再赘述。本文主要将一些改进点和代码的解释。 本文参考视频 58、Improved Diffusion的PyTorch代码逐行深入

    2024年02月04日
    浏览(30)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包