DispatcherServlet 本质上是一个 Servlet,所以遵循 Servlet 的生命周期。所以宏观上是 Servlet 生命周期来进行调度。

一、DispatcherServlet是什么

DispatcherServlet: 前端控制器, 统一处理请求和响应,整个流程控制的中心,由它调用其它组件处理用户的请求,本质上是一个 Servlet(初始化->运行->销毁),所以遵循 Servlet 的生命周期。所以宏观上是 Servlet 生命周期来进行调度。既然是Servlet那么就按照Servlet生命周期去分析源码就好了。

二、DispatcherServlet的继承结构(重要)

IDEA中快捷键Ctrl+Shift+Alt+U 可查看继承图
在这里插入图片描述

graph TD
A[Servlet]
A==>B[GenericServlet]
B==>C[HttpServlet]
C==>D[HttpServletBean]
D==>E[FrameworkServlet]
E==>F[DispatcherServlet]
从上图中可以看到DispatcherServlet的顶层接口是Servlet

三、初始化流程详细介绍

可以使用IDEA工具,跟着本文档步骤,一起查看初始化流程

$\color{#F00}{虽然我们看的是不同类中的调用过程,如果通过继承或者实现放到同一个类中}$
$\color{#F00}{其实我们就是在同一个类中来查看方法的调用。}$

1.Servlet接口

从Servlet接口开始步步分析,在Servlet接口中存在下图中的5中抽象方法。
快捷键: Alt+7
在这里插入图片描述
初始化方法则是init(ServletConfig config)方法

public interface Servlet {
    public void init(ServletConfig config) throws ServletException;    
}

2.GenericServlet抽象类

public abstract class GenericServlet implements Servlet, ServletConfig,
        java.io.Serializable {
        
     //重写Servlet中的初始化方法
     @Override
     public void init(ServletConfig config) throws ServletException {
         this.config = config;
         this.init();
      }
    
     //重写的init方法中,又调用空参的初始化方法
     public void init() throws ServletException {
        // NOOP by default
     }
}
重写Servlet接口中的初始化方法,发现其又调用了空参的初始化方法,那么接下来查看

3.HttpServle抽象类

在这里插入图片描述

可以发现HttpServle没有重写init方法,用的是父类中的方法,那么我们接着向下看

4.HttpServletBean抽象类

在这里插入图片描述

HttpServletBean中重写了GenericServlet中的init初始化方法,那么证明GenericServlet中的空参init方法直接到这里了

然后查看init方法调用过程
在这里插入图片描述也就是下图中的initServletBean()方法
在这里插入图片描述
现在可以发现这次调用的是initServletBean()方法,我们来看子类是否对该方法进行了重写

5.FrameworkServlet抽象类

在这里插入图片描述可以看到上图中重写了HttpServletBean中的initServletBean()方法,那么其中最重要的则是initWebApplicationContext()初始化web容器方法,接下来查看初始化方法都做了些什么如下图
在这里插入图片描述与上图为一个方法内,用来初始化和刷新WebApplicationContext
在这里插入图片描述

ServletContext是一个域对象。ServletContext是在web工程部署启动的时候创建。在web工程停止的时候销毁。Servlet上下文 一个 Web工程只有一个。

刷新容器时都做了什么呢?这个方法由子类实现在这里插入图片描述

6.DispatcherServlet类

主要是为了初始化Spring MVC中各个组件
在这里插入图片描述

FrameworkServlet创建WebApplicationContext后,刷新容器,调用onRefresh(wac),此方法在DispatcherServlet中进行了重写,调用了initStrategies(context)方法初始化各个组件

7.初始化时机

  • Servlet默认情况下,当第一次访问时完成初始化,但是我们可以看到流程比较复杂,所以需要在启动时初始化(防止第一次访问时间过长)
  • 在WebMvcProperties的内部类Servlet中的定义,默认值是-1,DispatcherServlet会在请求来时执行一次初始化
private int loadOnStartup = -1;
  • 因此要想在创建容器的过程中初始化DispatcherServlet,这需要设置该参数的值大于等于0

    spring.mvc.servlet.load-on-startup=1

各组件的作用

  • DispatcherServlet:前端控制器,统一处理请求和响应,整个流程控制的中心,由它调用其它组件处理用户的请求
  • HandlerMapping:处理器映射器,根据请求的url、method等信息查找Handler,即控制器方法
  • Handler:处理器,在DispatcherServlet的控制下Handler对具体的用户请求进行处理
  • HandlerAdapter:处理器适配器,通过HandlerAdapter对处理器(控制器方法)进行执行
  • ViewResolver:视图解析器,不需要工程师开发,由框架提供,进行视图解析
  • View:视图 将模型数据通过页面展示给用户

Dream_sky
13 声望1 粉丝

🍓 简介:java系列技术分享(👉持续更新中…🔥)