SpringMvc简单介绍
Spring MVC是一个基于MVC(Model view Controller)模式的WEB框架,它解决WEB开发中常见的问题(参数接收、文件上传、表单验证、国际化、等等),使用非常简单,SpringMvc作为Spring中的一个模块,可以与Spring无缝集成。
SpringMvc以Spring框架为核心,为应用程序中的Web层(表现层)提出的一套优秀的解决方案。
spring-webmvc-4.1.2.RELEASE.jar SpringMVC的jar文件。
spring-web-4.1.2.RELEASE.jar Spring对Web项目运行的支持。
1.1.1. MVC框架思想-核心控制器(前端控制器)
顾名思义核心控制器用于Web层核心功能的处理以及在所有控制器执行的。所有的WebMvc框架都采用了这种方式。
在Struts2中我们使用的是StrutsPrepareAndExecuteFilter作为核心控制器,在SpringMVC中使用的是DispatcherServlet为核心控制器.
DispatcherServlet核心控制器会拦截匹配的请求,把拦截下来的请求,依据相应的规则分发到目标Controller来处理。
创建项目确保Spring可用
导入jar包
com.springsource.org.apache.commons.logging-1.1.1.jar(版本三)
spring-beans-4.1.2.RELEASE.jar
spring-context-4.1.2.RELEASE.jar
spring-core-4.1.2.RELEASE.jar
spring-expression-4.1.2.RELEASE.jar
spring aop、orm、jdbc、tx相关jar根据项目使用自行添加;
准备配置文件配置 applicationContext.xml
1.1.1. 加入相关Spring mvc相关jar包。
spring-web-4.1.2.RELEASE.jar spring 对web项目的支持。
spring-webmvc-4.1.2.RELEASE.jar SpringMVC核心包。
配置核心控制器
Webmvc框架的心脏就是核心控制器,负责所有请求的公共功能,然后再分发给具体的控制器(我们编写的控制器),完成业务逻辑,响应视图。
配置:
<!-- springmvc的核心控制器,拦截所有的请求,负责分发到对应的Controller中的方法 -->
<servlet>
<servlet-name>springmvc</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>springmvc</servlet-name>
<!-- / 拦截所有的请求,拦截Controller的地址
/*拦截所有的请求,会拦截*.jsp类似请求
*.do *.action 拦截.do .action结尾的请求
-->
<url-pattern>/</url-pattern>
</servlet-mapping>
1.1.1. 准备SpringMVC映射文件
规范要求 |
说明 |
实现Controller接口或子接口。 注意:子接口很多已经过时了。 |
核心方法为handleRequest(req,resp),处理用户请求 |
普通的类(常用的哦) |
使用一个普通的类作为我们的控制器,每一个方法就是一个处理器,这种方式需要配合注解标签才能使用。 |
SpringMVC是Spring的一个模块,它的配置文件就是Spring的配置差不多,复制一份applicationContext.xml修改为applicationContext-mvc.xml。
SpringMVC中的控制器有一定规范,要么实现接口,要么使用POJO对象与注解配合使用。
handleRequest方法的两个参数与我们以前的servlet中service方法一样,request和response对象,我们可以使用这个两个对象完成一次请求的所有工作,比如你可以使用request接受参数,或者使用response重定向等等,注意方法除了返回值以外还有一个返回值ModelAndView。
1 SpringMVC的控制器Controller,和Struts2中的action一样。 2 */ 3 public class HelloController implements Controller{ 4 /** 5 * 处理请求方法。 6 * request:封装了请求对象; 7 * response:封装了这个请求的响应对象 8 * 返回一个ModelAndView对象: 9 * Model:模型 ,封装我们的数据 10 * View:视图,返回的jsp页面 11 * ModelAndView对象是springmvc控制器中的一个对象,用于封装数据模型和返回页面视图 12 */ 13 public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { 14 //获取请求参数 15 System.out.println("HelloController...."); 16 //调用service进行业务逻辑处理 17 System.out.println("HelloController 已经进行了业务逻辑处理"); 18 //返回jsp页面视图 19 ModelAndView mAndView = new ModelAndView(); 20 mAndView.setViewName("/01jsp/01_hello.jsp"); 21 return mAndView; 22 } 23 24 }
1)配置
SpringMVC是基于Spring,Spring中的核心就是Ioc容器,而Ioc容器中最重要的成员就是<bean>,SpringMVC中的控制器也是一个一个<bean>。使用name属性:表示这个Controller的访问路径
1 <!-- springmvc的核心控制器,拦截所有的请求,负责分发到对应的Controller中的方法 --> 2 <servlet> 3 <servlet-name>springmvc</servlet-name> 4 <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> 5 6 <!-- 启动springmvc的核心控制器的时候,就初始化加载springmvc的配置文件 --> 7 <init-param> 8 <param-name>contextConfigLocation</param-name> 9 <param-value>classpath:applicationContext-mvc.xml</param-value> 10 </init-param> 11 <!-- DispatcherServlet启动比较耗时,在启动加载文件的时候就进行加载 --> 12 <load-on-startup>1</load-on-startup> 13 </servlet> 14 <servlet-mapping> 15 <servlet-name>springmvc</servlet-name> 16 <!-- / 拦截所有的请求 17 /*拦截所有的请求 18 *.do *.action 拦截.do .action结尾的请求 19 --> 20 <url-pattern>/</url-pattern> 21 </servlet-mapping>
1.1.1. 入门小结:
①:创建一个动态工程,配置tomcat和编译路径
②:Spring的环境准备:导入基本的5个jar包和一个applicationContext.xml配置文件
③:Springmvc的环境的准备:
spring-web-4.1.2.RELEASE.jar spring 对web项目的支持。
spring-webmvc-4.1.2.RELEASE.jar SpringMVC核心包。
Web ,webmvc的两个jar包;
applicationContext-mvc.xml的配置文件
Web.xml:配置核心控制器:DispatcherServlet
④:Controller的准备:写一个类,实现Controller接口,覆写方法,返回一个视图jsp页面
同时应把这个Controller配置到applicationContext-mvc.xml,变成一个bean,name就是访问的路径
⑤:准备一个jsp视图
⑥:启动测试
1.1. 静态资源文件访问问题
由于我们配置的拦截器规则是”/”,”/”就代表默认控制器,tomcat本身自带有一个默认控制器,这个控制器用于处理静态资源请求,如果我们配置默认控制器,那么tomcat的默认控制器就不生效,导致静态资源无法访问。
解决办法:springmvc开启静态资源控制器。(适应于HTML页面视图)
<mvc:default-servlet-handler/>(release :释放)
1.1. 控制器三种实现方式
① 实现Controller接口
② 实现HttpRequestHandler接口
③ 普通类(pojo)和注解 @RequestMapping
public class ImplController implements Controller { @Override public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception { System.out.println("我implements Controller进来了。。。。。"); return null; } }
配置:将这个Controller交给spring管理,并使用name属性配置映射关系(就是这个Controller的访问路径)
1 public class HandlerController implements HttpRequestHandler { 2 @Override 3 public void handleRequest(HttpServletRequest arg0, HttpServletResponse arg1) throws ServletException, IOException { 4 System.out.println("进来了implements HttpRequestHandler。。。。"); 5 } 6 }
配置:将这个Controller交给spring管理,并使用name属性配置映射关系(就是这个Controller的访问路径)。
缺点:只能有一个方法,不能实现多个地址的映射
普通类(pojo)和注解
1 @RequestMapping("/user") 2 public class UserController { 3 /** 4 * 一个Index方法 5 * @return 6 */ 7 @RequestMapping("/index")//访问地址:/user/index 8 public String index(){ 9 System.out.println("我是一个index。。。。。。。。。。。。"); 10 return ""; 11 } 12 /** 13 * 一个list方法 14 * @return 15 */ 16 @RequestMapping("/list")//访问地址:/user/list 17 public void list(){ 18 System.out.println("我是一个list。。。。。。。。。。。。"); 19 } 20 21 }
配置:@RequestMapping配置类上和方法上
(只需要配置让spring管理这个bean即可,无需指定路径,因为方法上面通过@RequestMapping指定)
<!-- Controller的实现:方式一:定义一个普通的java类-->
<bean class="cn.itsource.springmvc._02_controller.UserController"> </bean>
需要开启SprigMVC注解支持:
<!-- 开启Springmvc的注解驱动:扫描@RequestMapping等注解 -->
<mvc:annotation-driven/>
总结
Springmvc中所有控制器,其实在spring中就是一个一个bean。
spring管理bean的方法分为两种,第一种是xml,,第二种是注解。
Springmvc中控制器建议使用注解方式,是官方推荐的,也外面公司使用方式。
控制器注解实现方式
1 /** 2 * 3 * Controller的实现: 4 * 全注解: 5 * @Controller的配置:相当于一起的xml中的bean配置 6 * @RequestMapping("/department")配置:bean的name的配置 7 * 8 * 注意:需要配置spring注解的扫描路径 9 * <!-- 开启Spring的注解的扫描:@Controller @Service @Repository @Component等 --> 10 <context:component-scan base-package="cn.itsource.springmvc"/> 11 * 开启springmvc注解的扫描: 12 * <!-- 开启Springmvc的注解驱动:扫描@RequestMapping等注解 --> 13 <mvc:annotation-driven/> 14 * @author admin 15 * 16 */ 17 @Controller//将这个类,交给Spring管理,需要开启注解的扫描路径 18 @RequestMapping("/department") 19 public class DepartmentController { 20 21 @RequestMapping("/index") 22 public void index(){ 23 System.out.println("index..........."); 24 } 25 @RequestMapping("/del") 26 public void del(){ 27 System.out.println("del......."); 28 } 29 30 }
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans xmlns="http://www.springframework.org/schema/beans" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 4 xmlns:mvc="http://www.springframework.org/schema/mvc" 5 xmlns:context="http://www.springframework.org/schema/context" 6 xsi:schemaLocation=" 7 http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd 8 http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd 9 http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> 10 <!-- 开启springMVC的默认处理控制器 :处理静态资源 --> 11 <mvc:default-servlet-handler /> 12 <!-- 开启spring对mvc注解支持功能,能识别@RequestMapping等注解 --> 13 <mvc:annotation-driven /> 14 <!-- 开启spring对注解配置支持,默认这个配置是存在的,但是为了规范起见,还是写上:@Controller:controller @Service:service @Repository:dao @Component :其他 --> 15 <context:annotation-config /> 16 <!-- 组件扫描路径 --> 17 <context:component-scan base-package="cn.itsource.springmvc" /> 18 </beans>
- 控制器常用操作
和struts2一样,控制器除了我们前面重点讲解处理请求并返回视图以外,还需要一些事情,比如接收页面传递参数、绑定数据到页面、返回json数据、文件上传、文件下载等
参数接收
配置请求编码过滤器
参数接收,首先要考虑乱码问题。然而springmvc框架本身没有处理请求编码,但是spring框架为我们提供了一个请求编码过滤器,我们在web.xml配置一个请求编码过滤器。
参数接收
配置请求编码过滤器
参数接收,首先要考虑乱码问题。然而springmvc框架本身没有处理请求编码,但是spring框架为我们提供了一个请求编码过滤器,我们在web.xml配置一个请求编码过滤器。
1 <!-- 支持UTF-8编码 --> 2 <filter> 3 <filter-name>characterEncoding</filter-name> 4 <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class> 5 <init-param> 6 <param-name>encoding</param-name> 7 <param-value>UTF-8</param-value> 8 </init-param> 9 </filter> 10 <filter-mapping> 11 <filter-name>characterEncoding</filter-name> 12 <url-pattern>/*</url-pattern> 13 </filter-mapping>
1.1.1. 参数接收方式
① 通过控制器的执行方法参数来接收普通参数
② 通过Domain模型对象来接收
③ 通过传统的HttpServletRequest接收
④ 通过url中的参数接收(restfull风格) @PathVariable("id")转换
1.通过控制器的执行方法参数来接收普通参数
2.通过模型对象来接收(常用)
3.接收url中参数的请求,接收用户请求参数值
4.通过传统的HttpServletRequest接收
1.1. 数据传递
就是Controller往前台(页面)传递数据
① 通过ModelAndView对象传递
② 通过Model对象传递
③ 通过request对象传递
④ 通过返回值传递
①通过ModelAndView对象传递
/** * 通过一个ModelAndView对象来传递参数 * @return */ @RequestMapping("/demo1") public ModelAndView demo1() { ModelAndView modelAndView = new ModelAndView(); modelAndView.addObject("msg", "大家好啊"); modelAndView.setViewName("/03jsp_contrlloerParamsToView/controllerToView.jsp"); User user=new User("zs", 13, 11L); modelAndView.addObject(user); return modelAndView;
通过Model对象进行数据传递
1 /** 2 * 通过形参中的一个Model对象来传递参数。 3 * springMvc自动创建模型对象传入到方法中,我们只需要在这个模型上添加数据就以。 4 * @param model 封装数据的模型对象 5 * @return 返回值是一个字符串,表示是返回的视图view 6 */ 7 @RequestMapping("/demo2") 8 public String demo2(Model model) { 9 model.addAttribute("msg", "一点都不好"); 10 return "/03jsp_contrlloerParamsToView/controllerToView.jsp"; 11 }
3.通过request对象进行数据传递
1 /** 2 * 使用原始的在request上添加属性 3 * @param request 4 * @return 返回值是一个字符串,表示返回的视图view 5 */ 6 @RequestMapping("/demo3") 7 public String demo3(HttpServletRequest request) { 8 request.setAttribute("msg", "我是另一种方式了哦"); 9 return "/03jsp_contrlloerParamsToView/controllerToView.jsp"; 10 }
4.通过返回值传递数据
1 /** 2 * 返回一个自定义对象:user。 3 * 返回值就是模型数据。 4 * springmvc会自动创建一个ModelAndView对象,mav,将uer添加到mav中:mav.addObject("user",user); 5 * 并且返回视图路径就是访问路径:mav.setViewName("/demo4.jsp"); 6 * @return 7 */ 8 @RequestMapping("/demo4") 9 public User demo4() { 10 User user=new User("2",34,34L); 11 return user; 12 } 13 14 yi
SpringMcv返回JSON
要把Java对象转换为Json,需要框架支持
Jackson:http://jackson.codehaus.org/ springMVC
JSON-lib:http://json-lib.sourceforge.net/ struts2
Gson:http://code.google.com/p/google-gson/
FastJson阿里开源
加入jackson json工具包
1 出现406状态异常 2 3 加入json jar包 jackson 4 5 处理如果有乱码的问题:springContext-mvc.xml 6 7 <!-- 为了处理返回的JSON数据的编码,设置为UTF-8 --> 8 9 <bean id="mappingJacksonHttpMessageConverter" class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter"> 10 11 <property name="supportedMediaTypes"> 12 13 <list> 14 15 <value>text/html;charset=UTF-8</value> 16 17 </list> 18 19 </property> 20 21 </bean> 22 23
对日期格式的特殊处理(后面要用到的知识)
从后台向前台:
默认返回的日期格式为时间戳,而在前台我们希望显示出指定规则的日期字符串。如:
默认:{"name":"小明哥","birthdate":121223223}
期望: {"name":"小明哥","birthdate":"2025-12-12 14:12:12"}
在日期get属性,字段上,添加一个格式化注解
@JsonFormat(pattern="yyyy-MM-dd HH:mm:ss",timezone="GMT+8")
从前台向后台:
在后台模型的setter方法上,添加注解
@DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
访问地址:localhost:8080/jsonV587?birthDay=2017-06-13 16:50:53
文件上传/下载
@RequestMapping(value = "/upload", method = RequestMethod.GET)
//映射关系的匹配有很多参数可以选:value:表示请求的路径,可以默认不写
//method:表示这个方法的请求方式:get或者post。当明显指定了访问方式后:就必须对应的方式才能进入。
文件上传
由于springmvc自己没有实现文件上传,它使用是apache.commons.fileupload ,需要导入以下的包
com.springsource.org.apache.commons.fileupload-1.2.0.jar
com.springsource.org.apache.commons.io-1.4.0.jar
1 ** 2 * 文件的上传: 3 * springmvc没有自己的上传方法。需要使用Apache.commons.fileupload 4 * com.springsource.org.apache.commons.fileupload-1.2.0.jar 5 com.springsource.org.apache.commons.io-1.4.0.jar 6 */ 7 @Controller 8 public class UploadController { 9 /** 10 * 显示指定这个方法是get请求 11 * 前台通过get请求访问这个路径,返回一个jsp文件上传页面 12 * @return 13 */ 14 @RequestMapping(value = "/upload", method = RequestMethod.GET) 15 public String uploadFileGet() { 16 System.out.println("get...."); 17 return "/WEB-INF/05_upload_jsp/upload.jsp"; 18 } 19 20 /** 21 * 文件上传实现方法: 22 * ①:获取上传文件的原始文件名 23 * ②:随机生产一个UUID作为上传后的文件名,放置文件名重复 24 * ③:获取文件名后缀,结合①②生产保存的文件名 25 * ④:获取需要保存的文件的服务器路径 26 * ⑤:使用file流写文件 27 * ⑥:完成文件保存 28 * @param name 注册名 29 * @param img 上传的文件图片对象 30 * @param request request请求 31 * @return 32 * @throws FileNotFoundException 33 * @throws IOException 34 */ 35 @RequestMapping(value = "/upload", method = RequestMethod.POST) 36 public String uploadFilePost(String name,MultipartFile img,HttpServletRequest request) throws FileNotFoundException, IOException { 37 //获取上传文件的原始文件名 38 String oFileName=img.getOriginalFilename(); 39 //获取文件名的后缀 40 String fNameSuffix= FilenameUtils.getExtension(oFileName); 41 //生产一个随机的文件名 42 String uuidName = UUID.randomUUID().toString(); 43 String fileName=uuidName+"."+fNameSuffix; 44 //获取保存文件的路径 45 String fileDir = request.getServletContext().getRealPath("/uploads"); 46 //使用file流写文件 47 File file=new File(fileDir,fileName); 48 if(!file.getParentFile().exists()){ 49 file.getParentFile().mkdirs(); 50 } 51 IOUtils.copy(img.getInputStream(),new FileOutputStream(file)); 52 return "/WEB-INF/05_upload_jsp/upload.jsp"; 53 } 54 }
1 <!—文件上传:必须写:enctype="multipart/form-data"—> 2 <form action="/upload" method="post" enctype="multipart/form-data"> 3 用户名:<input type="text" name="name"/><br/> 4 头像:<input type="file" name="img"/><br/> 5 <input type="submit" value="提交"/> 6 </form>
1 <!-- 配置文件上传解析器:id="multipartResolver",这个id不能乱写 2 设置一个maxUploadSize属性,就是上传文件的大小 3 --> 4 <bean id="multipartResolver" 5 class="org.springframework.web.multipart.commons.CommonsMultipartResolver"> 6 <property name="maxUploadSize"> 7 <value>2000000000</value> 8 </property> 9 </bean>
1 6.4.2.文件下载(还是原生Servlet方式) 2 /** 3 * 文件下载:原生的servlet 4 * ①:设置response的头信息 5 * ②:获取文件输出流 6 * ③:获取需要下载的文件输入流 7 * ④:文件流的拷贝 8 * @param response 9 * @param request 10 * @throws IOException 11 */ 12 @RequestMapping("/downLoad") 13 public void downLoad(HttpServletResponse response,HttpServletRequest request) throws IOException{ 14 //设置响应response的头信息和文件名 15 String filename="mm.jpg"; 16 response.setHeader("Content-Disposition", "attachment; filename="+filename+""); 17 //获取文件输出流 18 OutputStream out=response.getOutputStream(); 19 20 //获取下载文件的地址 21 String filePath =request.getServletContext().getRealPath("/upload"); 22 String fileAllPath=filePath+"/mm.jpg"; 23 //获取文件输入流 24 FileInputStream in=new FileInputStream(fileAllPath); 25 //文件流拷贝 26 IOUtils.copy(in, out); 27 }
- 执行流程
流程图
控制器=处理器(Handler)
1. 用户向服务器发送请求,请求被SpringMVC前端控制DispatcherServlet捕获;
2. DispatcherServlet通过调用HandlerMapping(处理器映射管理对象)获得该请求对应的Handler对象(包括控制器以及Handler对象对应的拦截器)
HandlerExecutionChain对象(包含:控制器+2个拦截器);
3. DispatcherServlet 根据获得的Handler,选择一个合适(管理Controller的方式:有xml方式和注解方式)的HandlerAdapter。(附注:如果成功获得HandlerAdapter后,此时将开始执行拦截器的preHandler(...)方法)
4. 提取Request中的模型数据,填充Handler入参,开始执行Handler(Controller)。 在填充Handler的入参过程中,根据你的配置,Spring将帮你做一些额外的工作:
HttpMessageConveter: 将请求消息(如Json、xml等数据)转换成一个对象,将对象转换为指定的响应信息
数据转换:对请求消息进行数据转换。如String转换成Integer、Double等
数据格式化:对请求消息进行数据格式化。 如将字符串转换成格式化数字或格式化日期等
数据验证: 验证数据的有效性(长度、格式等),验证结果存储到BindingResult或Error中
5.Handler执行完成后,向DispatcherServlet 返回一个ModelAndView对象;
6.根据返回的ModelAndView,选择一个适合的ViewResolver(必须是已经注册到Spring容器中的ViewResolver)返回给DispatcherServlet ;
7. ViewResolver 结合Model和View,来渲染视图(Model+View合成)
8. 将渲染结果返回给客户端。
1.1. 简易描述(面试用)
1. 客户端请求提交到DispatcherServlet
2. 由DispatcherServlet控制器查询一个或多个HandlerMapping,找到处理请求的Controller。
3. 通过Handler匹配一个合适HandlerAdapter ,通过HandlerAdapter 调用对象Controller方法。
4. Controller调用业务逻辑处理后,返回ModelAndView
5. DispatcherServlet查询一个或多个ViewResoler视图解析器,找到ModelAndView指定的视图。
6. 视图负责将结果显示到客户端。
Converter 变换器;
DataBinder 数据连接器
- 核心对象
1.1. HandlerMapping 处理器映射管理对象
HanderMapping 处理器映射管理对象:
作用:根据不同的请求选择最合适的处理器(自己编写的控制器),处理器映射管理对象可以配置多个,谁最先匹配就执行谁。
SpringMVC默认:/org/springframework/web/servlet/DispatcherServlet.properties
Java程序员必会springmvc框架三大组件工作流程与struts2框架区别
SpringMVC围绕着Servlet进行开发Web,代码的实现上同时也依赖Spring开发,不然也不会叫做SpringMVC,本文着重强调的重点在于SpringMVC的工作流程,并不设计具体代码开发,所以并不要求掌握Spring的知识。
SpringMVC的处理流程为,用户访问的地址被DispathcherServlet的url-pattern匹配到后,
DispathcherServlet会在内部从Spring容器中拿到HandlerMapping对象
该对象内部有一个LinkedHashMap,
在Spring容器初始化时,我们在@requestMapping中填写的url路径被存入这个map中作为Key值,一旦用户发送请求DispathcherServlet通过RequestMappingHandlerMapping中获取请求地址然后迭代这个Map寻求匹配的Key值,也就是我们在@requestMapping中写的路径,如果匹配成功就能够获取到我们的controller处理器的全包名和方法名
这时候DispathcherServlet创建一个HandlerAdapter接口下的子类对象执行从map中获取的方法,也就是我们在controller编写的方法
,返回一个ModelAndView对象,DispathcherServlet又从SpringWeb容器中拿到ViewResolver对象,
ViewResolver对象能够将上面方法的返回值ModelAndView中的ViewName解析出,该ViewName就是我们写的/WebINFO/下的JSP页面的这段字符串,ViewResolver通过该地址将整个jsp页面解析成View对象,将对象返回给DispathcherServlet。然后调用processDispatchResult方法对页面进行渲染,也就是将controller处理后的model数据与ViewResolver返回的view对象进行渲染,就是将他们重新组合成了一个处理后的jsp页面对象返回给浏览器。
以上就是DispathcherServlet的工作流程了,可以说整个流程都是在DispathcherServlet的方法内部进行的,SpringMVC框架的三大组件处理器映射器,处理器适配器,和视图解析器都是由DispathcherServlet从Spring的webapp容器中获取的。非常有意思的设计,下面让我们来看看这三大组件都有哪些配置。
这是一个property文件,位于springmvc框架的依赖jar包下。红色框框标识出都是DispathcherServlet中的对象属性。
LocaleResolver 是一个国际化的解析器,它使用i18n国际化的标准能够为不同国家的展示不同语言的页面。ThemeResolver 用于防止注入式攻击。HandlerMapping 配置默认使用的requestMapping映射器。HandlerAdapter 配置默认使用的requestMapping适配器。HandlerExceptionResolver 异常解析器RequestToViewNameTranslator 请求jsp路径时的事务管理器ViewResolver 配置默认使用的r视图解析器。
等等等等,同类型Struts2框架有22种拦截器分别对应不同的功能,因为web层与用户进行直接交互所以功能相比service和dao都要复杂些。我们也可以在xml文件中自定义每个功能所使用的类。
我们可以在xml文件中手动指定想要使用的组件类型,只需要将该类注册到spring容器中即可,不需要配置其他东西。
该标签用于启动mvc的注解驱动,有这个标签相当于我们默认使用注解来表示请求路径,就是@requestMapping注解,默认在上面property文件中是启用的,所以这个标签可以不写。
InternalResourceViewResolver则是个很有用的功能,他能够为我们controller中set的ViewName补充前后缀。见下图
图中代码本是配置jsp页面的路径的,有了上面的配置后我们可以省略所以jsp页面共同的前后缀部分,最后拼接后的路径为/WIN-INF/asas.jsp。
核心对象
1.1. HandlerMapping 处理器映射管理对象
HanderMapping 处理器映射管理对象:
作用:根据不同的请求选择最合适的处理器(自己编写的控制器),处理器映射管理对象可以配置多个,谁最先匹配就执行谁。
SpringMVC默认:/org/springframework/web/servlet/DispatcherServlet.properties
BeanNameUrlHandlerMapping |
处理通过<bean name="/xxx">注册的控制器。控制器需要实现Controller接口。 |
DefaultAnnotationHandlerMapping |
处理通过注解@Controller(类标签) 及@RequestMapping(方法标签) 注册的控制器。该处理器映射管理对象已经在Spring 3.2 版本过时,替换为RequestMappingHandlerMapping。 |
spring 中提供的内置处理器映射:
简单url处理器映射
org.springframework.web.servlet.handler.SimpleUrlHandlerMapping
(了解即可,现在已经基本不用了)
<bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
<property name="mappings">
<value>
/helloworld(url 地址)=helloworldController(bean id)
/helloworld002=helloworldController
</value>
</property>
</bean>
org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping 采用注解方式请求处理器映射。
使用<mvc:annotation-driven/>开启新的映射处理器。
HandlerAdapter 处理器适配
作用:支持多种类型的处理器,如何来执行"处理器(控制器)"; 如何执行我们的控制器。
Spring默认处理器适配:
org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter 处理实现了HttpRequestHandler接口对应的控制器
org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter 处理实现了Controlle接口对应的控制器。
使用<mvc:annotation-driven/>开启新的处理器适配
org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter 处理通过注解方式的控制器。 3.2中已过时,替换为org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter
1.1. ViewResolver 视图解析器 (struts2视图类型类似)
作用:根据不同的视图,响应不同的结果,比如普通的jsp或json.
SpringMVC默认:
InternalResourceViewResolver : 支持默认视图,采用forward,redirect。
视图名规则
不写前缀默认为"转发"
视图名字符串前缀:
forward:/xxx.jsp 采用转发。
redirect:/xxx.jsp 采用重定向。
new ModelAndView("forward:/userList");
new ModelAndView("redirect:/user");
注册(替换)视图解析器
设置视图路径的前后缀,该配置可以让我们写视图路径的时候更简单。
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsps/" />
<property name="suffix" value=".jsp" />
</bean>
路径简写:
注意事项:"forward:"与"redirect:"前缀问题
页面不在前缀路径中的情况(或者页面路径不是以.jsp为后缀)
课程总结
重点
Controller的实现方式:全注解
参数的接收: 在形参中使用java内置的类型接收(常用)
在形参中使用domain接收(常用)
视图返回:返回一个String的字符串
参数的返回:json的返回