SpringMVC-02-什么是SpringMVC

1、概述

img

Spring MVC是Spring Framework的Web开发部分,是基于Java实现MVC的轻量级Web框架。

  • 官方文档:https://docs.spring.io/spring-framework/docs/4.3.24.RELEASE/spring-framework-reference/html/
  • 中文官方文档:https://www.w3cschool.cn/spring_mvc_documentation_linesh_translation/spring_mvc_documentation_linesh_translation-y2ud27r5.html
  • 中文文档下载地址:https://www.jb51.net/books/593599.html

为什么要学习SpringMVC ?

Spring MVC的特点:

  1. 轻量级,简单易学
  2. 高效 , 基于请求响应的MVC框架
  3. 与Spring兼容性好,无缝结合
  4. 约定优于配置
  5. 功能强大:RESTful、数据验证、格式化、本地化、主题等
  6. 简洁灵活

Spring的web框架围绕DispatcherServlet [ 调度Servlet ] 设计。

DispatcherServlet的作用是将请求分发到不同的Handler。从Spring 2.5开始,使用Java 5或者以上版本的用户可以采用基于注解形式进行开发,十分简洁;

正因为SpringMVC好 , 简单 , 便捷 , 易学 , 天生和Spring无缝集成(可以使用IOC和AOP) , 使用约定优于配置 ,能够进行简单的junit测试 ,支持Restful风格 ,异常处理 ,本地化 ,国际化 ,数据验证 ,类型转换 ,拦截器 等等......所以我们要学习。

最重要的一点还是用的人多 , 使用的公司多 。

2、SpringMVC 核心组件

  • 前端控制器:DispactherServlet
  • 处理器映射器:HandlerMapping
  • 处理器适配器:HandlerAdapter
  • 处理器:Handler
  • 视图解析器:ViewResolver

组件介绍:

  • DispactherServlet:用于接收所有的客户端请求并将请求分发给合适的Handler(Controller)进行处理。在原生JavaWeb中,分发请求是由 Tomcat 根据 web.xml 来做的,SpringMVC使用 DispactherServlet 替代了这个功能。(不需要程序员开发)
  • HandlerMapping:解析每个请求的URL,找到对应的 Handler。(不需要程序员开发)
  • HandlerAdapter:适配器模式,适配调用具体的 Handler。(不需要程序员开发)
  • Handler:Controller层组件,对客户端请求进行逻辑处理,替代了原生JavaWeb中的 Servlet 所做的功能。(需要程序员手动开发)
  • ViewResolver:将 SpringMVC 中的 逻辑视图名 拼接成具体的视图地址,简化了视图地址的编写。(不需要程序员开发)

Spring MVC框架像许多其他MVC框架一样, 以请求为驱动 , 围绕一个中心Servlet分派请求及提供其他功能DispatcherServlet是一个实际的Servlet (它继承自HttpServlet 基类)

在这里插入图片描述

3、SpringMVC 执行原理

img

简要分析执行流程

  1. 当用户通过浏览器发起一个HTTP请求,请求直接到前端控制器 DispatcherServlet;
  2. 前端控制器接收到请求以后调用处理器映射器HandlerMapping,处理器映射器根据请求的URL解析出URI,找到具体的Handler,并将它返回给前端控制器;
  3. 前端控制器调用处理器适配器HandlerAdapter去适配调用Handler;
  4. 处理器适配器会根据Handler去调用真正的处理器去处理请求,并且处理对应的业务逻辑;
  5. 当处理器处理完业务之后,会返回一个ModelAndView对象给处理器适配器,HandlerAdapter再将该对象返回给前端控制器;ModelAndView 中的 Model 是指 被Model层执行业务处理后返回的数据对象,View 是指 将要转向的视图信息。
  6. 前端控制器DispatcherServlet将返回的ModelAndView对象传给视图解析器ViewResolver进行解析,解析完成之后就会返回一个具体的视图地址给前端控制器;(ViewResolver根据逻辑的View查找具体的View)
  7. 前端控制器DispatcherServlet转向具体的视图,并进行渲染;
  8. 渲染完成之后响应给用户(浏览器显示);

4、HelloSpringMVC(举个实例)

