简述SpringMVC(一)

本人小白一枚,欢迎大家一起讨论学习,如有错误,还望大家指教。

简述三层架构和MVC

三层架构
我们开发架构一般都是基于两种形式,一种是C/S架构(客户端/服务器)的,另一种是B/S架构(浏览器/服务器)的。在JavaEE开发中,几乎全都是基于B/S架构的开发。那么在B/S架构中,系统标准的三层架构分别是表现层、业务层和持久层,那么这三层都提供了那些功能?

  • 表现层:也就是我们常说的web层,它负责接收客户端请求,想客户端进行相应结果,通常客户端使用http协议请求web层,web需要接收http请求并完成http响应。表现层包括展示层和控制层,控制层负责接收请求,展示层负责结果展示。表现层的设计一般都是使用MVC模型(MVC是表现层的设计模型,和其它层是没有关系的)。
  • 业务层:也就是我们常说的service层,它负责业务逻辑处理,和我们开发项目的需求息息相关。web层依赖业务层,而业务层依赖持久层,为了保证事务的一致性,事务应该放在业务层来控制。
  • 持久层:也就是我们常说的dao层,负责数据持久化,包括数据层即数据库和数据库访问层,数据库是对数据进行持久化的载体,数据访问是业务层和持久层交互的接口,业务层需要通过数据访问层将数据持久化到数据库中,通俗的讲,持久层就是和数据库交互并对数据表进行增删改查。

MVC模型
MVC全名是Model View Controller,译为模型,视图,控制器。是一种用于设计创建web应用程序表现层的模式。MVC中每个部分各司其职。

  • Model(模型):通常指的就是我们的数据模型JavaBean,一般用于对数据的封装。
  • Vies(视图):通常指的是我们的jsp或者html,一般用于展示数据。
  • Controller(控制器):通常指的是我们的servlet,是应用程序中处理用户交互的部分,一般就是处理程序的逻辑。这个概念不是很容易理解。例如:我们要保存一个用户信息,该用户信息包含了姓名,性别,年龄等等。这时候表单输入要求年龄必须是1~100之间的整数。姓名和性别不能为空,并且要把数据填充到模型之中。此时除了js的校验外,服务器端也应该有数据准确性的校验,这就是控制器该做的事情。当检验失败后,由控制器负责把错误页面展示给用户,如果校验成功,控制器负责将数据填充到模型,并且调用业务层实现完整的业务需求。

简述SpringMVC

什么是SpringMVC
SpringMVC是一种基于Java实现的MVC设计模型的请求驱动类型的轻量级web框架,属于SpringFrameWork的后续产品,已经融合在Spring Web Flow里面。Spring框架提供了构建Web应用程序的全功能MVC模块,可以选择使用Spring中的SpringMVC框架或者集成其他MVC开发框架,如Struts等等。SpringMVC已经成为目前最主流的MVC框架之一,并且随着spring3.0的发布已经全面超越了Struts成为了最优秀的MVC框架。它通过一套注解,让一个简单的Java类成为处理请求的控制器,从而无需实现任何接口,同时它还支持RESTful编程风格的请求。
SpringMVC和Struts2的对比

  • 共同点:它们都是表现层框架,都是基于MVC模型编写的。它们的底层都离不开原始Servlet API。它们处理请求的机制都是一个核心控制器。
  • 区别
    • Spring MVC的入口是Servlet,而Struts2的入口是Filter。
    • Spring MVC是基于方法设计的,而Struts2是基于类,Struts2每次执行都会创建一个类,所以比Spring MVC消耗资源。
    • Spring MVC的使用更加简洁,同时还支持JSP303,处理ajax的请求更方便。
    • Struts2的olgn(对象导航图语言)表达式使页面的开发比Spring MVC更高效 ,但是执行效率并没有JSTL好,尤其是Struts2的表单标签。

