SpringMVC执行流程【简单理解举例】

本文介绍

该篇文章主要讲解SpringMVC的执行流程,即前端控制器、控制器等组件的调用
先从Spring的一个基础案例,转到SpringMVC。以此来观察到SpringMVC做了哪些改变
然后分析SpringMVC程序的执行流程,知道代码是如何跑起来的,一个请求又是如何返回一个页面的
最后根据SpringMVC的架构图,讲解程序中没有体现的、SpringMVC封装好的那些组件

作者能力有限,只作为自己学习的笔记,可能理解有误差(毕竟全信书不如不看书嘛)

Spring简单执行示例

案例内容:
浏览器访问:localhost/UserServlet,返回一个页面

程序结果:显示了一句话的浏览器页面

  • 项目目录
    项目目录
  • web.xml配置
    指定要拦截的请求路径是/UserServlet,由UserServlet类进行处理
<servlet>
	<servlet-name>UserServlet</servlet-name>
	<servlet-class>com.UserServlet</servlet-class>
</servlet>
<servlet-mapping>
	<servlet-name>UserServlet</servlet-name>
	<url-pattern>/UserServlet</url-pattern>
</servlet-mapping>
  • UserServlet
    打印语句到控制台,然后返回success.jsp页面
public class UserServlet extends HttpServlet{
	protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws Exception{
		System.out.println("user servlet is running...");
		req.getRequestDispatcher("success.jsp").forward(req,resp);
	}
	//doPost方法省略
}

改造成SpringMVC

上述程序改造成SpringMVC

  • 指定表现成业务处理器,并将其配置成Spring的bean(等同于Servlet)
    当前端访问时,就会执行该程序
    需要设置方法的访问地址,确定什么请求会执行这个方法
    设置要跳转的页面,不然会报错,如果不设置跳转页面,输出语句也会正常执行
//设定当前类为Spring的控制类
@Controller
public class UserController{
	//设定当前方法的访问映射地址,相当于之前web.xml中配置的<url-pattern>
	@RequestMapping("/save")
	//设置当前方法返回值类型为String,用于指定请求完成后跳转的页面
	public String save(){
		System.out.println("user mvc controller is running...");
		//返回跳转的页面名称
		return "success.jsp";
	}
}
  • 创建spring-mvc.xml配置文件
    等同于spring的xml配置文件,只是需要区分一下。此时可以删除原来的spring的配置文件
    在配置文件中开启组件扫描注解驱动,不然扫描不到上边类的@Controller注解,也就无法把UserController交给springMVC控制
<context:component-scan base-package="com"/>
  • 修改web.xml
    用DispatcherServlet顶替掉之前的UserServlet,目前可以将DispatcherServlet理解成== 看大门 == 的,专门拦截请求
    既然要拦截请求,那么作为一个正经看大门的,也要有原则!所以需要配置具体拦截哪个请求
    看大门的有了,那么用户真正想进去的还是== 办公室 (UserController)== 啊,只有spring加载了才可以。所以加上,把spring-mvc.xml文件加载进来
<servlet>
    <servlet-name>DispatcherServlet</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    <!--初始化时,读取spring-mvc.xml文件的配置,加载bean-->
    <init-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>classpath*:spring-mvc.xml</param-value>
    </init-param>
</servlet>

<!--读取bean中所有添加了映射注解的内容-->
<servlet-mapping>
    <servlet-name>DispatcherServlet</servlet-name>
    <url-pattern>/</url-pattern>
</servlet-mapping>

程序执行流程分析

  • 服务器启动
    1. 加载web.xml中的DispatcherServlet
    2. 读取spring-mvc.xml中的配置,加载所有com包中所有标记为bean的类
    3. 读取bean中方法上标注@RequestMapping的内容(知道自己可以处理哪些请求)
  • 处理请求
    1. DispatcherServlet配置拦截所有请求(因为在web.xml中配置的是/)
    2. 使用请求路径与所有加载的@RequestMapping的内容进行对比
    3. 找到匹配的访问路径,执行对应的方法
    4. 根据方法返回值,在webapp目录中查找对应的页面并展示

SpringMVC架构图以及执行流程(可以直接跳过来)

架构图

SpringMVC架构图执行

名词解释(官方话):

  • 前端控制器DispatcherServlet: 整体流程控制中心,降低组件间的耦合性
  • 处理器映射器HandlerMapping: 根据用户请求找到对应具体的Handler处理器
  • 处理器Handler: 业务处理的核心类(servlet类似,自己开发)
  • 处理器适配器HandlAdapter: 对Handler处理器进行执行,即找到要执行的servlet方法
  • 视图解析器View Resolver: 将处理结果生成View视图
  • View: 最终产出的页面结果

执行流程

  1. 用户发送请求 --> 前端控制器
  2. 前端控制器(若配置了拦截此路径)会拦截此请求,然后调用处理器映射器
  3. 处理器映射器确定要调用哪个处理器,并可能执行处理器链(过滤器、拦截器),最后将处理器地址返回给前端控制器
  4. 前端控制器拿着地址调用处理器适配器,由其去调用具体的处理器(业务处理方法实现)
  5. 处理器会返回页面以及数据(Model And View)给处理器适配器
  6. 处理器适配器将其再返回给前端控制器
  7. 前端控制器调用视图解析器,将MV解析成JSP或者HTML,返回给前端控制器
  8. 最后前端控制器将解析完的页面返回给用户

自己理解

可能有点啰嗦,但是却很能理解(基于真事改编)**
一次请求就可以看做是你去银行办事
假设小明(没错,就是他)今天要去银行开通手机支付
举例银行办理业务流程图

  • 你不能直接去柜台办理(除非你特别豪横、有钱、知道哪个柜台可以办理这个业务
  • 所以第一步是去咨询前台(前端控制器),告诉前台小哥哥/小姐姐你要办理更改密码这个业务
  • 前台在电脑上查询(处理器映射器)这个业务是哪个柜台能办理(前台业务能力真低
  • 然后前台就告诉你在预约机器(处理器适配器)上排队取号,选便民服务(不要问我这是不是真的,我不知道
  • 当轮到你时,你就去柜台(处理器)办理业务,柜台小姐姐说已经改好了,但是需要你在手机银行软件上转账三次进行激活(激活操作就相当于Model And View,此时用户还不能直接处理这个数据)
  • 小明不知道该怎么操作,于是还是要问前台(前端控制器)
  • 那业务低的前台(前端控制器)就问问他们的经理(视图解析器
  • 经理(视图解析器)告诉前台(前端控制器)操作步骤(View),然后前台再告诉小明,自此,小明这个业务才算完成
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值