Spring MVC执行流程已经是JAVA面试中老生常谈的问题,相信各位小伙伴也是信手拈来。今天咱们来谈谈另外一个面试中必会必知的问题: @RestController
和@Controller
的区别?html
基于注解的MVC框架简化了建立RESTful web服务的过程。传统的Spring MVC控制器和RESTful web服务控制器之间的关键区别是HTTP响应体的建立方式。传统的MVC控制器依赖于视图技术,基于REST的web服务控制器仅返回对象,而对象数据直接以JSON/XML的形式写入HTTP响应。java
支持如下方式来建立 REST 资源:web
在传统的工做流中,ModelAndView对象是从控制器转发到客户机的,经过在方法上加@ResponseBody,Spring直接从控制器返回数据,而不须要查找视图。从4.0版本开始,随着@RestController注释的引入,这个过程获得了进一步简化。下面将解释每种方法。面试
@Controller用于标记在一个类上,使用它标记的类就是一个Spring MVC Controller对象,分发处理器会扫描使用该注解的类的方法,并检测该方法是否使用了@RequestMapping注解。spring
@ResponseBody注解用于将Controller的方法返回的对象,经过适当的HttpMessageConverter转换为指定格式后,写入到Response对象的body数据区,一般用来返回 JSON 或者 XML 数据,返回 JSON 数据的状况比较多。json
Spring有一个在后台注册的HttpMessageConverters列表。HTTPMessageConverter的职责是根据预约义的mime类型将请求主体转换为特定的类,而后再转换回响应主体。每当发出的请求点击@ResponseBody时,Spring循环遍历全部已注册的HttpMessageConverters,寻找第一个符合给定mime类型和类的请求,而后将其用于实际的转换。
建立实体类:后端
package com.laocaicai.week1.entity; import javax.xml.bind.annotation.XmlRootElement; @XmlRootElement(name = "Dog") public class DogEntity { String name; String breed; public String getName() { return name; } public void setName(String name) { this.name = name; } public String getBreed() { return breed; } public void setBreed(String breed) { this.breed = breed; } public DogEntity() { } }
建立Controller:api
package com.laocaicai.week1.controller; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.ResponseBody; import com.laocaicai.week1.entity.DogEntity; @Controller @RequestMapping("dogs") public class DogController { DogEntity dog = new DogEntity(); @RequestMapping(value = "/{name}", method = RequestMethod.GET, produces = "application/json") public @ResponseBody DogEntity getDogInJSON(@PathVariable String name) { dog.setName(name); dog.setBreed("中国细犬"); return dog; } @RequestMapping(value = "/{name}.xml", method = RequestMethod.GET, produces = "application/xml") public @ResponseBody DogEntity getDogInXML(@PathVariable String name) { dog.setName(name); dog.setBreed("中国细犬"); return dog; } }
在Spring配置文件中添加
和
标签,前者用于激活注释并扫描包以查找和注册应用程序上下文中的bean,后者增长了对读取和写入JSON/XML的支持(对于返回JSON格式数据,须要导入jackson-databind依赖;对于XML格式,须要导入jaxb-api-osgi依赖)
使用URL:http://localhost:8687/week_1/dogs/哮天犬
,输出JSON:服务器
使用URL:http://localhost:8687/week_1/dogs/哮天犬.xml
,输出XML:网络
Spring 4.0引入了@RestController
,@RestController
注解是一种快捷方式,它所声明的控制器在返回响应时,就如同使用了@ResponseBody
注解同样。它会告诉Spring 将返回类型序列化为合适的格式,默认状况下为JSON 格式。经过用@RestController
注释控制器类,您再也不须要向全部请求映射方法添加@ResponseBody
。
package org.springframework.web.bind.annotation; import java.lang.annotation.Documented; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; import org.springframework.stereotype.Controller; @Target({ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Documented @Controller @ResponseBody public @interface RestController { String value() default ""; }
要在咱们的示例中使用@RestController
,咱们所须要作的就是将@Controller
修改成@RestController
并从每一个方法中删除@ResponseBody
。生成的类应该以下所示
package com.laocaicai.week1.controller; import com.laocaicai.week1.entity.DogEntity; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RestController; @RestController @RequestMapping("2dogs") public class DogRestController { DogEntity dog = new DogEntity(); @RequestMapping(value = "/{name}", method = RequestMethod.GET, produces = "application/json") public DogEntity getDogInJSON(@PathVariable String name) { dog.setName(name); dog.setBreed("中国细犬"); return dog; } @RequestMapping(value = "/{name}.xml", method = RequestMethod.GET, produces = "application/xml") public DogEntity getgetDogInXMLInXML(@PathVariable String name) { dog.setName(name); dog.setBreed("中国细犬"); return dog; } }
注意,咱们再也不须要将
@ResponseBody
添加到请求映射方法中,在进行更改以后,再次在服务器上运行应用程序会产生与以前相同的输出。
经过本篇的介绍,小伙伴们会发现使用@RestController
很是简单,是从Spring v4.0开始建立MVC RESTful web服务的首选方法。@RestController
(Spring4+)至关于@Controller
+ @ResponseBody
,返回json或者xml格式数据;若是在控制器类上使用@RestController
来代替@Controller
的话,Spring将会为该控制器的全部处理方法应用消息转换功能,咱们没必要为每一个方法都添加@ResponseBody
了。
参考资料:
本文做者:Srivatsan Sundararajan, 翻译:laocaicaicai
原文连接: https://dzone.com/articles/sp...
译文首发: http://blog.didispace.com/tr-...
本文有spring4all技术翻译组完成,更多国外前沿知识和干货好文,欢迎关注公众号:后端面试那些事儿。