入门演示

  • 创建一个web工程,并在pom文件添加如下坐标。
  <properties>
    <!--版本锁定-->
    <spring.version>5.0.2.RELEASE</spring.version>
  </properties>

  <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.11</version>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>${spring.version}</version>
    </dependency>
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-web</artifactId>
      <version>${spring.version}</version>
    </dependency>
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>${spring.version}</version>
    </dependency>
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>servlet-api</artifactId>
      <version>2.5</version>
      <scope>provided</scope>
    </dependency>
    <dependency>
      <groupId>javax.servlet.jsp</groupId>
      <artifactId>jsp-api</artifactId>
      <version>2.0</version>
      <scope>provided</scope>
    </dependency>
  </dependencies>
  • 创建controller包,并添加测试类。
@Controller
public class Demo {
    @RequestMapping("hello")
    public String demo1() {
        System.out.println("Hello SpringMVC~~~");
        return "success";
    }
}
  • 在web.xml中配置如下内容。
<web-app>
  <!--spring核心控制容器-->
  <servlet>
    <servlet-name>dispatcherServlet</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    <!--配置servlet的初始化参数,读取配置文件,创建spring容器-->
    <init-param>
      <param-name>contextConfigLocation</param-name>
      <param-value>classpath:springmvc.xml</param-value>
    </init-param>
    <!--配置servlet启动时加载对象-->
    <load-on-startup>1</load-on-startup>
  </servlet>
  <servlet-mapping>
    <servlet-name>dispatcherServlet</servlet-name>
    <url-pattern>/</url-pattern>
  </servlet-mapping>
</web-app>
  • 在resources目录下创建springmvc.xml配置文件,并添加如下内容。
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xmlns:context="http://www.springframework.org/schema/context"
       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
        http://www.springframework.org/schema/mvc
        http://www.springframework.org/schema/mvc/spring-mvc.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd">
    <!--配置spring创建容器时要扫描的包-->
    <context:component-scan base-package="controller"/>
    <!--配置视图解析器-->
    <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/WEB-INF/pages/"/>
        <property name="suffix" value=".jsp"/>
    </bean>
    <!--配置spring开启注解mvc的支持-->
    <mvc:annotation-driven/>
</beans>
  • 修改index.jsp页面,添加两个超链接,以下两种方式都可以访问到我们那个Controller类。
<%@ page contentType="text/html;charset=UTF-8" language="java" isELIgnored="false" %>
<html>
<body>
<a href="/hello"><h3>入门演示1</h3></a>
<a href="${pageContext.request.contextPath}/hello"><h3>入门演示2</h3></a>
</body>
</html>
  • 添加success.jsp页面,当执行到controller时,会让其跳转到该页面。
<%@ page contentType="text/html;charset=UTF-8" language="java" isELIgnored="false" %>
<html>
<head>
    <title>Title</title>
</head>
<body>
    <h3>演示成功</h3>
</body>
</html>
  • 启动项目,测试并查看结果,无论点击演示1还是点击演示2,都会跳转到演示成功页面。
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

入门演示执行过程及原理分析
从刚才的演示中,我们可以分析出来,当服务器启动时,应用被加载,服务器会读取web.xml中的配置内容,而后创建spring容器并且初始化容器中的对象。当点击超链接,浏览器发出请求,被DispatherServlet前端控制器捕获,该Servlet并不处理请求,而是将该请求转发出去,转发的路径是根据请求的URL,匹配到@RequestMapping中的内容,如果匹配到,则执行对应的方法,该方法有一个字符串的返回值,对于这个返回值的含义,我们在下面介绍。根据执行方法的返回值,由InternalResourceViewResolver视图解析器为我们找到对应的结果视图,最后渲染结果视图,并将结果响应给浏览器。
在这里插入图片描述
在这里插入图片描述

简述SpringMVC组件

  • DispatchServlet:前端控制器,用于请求到达前端控制器,他就相当于mvc模式中的c,dispatcherServlet是整个流程控制的中心,由它调用其他组件处理用户请求,dispatcherServlet的存在降低了组件之间的耦合。
  • HeadlerMapping:处理器映射器,HandlerMapping负责根据用户请求找到Handler即处理器,SpringMVC提供了不同映射器实现不同的映射方式,例如:配置文件方式,实现接口方式,注解方式等等。
  • Handler:处理器,它就是我们开发中要编写的具体业务控制器。由DispatcherServlet把用户请求转发到Handler中,由Handler对具体的用户请求进行处理。
  • HandlerAdapter:处理器适配器,通过HandlerApdater对处理器进行执行,这就是适配器模式的应用,通过扩展适配器可以对更多类型的处理器进行执行。
  • ViewResolver:视图解析器,ViewResolver负责将结果生成View视图,ViewResolver首先根据逻辑视图名解析物理视图名即具体的页面地址,再生成View视图对象,最后对View进行渲染将结果通过页面展示给用户。
  • View:视图,SpringMVC框架提供了很多的View视图类型的支持,包括jstlView、freemarkerView、pdfView等等。我们最常用的视图就是jsp。一般情况下需要通过页面标签或页面模板技术将模板数据通过页面展示给用户,需要由程序员根据业务需求开始开发具体的页面。

