目录
1.概述
Java EE三层架构
Spring MVC在三层架构中的位置
Spring MVC在表现层的作用
Spring MVC的特点
- Spring MVC是Spring框架的后续产品,可以方便地使用Spring框架所提供的其他功能。
- Spring MVC使用简单,很容易设计出干净简洁的Web层。
- Spring MVC支持各种请求资源的映射策略。
- Spring MVC具有非常灵活的数据验证、格式化和数据绑定机制,能使用任何对象进行数据绑定,不必实现特定框架的API。
- Spring MVC支持国际化,可以根据用户区域显示多国语言。
- Spring MVC支持多种视图技术。它支持JSP、Velocity和FreeMarker等视图技术。
- Spring MVC灵活性强,易扩展。
2.Spring MVC入门程序
代码实现
<?xml version="1.0" encoding="utf8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.it</groupId>
<artifactId>Days10</artifactId>
<version>1.0-SNAPSHOT</version>
<!-- 声明当前是一个maven的web工程-->
<packaging>war</packaging>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<!--spring的ioc相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>4.0.0</version>
<!--依赖范围-->
<scope>provided</scope>
</dependency>
<!-- spring jdbc相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-jdbc</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<!-- 事务相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<!--spring事务aop相关-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aspects</artifactId>
<version>5.2.6.RELEASE</version>
</dependency>
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.9.6</version>
<scope>runtime</scope> </dependency>
<dependency>
<groupId>aopalliance</groupId>
<artifactId>aopalliance</artifactId>
<version>1.0</version> </dependency>
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.3</version>
</dependency>
<!--单元测试-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
<!--mysql驱动-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.28</version>
<scope>runtime</scope>
</dependency>
<!-- <dependency>-->
<!-- <groupId>org.slf4j</groupId>-->
<!-- <artifactId>slf4j-log4j12</artifactId>-->
<!-- <version>1.6.1</version>-->
<!-- </dependency>-->
<!-- <dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.17</version>
</dependency>-->
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.2</version>
<configuration>
<source>1.8</source>
<source>1.8</source>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.2</version>
<configuration>
<uriEncoding>utf-8</uriEncoding>
<port>8080</port>
<!-- 虚拟项目名-->
<path></path>
</configuration>
</plugin>
</plugins>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.properties</include>
<include>**/*.xml</include>
</includes>
<filtering>true</filtering>
</resource>
<resource>
<directory>src/main/resources</directory>
</resource>
</resources>
</build>
</project>
<?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>
<!--配置springmvc配置文件的位置-->
<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>
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context https://www.springframework.org/schema/context/spring-context.xsd">
<!-- 注解扫描-->
<context:component-scan base-package="com.it.controller"></context:component-scan>
<!--视图解析器-->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="suffix" value=".jsp"></property><!--视图解析器的后缀-->
<property name="prefix" value="/WEB-INF/pages/"></property><!--视图解析器的前缀-->
</bean>
</beans>
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class FirstController {
@RequestMapping("/firstController")
public String sayHello()
{
System.out.println("访问第一个controller");
//string返回值,默认是视图的名字(视图解析器的前缀+此处的字符串+视图解析器的后缀)
return "success";
}
}
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<h1>hello springMVC!!!</h1>
</body>
</html>
Spring MVC工作原理
Spring MVC三大组件—处理器映射器
圈1是URL,圈2是Hanlder
Spring MVC三大组件—处理器适配器
Spring MVC三大组件—视图解析器
视图解析器进行视图解析,首先将逻辑视图名解析成物理视图名,即具体的页面地址,再生成View视图对象返回。
Spring MVC执行流程
Spring MVC执行流程详细介绍
1.用户通过浏览器向服务器发送请求,请求会被Spring MVC的前端控制器DispatcherServlet拦截。
2.DispatcherServlet拦截到请求后,会调用HandlerMapping(处理器映射器)。
3.处理器映射器根据请求URL找到具体的处理器,生成处理器对象及处理器拦截器(如果有则生成)一并返回给DispatcherServlet。
4.DispatcherServlet会通过返回信息选择合适的HandlerAdapter(处理器适配器)。
5.HandlerAdapter会调用并执行Handler(处理器),这里的处理器指的就是程序中编写的Controller类,也被称之为后端控制器。
6.Controller执行完成后,会返回一个ModelAndView对象,该对象中会包含视图名或包含模型和视图名。
7.HandlerAdapter将ModelAndView对象返回给DispatcherServlet。
8.前端控制器请求视图解析器根据逻辑视图名解析真正的视图。
3.Spring MVC的核心类和注解
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>
<!-- 启动时加载
如果不配置:当第一次访问当前servlet,tomcat才会加载这个servlet.
配置了正整数,意味着tomcat启动,就自动加载这个servlet
-->
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>DispatcherServlet</servlet-name>
<!--
代表缺省(默认)的servlet,当一个请求找不到与之对应的servlet的时候,就照这个缺省的servlet.
最终结果,拦截所有游览器发出的请求
-->
<url-pattern>/</url-pattern>
</servlet-mapping>
如果web.xml没有通过<init-param>元素指定DispatcherServlet初始化时要加载的文件,则应用程序会去WEB-INF文件夹下寻找并加载默认配置文件,默认配置文件的名称规则如下所示。
其中,[servlet-name]指的是web.xml文件中<servlet-name>元素的值;“-servlet.xml”是配置文件名的固定拼接。
<load-on-startup>元素取值
@Controller注解
基于@Controller注解的处理器类示例代码
import org.springframework.stereotype.Controller;
...
@Controller //标注@Controller注解
public class FirstController{
...
}
Spring MVC配置文件的类包扫描配置信息
<beans xmlns="http://www.springframework.org/schema/beans"
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/context
http://www.springframework.org/schema/context/spring-context.xsd">
<!-- 配置要扫描的类包 -->
<context:component-scan base-package="com.itheima.controller"/>
......
</beans>
Spring扫描配置文件范围
@RequestMapping注解
方式—标注在方法上
@RequestMapping("/login")
public String login()
{
System.out.println("处理登录成功");
return "success";
}
方式二标注在类上
@Controller
@RequestMapping("/springMVC")
public class FirstController {
这个一般用来做路径的分模块管理的
@RequestMapping注解的属性
value属性的两种映射路径标注
@RequestMapping(value="/firstController")
@RequestMapping("/firstController")
@Controller
public class AuthController {
@RequestMapping(value = {"/addUser","/deleteUser"})
public String checkAuth()
{
System.out.println("增删改体验");
return "success";
}
}
method属性限定处理器映射
@Controller
@RequestMapping("/method")
public class MethodController {
@RequestMapping(method = RequestMethod.GET)
public String get()
{
System.out.println("RequestMethod.GET");
return "success";
}
@RequestMapping(method = RequestMethod.POST)
public String post()
{
System.out.println("RequestMethod.post");
return "success";
}
@RequestMapping(method = RequestMethod.PUT)
public String put()
{
System.out.println("RequestMethod.put");
return "success";
}
@RequestMapping(method = RequestMethod.DELETE)
public String delete()
{
System.out.println("RequestMethod.delete");
return "success";
}
}
启动后我们用postman工具测试
method属性中有多个HTTP请求类型
如果需要同时支持多个请求方式,则需要将请求方式列表存放在英文大括号中,以数组的形式给method属性赋值,并且多个请求方式之间用英文逗号分隔,示例代码如下所示。
@RequestMapping(value = "/method",
method = {RequestMethod.GET,RequestMethod.POST})
public void getAndPost() {
System.out.println("RequestMethod.GET+RequestMethod.POST");
}
params属性值的定义方式
@Controller
public class ParamsController {
@RequestMapping(value = "/params",params = "id=1")
public void findById(String id) {
System.out.println("id="+id); }}
4.请求映射方式
请求映射方式的分类
a. 基于请求方式的URL路径映射
Spring MVC组合注解
@GetMapping:匹配GET方式的请求。
@PostMapping:匹配POST方式的请求。
@PutMapping:匹配PUT方式的请求。
@DeleteMapping:匹配DELETE方式的请求。
@PatchMapping:匹配PATCH方式的请求。
@GetMapping用法示例
// @RequestMapping(value = "/firstController",method = RequestMethod.GET)
@GetMapping("/firstController")
public String sayHello()
{
System.out.println("访问第一个controller");
//string返回值,默认是视图的名字(视图解析器的前缀+此处的字符串+视图解析器的后缀)
return "success";
}
这个GetMapping和上面注释处理是相同的 结果
b. 基于Ant风格的URL路径映射
Ant风格通配符的路径匹配
ant1
@RequestMapping("/ant1?")
public String ant1()
{
System.out.println("ant1方法");
return "success";
}
这个1后面只能跟1个字符,多了不行
ant2
@RequestMapping("/ant2/*.do")
public String ant2()
{
System.out.println("ant2方法");
return "success";
}
这个.do前面跟几个字符都可以
ant3
@RequestMapping("/*/ant3")
public String ant3()
{
System.out.println("ant3方法");
return "success";
}
这个/ant3前也是多个字符可以
ant4
@RequestMapping("/**/ant4")
public String ant4()
{
System.out.println("ant4方法");
return "success";
}
这个/ant4前可以跟一级或2级目录
ant5
@RequestMapping("/ant5/**")
public String ant5()
{
System.out.println("ant5方法");
return "success";
}
这个后面跟0或任意多的
映射路径使用多个通配符情况
c.基于RESTful风格的URL路径映射
传统风格访问的URL格式如下所示。
而采用RESTful风格后,其访问的URL格式如下所示。
需要注意的是,RESTful风格中的URL不使用动词形式的路径,例如,findUserById表示查询用户,是一个动词,而user表示用户,为名词。
RESTful风格的基本请求操作
RESTful风格四种请求的约定方式
地址一样请求的方式不一样,所代表的含义不一样
使用RESTful风格的优势
代码演示
@Controller
@RequestMapping("/user")
public class UserController {
@GetMapping("/{id}")
public String findById(@PathVariable("id") String id)
{
System.out.println("根据id查询:"+id);
return "success";
}
@DeleteMapping("/{id}")
public String deleteById(@PathVariable("id") String id)
{
System.out.println("根据id删除:"+id);
return "success";
}
@PutMapping("/{id}")
public String updateById(@PathVariable("id") String id)
{
System.out.println("根据id更新:"+id);
return "success";
}
@PostMapping("/{id}")
public String add()
{
System.out.println("新增");
return "success";
}
}