4.1、配置版

  1. 新建一个Moudle , SpringMVC-02-HelloMVC , 添加web的支持!

    image-20240627111446334

  2. 确定导入了SpringMVC 的依赖!

  3. 配置web.xml , 注册DispatcherServlet

    <?xml version="1.0" encoding="UTF-8"?>
    <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><!--注册DispatcherServlet--><servlet><servlet-name>DispatcherServlet</servlet-name><servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class><!--关联一个springmvc的配置文件--><init-param><param-name>contextConfigLocation</param-name><param-value>classpath:spring-mvc.xml</param-value></init-param><!--启动级别-1--><load-on-startup>1</load-on-startup></servlet><servlet-mapping><servlet-name>DispatcherServlet</servlet-name><url-pattern>/</url-pattern></servlet-mapping></web-app>
    

    配置说明:

    • init-param:当请求进入此servlet时,会携带的初始参数
    • classpath:classpath*::前者指的是 当前项目的编译路径,后者代表的是 当前项目及其依赖jar包的所有编译路径
    • load-on-startup:启动级别,当值为0或者大于0时,表示容器在应用启动时就加载这个servlet,值越小,优先级越高,当值是一个负数时或者没有指定时,则指示容器在该servlet被选择时才加载。
    • url-pattern 为 ‘/’:默认匹配,详见 关于tomcat中servlet的url-pattern匹配规则
  4. 编写SpringMVC 的 配置文件!名称:spring-mvc.xml,添加处理器映射器、 处理器适配器、 视图解析器

    image-20240627114550878

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"><!-- Handler映射器 --><bean class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"/><!-- Handler适配器 --><bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"/><!-- 视图解析器 --><bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"><property name="prefix" value="/WEB-INF/jsp/"/><property name="suffix" value=".jsp"/></bean></beans>
    
  5. 编写处理器 Handler ,实现Controller接口 或者 增加注解;需要返回一个ModelAndView,装数据,封视图

    image-20240627135809638

    import org.springframework.web.servlet.ModelAndView;
    import org.springframework.web.servlet.mvc.Controller;import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;public class HelloController implements Controller {@Overridepublic ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception {ModelAndView mv = new ModelAndView();mv.addObject("msg","HelloMVC");mv.setViewName("hello");return mv;}
    }
    
  6. 将编写的 Handler 交给SpringIOC容器,注册bean,添加到spring-mvc.xml中。

    <!-- Handler -->
    <bean id="/hello" class="controller.HelloController"/>
    
  7. 编写要跳转的jsp页面,显示ModelandView存放的数据,以及正常页面;

    image-20240627140629006

    <%@ page contentType="text/html;charset=UTF-8" language="java" %>
    <html>
    <head><title>hello</title>
    </head>
    <body>
    ${msg}
    </body>
    </html>
    
  8. 配置Tomcat,启动测试!

    image-20240627140949040

    image-20240627141420275

可能遇到的问题:访问出现404,排查步骤:

  1. 查看控制台输出,看一下是不是缺少了什么jar包。

  2. 如果缺少jar包,就在项目结构中添加相应的lib依赖!

    image-20240627142003042

    image-20240627142053793

  3. 重启Tomcat 即可解决!