<mvc:annotation-driven>说明
在SpringMVC的各个组件中,处理器映射器、处理器适配器、视图解析器称为SpringMVC的三大组件。通过上面的演示在springmvc.xml中我们只配置的视图解析器,并没有配置处理器映射器以及处理器适配器,原因就是使用<mvc:annotation-driven>,该配置会自动加载处理器映射器和处理器适配器。该配置替代了处理器映射器和处理器是配置,它相当于在xml中配置了:

<!-- HandlerMapping --> 
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping"/> 
<bean class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"/>
<!-- HandlerAdapter --> 
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerA dapter"/> 
<bean class="org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter"/> 
<bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"/> 
<!-- HadnlerExceptionResolvers --> 
<bean class="org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExcept ionResolver"/> 
<bean class="org.springframework.web.servlet.mvc.annotation.ResponseStatusExceptionResolver"/>
<bean class="org.springframework.web.servlet.mvc.support.DefaultHandlerExceptionResolver"/> 

请求参数的绑定
我们都知道,表单中的请求参数都是基于key=value的形式,SpringMVC绑定请求参数的过程是通过提交请求参数对控制器中方法参数进行绑定。支持的数据类型有基本数据类型,包括基本类型和String类型,POJO类型,包括实体类以及关联的实体类。数组和集合类型:包括List结构和Map结果的集合。SpringMVC参数绑定是自动实现的,如果要使用,必须遵循使用要求。如果是基本类型或者String类型,要求我们的参数名称和控制器中的方法的参数名称必须保持一致,严格区分大小写。如果是POJO类型,或者是它关联对象,要求表单中参数名称和POJO类的属性名称保持一致,并且控制器方法的参数类型是POJO类型。如果是集合类型,有两种方式,第一种要求集合类型的请求参数必须在POJO中,在表单中请求参数名称要和POJO中的集合属性名称相同,给List集合中的元素赋值,使用下标。给Map集合中的元素赋值,使用键值对。第二种,接收的请求参数时json格式数据,需要借助一个注解实现。如果遇到特殊类型要求,我们可以自己编写自定义类型的转换器。
请求参数中文乱码问题
get请求方式:tomcat对get和post请求处理方式是不同的,get请求的编码问题,要改tomcat的servlet.xml配置文件,修改如下。

<Connector connectionTimeout="20000" port="8080" protocol="HTTP/1.1" redirectPort="8443"/> 

修改为:

<Connector connectionTimeout="20000" port="8080" protocol="HTTP/1.1" redirectPort="8443" useBodyEncodingForURI="true"/> 

如果遇到ajax请求乱码则修改为:

<Connector connectionTimeout="20000" port="8080" protocol="HTTP/1.1" redirectPort="8443" useBodyEncodingForURI="UTF-8"/> 

post请求方式:在web.xml中配置过滤器。

 <!-- 配置SpringMVC编码过滤器 -->
  <display-name>Archetype Created Web Application</display-name>
  <filter>
    <filter-name>characterEncodingFilter</filter-name>
    <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
    <!-- 设置过滤器的属性 -->
    <init-param>
      <param-name>encoding</param-name>
      <param-value>UTF-8</param-value>
    </init-param>
    <!-- 启动过滤器 -->
    <init-param>
      <param-name>forceEncoding</param-name>
      <param-value>true</param-value>
    </init-param>
  </filter>
  <!-- 过滤所有请求 -->
  <filter-mapping>
    <filter-name>characterEncodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>

