思维导图:
一.引言
Spring MVC 的功能是帮助我们实现视图V和数据模型M的解耦,而这靠的就是中间的重定向层Controller C.本文主要分为三个部分进行介绍.第一部分讲解Spring MVC的工作原理,第二部分简单的搭建了一个Spring MVC的例子,第三部分则引入数据模型M,对M进行相关的处理.
二.Spring MVC的工作原理
Spring MVC的工作原理是将带有数据的请求经过特定的控制器处理后,有控制器决定使用那个视图解析器获取视图在返回给前端页面.具体流程如下图:
- 首先,所有的请求都会到达一个DispacherServlet,这是一个前端控制器,他负责将请求委托给相应的组件处理.
- DispacherServlet根据此请求的URL地址匹配对应的处理器映射,决定由那个控制器Controller处理.
- 请求到达控制器,控制器会进行处理,如何处理则属于业务逻辑层面.
- 控制器处理完毕后,会返回数据模型并指定视图名称
- DispacherServlet根据视图解析器并利用控制器返回的视图名称来获取特定的视图页面
- 视图会进行渲染
- 将视图返回给请求
三.搭建Spring MVC
在这一小节中,我们的目的是搭建一个使用Spring MVC的web工程,其作用就是给特定请求返回一个只有Hello Spring的页面.
搭建Spring MVC 的web工程主要分为以下几个步骤:
- 配置web应用的初始化类
- 配置两种应用上下文
- 创建控制器并配置后相应的视图
3.1初始化web应用
这一步的主要作用有三:设置基础路径,指定DispatherServlet上下文配置类.指定ContextLoaderListner上下文配置类.
/**
* 微博初始化类
* 主要作用是初始化两个应用上下文及映射URL地址
* 必须继承AbstractAnnotationConfigDispatcherServletInitializer实现以下三个方法
*
* @author : zhouhao
* @date : Created in 2019/3/14 6:54
*/
public class MicroBlogAppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
/**
* 负责初始化网页URL地址的映射,"/"表示对应所有的路径
*
* @return : java.lang.String[]
* @author : zhouhao
* @date : 2019/3/14 6:58
*/
@Override
protected String[] getServletMappings() {
return new String[]{"/"};
}
/**
* 负责初始化ContextLoaderListner上下文
* 包括应用后端的中间件和数据层组件
*
* @return : java.lang.Class<?>[]
* @author : zhouhao
* @date : 2019/3/14 7:07
*/
@Override
protected Class<?>[] getRootConfigClasses() {
return new Class[]{MicroBlogRootConfig.class};
}
/**
* 负责初始化DispatcherServlet上下文
* 包括spring的bean,视图解析器,控制器,处理器映射等
*
* @return : java.lang.Class<?>[]
* @author : zhouhao
* @date : 2019/3/14 7:05
*/
@Override
protected Class<?>[] getServletConfigClasses() {
return new Class[]{MicroBlogWebConfig.class};
}
}
3.2创建两种上下文的配置类
ContextLoaderListner上下文
/**
* ContextLoaderListner上下文的配置类,由于暂时用不到,所以不做介绍
*
* @author : zhouhao
* @date : Created in 2019/3/14 7:07
*/
@Configuration
@ComponentScan(basePackages={"com.zhouhao.springstudy.web"}, excludeFilters={@ComponentScan.Filter(type= FilterType.ANNOTATION, value= EnableWebMvc.class)})
public class MicroBlogRootConfig {
}
DispatcherServlet上下文
/**
* 在Spring中集成Spring MVC
* 集成的根本方法是使此配置类实现 WebMvcConfigurer 接口或者继承 WebMvcConfigurationSupport 类
* WebMvcConfigurerAdapter类已过时,所以不用,WebMvcConfigurerAdapter只是WebMvcConfigurer的一个空实现类
* 使用@EnableWebMvc注解可以引入WebMvcConfigurationSupport配置,因为@EnableWebMvc引入了WebMvcConfigurationSupport的一个子类实现.
* 综上,如果想在spring中集成spring mvc的话,实现WebMvcConfigurer或者启用@EnableWebMvc注解(=继承WebMvcConfigurationSupport).
*
*
* @author : zhouhao
* @date : Created in 2019/3/14 7:04
*/
@Configuration
@EnableWebMvc
@ComponentScan("com.zhouhao.springstudy.controller")
public class MicroBlogWebConfig implements WebMvcConfigurer{
/**
* 装配视图解析器
* 举例:若依据如下配置,控制器返回视图名称为home,则可解析到WEB-INF/views/home.jsp这个视图文件
*
* @return : org.springframework.web.servlet.ViewResolver
* @author : zhouhao
* @date : 2019/3/15 8:08
*/
@Bean
public ViewResolver viewResolver(){
InternalResourceViewResolver resolver = new InternalResourceViewResolver();
//视图的前缀
resolver.setPrefix("WEB-INF/views/");
//视图的后缀
resolver.setSuffix(".jsp");
//将上下文作为属性公开
resolver.setExposeContextBeansAsAttributes(true);
return resolver;
}
}
3.3创建控制器及视图
- 控制器
/**
* 一个简单的控制器,他会将 工程URL/home 路径的请求返回一个只有HOME的视图页面
* 控制器必须使用@Controller注解,其原理是实现了@Componet注解
* 使用@Controller是为了和其他层次更容易区分,比如@Service
* 也可以将@RequestMapping注解用在类上,功能同方法一样
*
* @author : zhouhao
* @date : Created in 2019/3/14 7:43
*/
@Controller
public class HomeController {
/**
* 对URL/home请求返回一个home.jsp的页面
* 使用@RequestMapping注解指定请求路径和控制器方法或者类的映射
*
* @return : java.lang.String
* @author : zhouhao
* @date : 2019/3/15 8:15
*/
@RequestMapping("/home")
public String index(){
return "home";
}
}
- 视图
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Spring MVC 基础</title>
</head>
<body>
<h1>HOME</h1>
</body>
</html>
通过以上代码,将项目生成war包并发布到Tomcat后,就可以使用了.
四.参数传递
在这一小节中,我们将接受前端页面的参数并在另一个页面中展现这些参数已达到介绍参数传递过程的目的.
4.1前端页面传入参数
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>注册</title>
</head>
<body>
<h1>SPRING MVC 参数测试</h1>
<form action = "regist" method="get">
账号:<input type="text" name="name"/>
密码:<input type="text" name="password"/>
<input type = "submit" value = "提交">
</form>
</body>
</html>
4.2控制器
/**
* 简单的模拟了注册
* 这个控制器会接收前端页面的参数,在做了一定的处理后,放入model中,然后前端页面便可以获取相关数据了
* Model类即是MVC中M,表示数据对象
*
* @author : zhouhao
* @date : Created in 2019/3/14 7:43
*/
@Controller
public class HomeController {
/**
* 获取前端传入的参数并写入数据对象中
* 使用@RequestParam可以获取前端传入的参数
* 也可以使用@PathVariable注解获取参数,只不过这样必须在@RequestMapping中设置占位符
*
* @param name 账号
* @param password 密码
* @param model 数据对象,写入数据后,前端页面可以获取写入的数据
* @return : java.lang.String
* @author : zhouhao
* @date : 2019/3/15 20:48
*/
@RequestMapping("/regist")
public String regist( String name, @RequestParam String password, Model model){
model.addAttribute("name",name);
model.addAttribute("password",password);
return "home";
}
}
4.3 接受参数页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<h1>THANKES FOR YOU TO REGIST MY WEB</h1>
你的账号是:${name}<br>
你的密码是:${password}<br>
</body>
</html>
只不过现在大家好像都不用的jsp了,所以这篇文章有点过时哈,主要是用jsp写的简单些.
注:本篇文章由《Spring实战》第五章:构建Spring Web应用程序 总结而来,由于本人非计算机专业出身,许多知识实在是理解不能,总结有相当多的遗漏,乃是我看不懂所致,更别说其中内容肯定有大量的理解错误,万望大家提出批评,我好改正。