4.2、注解版

  1. 新建一个Moudle,SpringMVC-03-Annotation ,添加web支持!

    image-20240628170543106

  2. 在pom.xml文件引入相关的依赖:主要有Spring框架核心库、Spring MVC、Servlet、 JSTL等。在父项目中已经引入了

  3. 配置web.xml

    image-20240628171324339

    <?xml version="1.0" encoding="UTF-8"?>
    <web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"version="4.0"><servlet><servlet-name>DispatcherServlet</servlet-name><servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class><init-param><param-name>contextConfigLocation</param-name><param-value>classpath:spring-mvc.xml</param-value></init-param><load-on-startup>1</load-on-startup></servlet><servlet-mapping><servlet-name>DispatcherServlet</servlet-name><url-pattern>/</url-pattern></servlet-mapping></web-app>
    

    配置说明:在上面的配置版讲过了,这里一样,就不说了。

  4. 添加Spring MVC配置文件

    image-20240628172911701

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"xmlns:context="http://www.springframework.org/schema/context"xmlns:mvc="http://www.springframework.org/schema/mvc"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsdhttp://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsdhttp://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
    "><!-- 组件扫描 --><context:component-scan base-package="com.moondream.controller"/><!-- 使用 default-servlet 处理静态资源 --><mvc:default-servlet-handler/><!-- 使用mvc注解驱动 --><mvc:annotation-driven/><bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"><property name="prefix" value="/WEB-INF/jsp/"/><property name="suffix" value=".jsp"/></bean></beans>
    

    配置说明:

    1. 加入了两个Xml命名空间 contextmvc

    2. <context:component-scan/>:组件扫描

      命名空间 context 下的标签,扫描指定包下所有被模板注解标注了的类,将其bean化并注册到IOC中。

      模板注解 即 @component 及其 组合注解(@Controller、@Configuration……),它们大都位于 org.springframework.stereotype 包下,抽象定义为 项目的某个模块,比如 @Controller 代表 项目的 控制层,@Service 代表 项目的 服务层,@Configuration 代表 项目的 配置,@Component 代表 项目的 组件。

      不想使用组件扫描,也可以将其手动一个个注册成bean

      <bean class="com.moondream.controller.HelloController"/>
      
    3. <mvc:default-servlet-handler/>:使用 default-servlet 来处理请求

      命名空间 mvc 下的标签,将 匹配到的请求 转发到 Tomcat 内建的 default servlet 中处理。

      一般用来处理 静态资源请求(.html、.css、.mp3、.jpg……),使用此标签要注意 配置中多个HandlerMapping的优先级问题,免得 非静态资源请求 被匹配上 default servlet ,那样会报 404 错误。

      其本质是

          <bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping"><!-- SimpleUrlHandlerMapping 通过urlMap来找相应的Handler --><property name="urlMap"><map><entry key="/**" value="org.springframework.web.servlet.resource.DefaultServletHttpRequestHandler#0"/></map></property></bean><bean class="org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter"/><bean class="org.springframework.web.servlet.resource.DefaultServletHttpRequestHandler"/>
      
    4. <mvc:annotation-driven/>:使用 mvc 注解驱动

      命名空间 mvc 下的标签,使用注解的方式来处理请求。

      其本质是

      <bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping"><!-- 使用高优先级 --><property name="order" value="0"/>
      </bean>
      <bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter"/>
      

      (spring3.1之前使用的是 DefaultAnnotationHandlerMapping 与 AnnotationMethodHandlerAdapter )

      (spring3.1之后替换成如上述所示)

      注解方式处理请求的简要流程:

      1)Spring容器启动,RequestMappingHandlerMapping在bean加载完成后,扫描出所有带有@Controller注解的bean,进而遍历出其中所有带有@RequestMapping注解 的方法,将方法上@RequestMapping注解信息封装成RequestMappingInfo对象,其包含了请求路径、请求方法、请求参数、请求头等信息,将方法本身封装成HandlerMethod对象,并以RequestMappingInfo为键,HandlerMethod为值,存储在一个Map结构中,以便于后续查找。

      2)当一个HTTP请求到达DispatcherServlet时,DispatcherServlet会调用RequestMappingHandlerMappinggetHandler()方法来查找到相应的 Handler,这里就是HandlerMethod

      3)如果找到了匹配的HandlerMethodDispatcherServlet就会根据其类型选择合适的HandlerAdapter(即RequestMappingHandlerAdapter)来执行它,并返回结果;如果没有找到匹配的HandlerMethodDispatcherServlet就会抛出异常并使用下一个 HandlerMapping 来查找 Handler 或者返回404错误页面。

      4)如果被封装成HandlerMethod的方法 或者 其上的类 被@ResponseBody注解 标注,那么HandlerMethod的返回结果就是一个单纯的数据字符串,会被当成响应体直接返回给客户端浏览器,否则就是逻辑视图名,会被视图解析器解析后转向具体视图。

      详见这篇文章的 RequestMappingHandlerMapping 部分:Spring MVC源码解析——HandlerMapping(处理器映射器)

  5. 编写Controller层,创建一个Java类:com.moondream.controller.HelloController , 注意编码规范

    image-20240629202633806

    import org.springframework.stereotype.Controller;
    import org.springframework.ui.Model;
    import org.springframework.web.bind.annotation.RequestMapping;@Controller
    @RequestMapping("/HelloController")
    public class HelloController {//真实访问地址 : 项目名/HelloController/hello@RequestMapping("/hello")public String sayHello(Model model){//向模型中添加属性msg与值,可以在JSP页面中取出并渲染model.addAttribute("msg","hello,SpringMVC");// /WEB-INF/jsp/hello.jspreturn "hello";}
    }
    

    注意:

    • 标注在类上的 @RequestMapping,相当于前置要求,每个RequestMappingInfo在被封装时,都会将类和对应方法上的 @RequestMapping 注解信息 整合注入自己。
    • 被封装成HandlerMethod的方法,返回值必须是String类型,方法参数会被框架进行数据绑定。如果想在访问的请求上加数据,可以设置一个Model类型的参数,这个参数对象将由框架传入,它会把自身被加入的数据封装到访问的请求上。不要设置ModelAndView类型的参数,它在HandlerMethod中无效。
    • 一个RequestMappingInfo匹配的请求范围不能被另一个RequestMappingInfo完全覆盖,不然程序会报错。简单来说,你要保证一个RequestMappingInfo至少有一类请求能匹配上。
  6. 创建视图层

    image-20240629225356409

    在WEB-INF/jsp目录中创建hello.jsp , 视图可以直接取出并展示从Controller带回的信息;

    <%@ page contentType="text/html;charset=UTF-8" language="java" %>
    <html>
    <head><title>Hello</title>
    </head>
    <body>
    ${msg}
    <br/>
    <%out.print(request.getRequestURI());%>
    </body>
    </html>
    
  7. 配置Tomcat运行,开启服务器,访问对应的请求路径!

    image-20240629225849505

    http://localhost:8080/spring03/HelloController/hello

    image-20240629230333689

    运行成功!!!

4.3、小结

实现步骤:

  1. 新建一个web项目
  2. 导入相关jar包
  3. 编写web.xml , 注册DispatcherServlet
  4. 编写springmvc配置文件
  5. 接下来就是去创建对应的控制类 , controller
  6. 最后完善前端视图和controller之间的对应
  7. 测试运行调试.

使用springMVC必须配置的三大件:

  • 处理器映射器、处理器适配器、视图解析器

通常,我们只需要手动配置视图解析器,而处理器映射器处理器适配器只需要开启注解驱动即可,省去了大段的xml配置。

不知道有没有小伙伴注意到一个问题:

在上述注解版的案例中,我们通过命名空间mvc下的两个标签default-servlet-handlerannotation-driven,在SpringIOC中配置了多个HandlerMapping和HandlerAdapter,

那么,当请求到达时,DispatcherServlet该使用哪个HandlerMapping和HandlerAdapter呢?

当IOC中有多个HandlerMapping时:

  1. DispatcherServlet会优先使用优先级高的HandlerMapping(所有HandlerMapping中,都有一个order属性,代表优先级)
  2. 如果HandlerMapping优先级一样,DispatcherServlet会使用先注册的
  3. 如果使用的HandlerMapping根据请求找不到Handler,DispatcherServlet会继续使用下一优先级的HandlerMapping继续找,直到找到Handler

当IOC中有多个HandlerAdapter时:

  1. DispatcherServlet会遍历所有注册的HandlerAdapter,根据请求的Handler类型来选择对应的HandlerAdapter
  2. 如果有多个HandlerAdapter都能够支持当前请求的Handler类型,选择第一个适配成功的HandlerAdapter来执行Handler,即选择先注册的HandlerAdapter

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/734410.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

视图控制器UINavigationController的介绍与基本使用

UINavigationController 是 iOS 中用于管理视图控制器层次结构的一个重要组件,通常用于实现基于堆栈的导航。它提供了一种用户界面,允许用户在视图控制器之间进行层次化的导航,例如从列表视图到详细视图。 UINavigationController 的主要功能管理视图控制器堆栈:使用一个堆…

拉普拉斯网格变形实现

因为课题需要,除了RBF还做了一个Laplace网格变形,其他大佬已经把原理写的很详细了,我就简单介绍一下公式,主要还是写写实现过程。过程同样参考了大佬的部分代码,而且实现的时候刚开始敲代码不久,所以有点乱QAQ。 首先,计算离散拉普拉斯坐标,网格上的点vi的拉普拉斯坐标…

文本三剑客之grep和awk

文本三剑客之grep和awk 目录文本三剑客之grep和awk 一、grep命令 grep命令的语法:grep[选项]...查找条件 目标文件命令 作用-m数字 多个匹配只取第一个-v 取反-i 忽略大小写-n 显示匹配的行号-c 统计匹配的行数-o 仅显示匹配到的字符串-A 数字 匹配后几行-B 数字 匹配前几行-C…

shell之条件测试语句

shell之条件测试语句 目录shell之条件测试语句一、test命令或[]中括号判断1、test命令2、[]中括号2.1 整数值比较[]2.2 实例操作2.2.1 查看系统内存是否超出预定值2.2.2 比较两个数的大小2.3 字符串比较2.3.1 案例:判断字符串是否相同2.3.2 案例:判断字符串是否为空2.4 逻辑测…

ikbc poker 2说明书

Poker II电子版说明书这是带6个dip开关,type-c接口,背后有理线槽支持侧向出线的一款poker。背后的金属铭牌型号为Poker Ⅱ。ikbc官网已经没有poker相关的内容了,说明书固件都无从下载。这份电子版说明书是找客服要的,这里存一下以作备份。原文档链接:ikbc_poker_II_说明书…

Django数据库

一、MySQL驱动程序安装 我们使用Django来操作MySQL,实际上底层还是通过python来操作的。因此我们想要用Django来操作MySQL,首先还是需要安装一个驱动程序。在Python3中,驱动程序有多种选择。比如pymysql以及mysqlclient等。这里我们就使用mysqlclient来操作。mysqlclient安装…

最后两次oop作业总结

1.前言 最后两次作业(即第七八次作业)大题目都是家居强电电路模拟程序,每次作业分别给了一个礼拜的时间去完成,题量较少,难度逐渐升高,以下为依次对两周题目集的知识点,题量和难度进行概述:第六次作业: 第六次作业只有一道题 家居强电电路模拟程序3,题目大概是输入设…

日志采集/分析

目录EFK1. 日志系统2. 部署ElasticSearch2.1 创建handless服务2.2 创建sts3. 部署kibana4. 部署ilogtail(docker-compose)4.1 编写docker-compose4.2 配置ilogtail采集4.3 查看容器采集的日志4.4 采集容器标准输出日志(可选)4.5 查看采集的容器日志5. 部署kafka5.1 kafka介绍…

AOD始终显示时间和信息(Dream)简析

AOD始终显示时间和信息(Dream)简析DreamManagerService启动在SystemServer的startOtherServices方法中会启动DreamManagerService服务这里是调用SystemServiceManager的startService方法显然,在SystemServiceManager的startService方法中首先将要启动的系统服务添加到其mSer…

操作系统——学习笔记(2)CPU虚拟化

学习黑皮书的一些呆瓜行为hhhhh

免费的攻击面管理平台-森罗

产品简介 森罗是有安科技推出的一款全新综合网络安全攻击面管理平台,集网络空间测绘与漏洞扫描于一体。森罗自带万象漏洞扫描器,与Nessus和Nuclei等许多产品一样,但它更现代,具有免等待的OOB测试策略、高级漏洞PoC IDE和强大的VDSL(漏洞域特定语言)引擎,使您能够轻松快速…

Fake权限验证小例子

前言 关于本地测试如何进行Fake权限验证 正文 在我们使用swagger调试本地接口的时候,我们常常因为每次需要填写token而耽误工作,不可能每次调试的时候都去本地测试环境请求一个token进行验证吧。上图可能是我们本地测试的时候需要填写的一个token位置,本地测试不方便。 那么…

41、linux-yum源管理-阿里云仓库配置

yum的管理1、清理原有的yum配置 把本地或者官方的/etc/yum.repos.d/路径下的所有repo配置文件移走确保/etc/yum.repos.d/这里没有其它文件2、下载配置阿里巴巴开源镜像站官网配置:https://developer.aliyun.com/mirror/在这个位置/etc/yum.repos.d/下载阿里云的yum源文件登陆…

vim基础使用

五、vim编辑器的使用 所有的Linux系统都默认有vi编译器,它就相当于Windows的记事本,当然,你也可以选择更好用的vim编译器,需要下载 yum install vim -y vim 有三种模式 使用vim filename wq!之后 这个命令如果filename不存在则 创建文件 [root@bogon opt]# vim zhanghaow…

【YOLOv8改进 - 注意力机制】NAM:基于归一化的注意力模块,将权重稀疏惩罚应用于注意力机制中,提高效率性能

**NAM: 提升模型效率的新颖归一化注意力模块,抑制非显著权重,结合通道和空间注意力,通过批量归一化衡量重要性。在Resnet和Mobilenet上的实验显示优于其他三种机制。源码见[GitHub](https://github.com/Christian-lyc/NAM)。**介绍摘要 识别较不显著的特征是模型压缩的关键。…

VP记录

我是真的红温了受打击了,他妈难受死了,遂记录这玩意儿,就算他妈没几个月就要退役。 ABC360 就是这场把我打击到了。之前15min切完ABCD,这回25min切B题,幽默🤡頑張って