自定义类型转换器
当我们需要将一个格式为“2020-04-12”的字符串转换一个Date类型时,我们需要自定义一个类型转换器来为我们解决这个问题,SpringMVC提供了一个Converter接口,自定义一个类型转换类,并实现该接口。
在这里插入图片描述

public class StringToDateConverter implements Converter<String, Date> {

    @Override
    public Date convert(String s) {
        DateFormat format = null;
        try {
            if (StringUtils.isEmpty(s)) {
                throw new NullPointerException("请输入要转换的日期");
            }
            format = new SimpleDateFormat("yyyy-MM-dd");
            Date date = format.parse(s);
            return date;
        } catch (ParseException e) {
            e.printStackTrace();
            throw new RuntimeException("类型转换异常");
        }
    }
}

在SpringMVC配置文件中配置类型转换器,spring配置类型转换器的机制是,将自定义的转换器注册到类型转换服务中去并在annotation-driver标签中引用配置的类型转换器。

<!--配置类型转换器工厂-->
<bean id="conversion" class="org.springframework.context.support.ConversionServiceFactoryBean">
    <property name="converters">
        <array>
            <!--配置自定义类型转换器-->
            <bean class="utils.StringToDateConverter"/>
        </array>
    </property>
</bean>
<!--配置spring开启注解mvc的支持-->
<mvc:annotation-driven conversion-service="conversion"/>

使用ServletAPI
SpringMVC支持原始ServletAPI对象作为控制器方法的参数,支持原始ServletAPI对象有如下图所示。
在这里插入图片描述

简述常用注解

  • @RequestMapping:该注解用户建立URL和处理请求方法之间的对象关系,可以用于类上,可以用于方法上,用于类上相当于访问的根目录,用于方法上相当于URL的第二级访问目录。
    • value:用于指定请求的URL,它的作用和path属性作用是一样的。
    • method:用于指定请求方式,属性值有RequestMethod.GET,RequestMethod.POST,RequestMethod.DELETE等等。
    • params:用于指定限制请求参数的条件,它支持简单的表达式,要求请求参数的key和value必须和配置一模一样。
    • headers:用于指定限制请求消息头的条件。
  • @RequesetParam :把请求中指定名称的参数给控制器中的形参赋值。在上面我们介绍了SpringMVC中的参数绑定时,需要请求参数名称和控制器中形参的名称要一致,如果名称不一致我们想将参数进行绑定,该怎么解决?这个注解的出现就是解决这个问题的。
    • value:请求参数中的名称。
    • required:请求参数中是否必须提供此参数,默认值为true,表示必须提供,如果不提供将报错。
  • @RequestBody 用于获取请求体内容,直接使用得到的是key=value&key=value…结构的数据,get方式不适用。
    • required:是否必须有请求体,默认值为true,当取值为true时,get请求方式会报错,如果取值为false时,get请求得到的是null。
  • @PathVaribale:用于绑定url中的占位符,例如:请求url中的/delete/{id},这个{id}就是url的占位符。url支持占位符是在spring3.0之后加入的,是SpringMVC支持rest风格url的一个重要标志。
    • value:用于指定url中占位符名称。
    • required:是否必须提供占位符。
  • @RequestHeader:用于获取请求消息头 ,这个注解不是很常用。
    • value:标明消息头的名称。
    • required:是否必须有此消息头。
  • @CookieValue:用于把指定的cookie名称传入控制器方法参数。
    • value:标明cookie的名称。
    • required:是否必须有此cookie。
  • @ModelAttribute :该注解是SpringMVC4.3版本之后新加入的,它可以用于修饰方法和参数,出现在方法上,表示当前方法会在控制器方法执行之前先执行。它可以修饰没有返回值的方法,也可以修饰有具体返回值的方法。出现在参数上,获取指定的数据给参数赋值。应用场景,我们在编辑一个用户时,用户有一个创建信息字段,该字段的值是不允许被修改的。在提交表单数 据是肯定没有此字段的内容,一旦更新会把该字段内容置为 null,此时就可以使用此注解解决问题。
  • @SessionAttribute:用于多次执行控制器方法间参数的共享。
    • value:用于指定存入的属性名称,用在类上。
    • type:用于指定存入的数据类型。
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值