1.使用Front设计模式优点
-
只需要在一个Servlet中编写获取容器Bean的代码,减少了代码冗余。
-
不需要为每个控制器都创建一个类,而是可以在一个普通Java类中提供普通实例方法代表以前servlet中的service方法。
-
因为可以自己编写普通Java类,这类可以放入到Spring容器中,注入Service更方便。
-
同时因为是自己编写的Java,所以可以进行一些封装,对其他操作进行简化。(代码中没有体现)
EmpController:为控制器类,控制器类中可以有多个控制单元。
本质为普通的bean,交给springmvc容器管理。
2.Spring中的父子容器问题
Spring MVC属于Spring的子框架,所以Spring MVC中可以使用Spring框架的全部内容。(这里的父子关系只是逻辑上的父子关系,只是SpringMVC调用了Spring,并不是所谓的继承关系)
Spring MVC子容器可以调用Spring 父容器的全部内容。但是Spring父容器不能调用Spring MVC子容器内容。
3.Spring MVC环境搭建
Spring MVC 在平时随意可以当成一个独立框架看待,但其本质只是Spring Framework中的spring-webmvc.jar文件,这个jar文件依赖了spring web模块和Spring框架核心功能的5个依赖。所以在只使用Spring MVC框架时需要导入spring-webmvc依赖即可。
<?xml version="1.0" encoding="UTF-8"?>
<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.bjsxt</groupId>
<artifactId>springmvc1</artifactId>
<version>1.0-SNAPSHOT</version>
<packaging>war</packaging>
<dependencies>
<!-- 依赖了Spring框架核心功能的5个依赖以及Spring整合Web的依赖spring-web -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.3.16</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.tomcat.maven</groupId>
<artifactId>tomcat7-maven-plugin</artifactId>
<version>2.2</version>
<configuration>
<path>/bjsxt</path>
<port>8081</port>
</configuration>
</plugin>
</plugins>
</build>
</project>
2.编写web.xml内容
<?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">
<!--
Tomcat:
1.由于配置了<load-on-startup>1</load-on-startup>
Tomcat启动时就会创建DispathcherServlet对象。
2.DispathcherServlet对象创建后会执行初始化方法,
servletConfig对象读取servlet的初始化参数,根据读取到的初始化参数值创建springmvc容 器。(设置spring容器为父容器,逻辑上的父子关系)
springmvc配置文件中配置了<context:component-scan base-package="com.lsp.controller"/>
com.lsp.controller包中的类存在@Controller注解,该类交给springmvc容器管理。
3.只要获取到了springmvc容器就可以获取springmvc容器中的控制类对象。
4.DispathcherServlet映射路径为/,除了.jsp其它全部能匹配
5.客户端发起请求,协议://ip:port/qqq
访问的资源/qqq和DispathServlet的映射路径/可以匹配,
执行DispathcherServlet中service方法,从springmvc容器中获取控制器类,通过控制器找到控制单元,
可以根据请求资源和控制单元的注解值找到对应的控制单元,
执行控制单元,处理请求。
-->
<servlet>
<servlet-name>springmvc</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<!-- 参数名称必须叫做:contextConfigLocation。单词和大小写错误都导致配置文件无法正确加载 -->
<param-name>contextConfigLocation</param-name>
<!-- springmvc.xml 名称自定义,只要和后面创建的文件名称对应就可以了。 -->
<param-value>classpath:springmvc.xml</param-value>
</init-param>
<!-- Tomcat启动立即加载Servlet,而不是等到访问Servlet才去实例化DispatcherServlet -->
<!-- 配置上的效果:Tomcat启动立即加载Spring MVC框架的配置文件-->
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>springmvc</servlet-name>
<!-- /表示除了.jsp结尾的uri,其他的uri都会触发DispatcherServlet。此处前往不要写成 /* -->
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
3.创建控制器类
提示:
Spring MVC自定义控制器类都是以Controller结尾。
这些类都是放在controller的包中。
控制单元方法的访问权限修饰符没有强制要求,但是多写成public的。
控制单元的方法名没有要求,只要满足Java方法名定义要求就可以
4.@RequestMapping注解
@RequestMapping注解可以写到控制器类上,也可以写在控制单元方法上。
(如果类上和方法上都有写访问时的路径为控制器类上的类路径 / 控制器单元上的路径)
如果写在类上,表示当前类所有控制单元的映射路径,都以指定路径开头。
如果写在方法上,表示当前方法的映射而路径。最终访问这个控制单元的映射路径为:如果类上和方法上都有写访问时的路径为控制器类上的类路径 / 控制器单元上的路径
5.@RequestMapping的参数
1.path:映射的路径
映射一个访问路径:path = {"aa"} -》省略{} -》path = "aa",
映射多个访问路径:path = {"aa,bb"}
2.value:和path作用相同,只有一个value属性时,value可以省略
3.name:添加描述信息
4.method:允许的请求方式
RequestMethod.POST
RequestMethod.GET ...
简化:
@GetMapping -》 @RequestMapping(method = RequestMethod.GET)
@PostMapping -》@RequestMapping(method = RequestMethod.POST)
...
5.params: 指定子请求中必须携带的请求参数
6.headers: 指定请求中必须携带的请求头
7.produces:配合@ResponseBody注解使用,指定响应内容的类型。单独使用没有意义。
6.Ant风格的映射路径
符号 | 解释 |
? | 匹配任意单字符 |
* | 匹配0或者任意数量的字符 |
** | 匹配0或者更多数量的目录 |
使用Ant的特殊符号时,表示模糊匹配。可能出现客户端发送过来的URL能匹配上多个映射路径,这时的优先级为:
固定值 (bjsxt1) > ?形式(bjsxt?) > 一个*
号(/*
) > (/**)
形式
7.转发与重定向
底层:默认使用转发
return "/index.jsp"; 等价于 return "/index.jsp"; -》转发到项目目录下的资源
return "del"; 等价于 return "forward:del"; -》转发到当前所在目录中的资源
转发特点:
1.一次请求
2.地址栏不变
3.共享同一个Request和Response对象
4.tomcat内部行为
5.表单重复提交
使用重定向:手动指定
return "redirect:/index.jsp"; -》转发到项目目录下的资源
return "redirect:del"; -》转发到当前所在目录中的资源
重定向特点:
1.两次请求
2.地址栏改变
3.不共享同一个Request和Response对象
4.不是tomcat内部行为
5.解决表单重复提交
WEB-INF中的资源不可以客户端直接访问,保证资源的安全性,
客户端访问控制类中的控制单元,有控制单元转发到WEB-INF中的资源。
ModelAndView:模型数据(存储业务数据)和视图
Model:模型数据(存储模型层中查询到的数据)
View: 视图(页面属于视图中的一种)
控制单元执行完成后,无论什么类型返回值,都会封装为ModelAndView。
底层源码:
ModelAndView mv;
mv = ha.handle(processedRequest, response, mappedHandler.getHandler());
执行控制单元,控制单元返回结果封装为ModelAndView。
控制单元返回的结果固定被封装为ModelAndView。
视图解析器:ViewResolver(接口),解析不同的视图,使用不同的实现类
视图解析器,解析控制单元返回的ModelAndView,经过解析返回具体的View对象。
视图解析器解析JSP执行过程:
1.控制单元返回值固定封装为ModelAndView。例如:ViewName:/index.jsp
2.render();渲染方法
1.解析出视图名称。/index.jsp
2.根据视图名获取对应的视图解析器(默认使用:InternalResourceViewResolver),
3.通过InternalResourceViewResolver解析返回View对象(jsp 返回InternalResourceView)
4.InternalResourceView.render() 视图的渲染(将model中的数据通过view,向客户端完成响应)
1.将Model中的数据存储到request域对象中。
2.将请求转发到index.jsp。