1. 返回JSON
加入Jar包:
编写目标方法,使其返回 JSON 对应的对象或集合,并在在方法上添加 @ResponseBody 注解。具体代码如下:
1
2
3
4
5
6
7
8/**
* 返回 JSON 对应的对象或集合
*/
"/testJackson") (
public User testJackson() {
return new User(100, "aa", "abc123", true, 1001.2, new Date(), "shoto@gmail.com");
}@ResponseBody 表示该方法的返回结果直接写入 HTTP response body 中,一般在异步获取数据时使用(也就是AJAX),在使用 @RequestMapping后,返回值通常解析为跳转路径,但是加上 @ResponseBody 后返回结果不会被解析为跳转路径,而是直接写入 HTTP response body 中。 比如异步获取 json 数据,加上 @ResponseBody 后,会直接返回 json 数据。
运行结果如下所示:
JSON数据如下所示:2. 运行原理
在返回JSON的示例中,JSON的返回与HttpMessageConverter<T>接口相关。该接口是 Spring3.0 新添加的一个接口,负责将请求信息转换为一个对象(类型为 T),将对象(类型为 T)输出为响应信息。具体的过程如下图所示:
我们在页面点击请求时,HttpInpyutMessage类会将请求报文转为输入流并由HttpMessageConverter的子类转换器转换为Java对象,然后在由SpringMVC进行处理后会将Java对象通过HttpMessageConverter的子类转换器转换输入流,并生成响应报文。
3. HttpMessageConverter接口
3.1 接口方法
HttpMessageConverter<T>接口定义的方法:
- Boolean canRead(Class<?> clazz,MediaType mediaType): 指定转换器可以读取的对象类型,即转换器是否可将请求信息转换为 clazz 类型的对象,同时指定支持 MIME 类型(text/html,applaiction/json等)
- Boolean canWrite(Class<?> clazz,MediaType mediaType):指定转换器是否可将 clazz 类型的对象写到响应流中,响应流支持的媒体类型在MediaType 中定义。
- LIst<MediaType> getSupportMediaTypes():该转换器支持的媒体类型。
- T read(Class<? extends T> clazz,HttpInputMessage inputMessage):将请求信息流转换为 T 类型的对象。
- void write(T t,MediaType contnetType,HttpOutputMessgae outputMessage):将T类型的对象写到响应流中,同时指定相应的媒体类型为 contentType。
3.2 接口实现类
HttpMessageConverter有如下的实现类。
DispatcherServlet 默认装配RequestMappingHandlerAdapter ,而RequestMappingHandlerAdapter 默认装配如下HttpMessageConverter:
在加入 jackson jar 包后, RequestMappingHandlerAdapter装配的 HttpMessageConverter 如下:
上述返回JSON的示例,其底层使用的则是HttpMessageConverter的子类MappingJackson2HttpMessageConverter转化器处理的。
4. 模拟文件上传
1.在请求页面编写如下代码:
1 | <!-- 模拟文件上传 --> |
2.在控制器类中编写如下目标方法,对请求进行处理:
1 | /** |
注意: @RequestBody是作用在形参列表上,用于将前台发送过来固定格式的数据通过系统默认配置的 HttpMessageConverter进行解析(这里是HttpMessageConverter的子类StringHttpMessageConverter),然后封装到入参requestBody上。
3.需要在MVC文件中配置<mvc:annotation-driven /> **,<mvc:annotation-driven /> 会自动注册RequestMappingHandlerMapping、RequestMappingHandlerAdapter** 与ExceptionHandlerExceptionResolver 三个bean。正如前面所提到的RequestMappingHandlerAdapter默认装配了HttpMessageConverter。
4.当在页面选择要上传的文件并输入描述文本并点击提交后,服务器端会打印如下数据并将”Success!”文本返回给客户端并显示在页面上。
使用 HttpMessageConverter<T> 将请求信息转化并绑定到处理方法的入参中或将响应结果转为对应类型的响应信息,Spring 提供了两种途径:
- @RequestBody / @ResponseBody 对处理方法进行标注。(上面示例使用的)
- 使用 HttpEntity<T> / ResponseEntity<T> 作为处理方法的入参或返回值。(下面的文件下载示例)
注意:@RequestBody 和 @ResponseBody 不一定要成对出现。
5. 文件下载
1.首先需要在请求页面编写文件下载请求链接代码:
1 | <!-- 模拟文件下载 --> |
2.接着在控制器类中编写如下目标方法,对请求进行处理:
1 | /** |
3.在MVC文件中配置<mvc:annotation-driven />后即可点击链接进行文件的下载了。
提示:当控制器处理方法使用到 @RequestBody/@ResponseBody 或HttpEntity<T>/ResponseEntity<T> 时, Spring 首先根据请求头或响应头的Accept 属性选择匹配的 HttpMessageConverter, 进而根据参数类型或泛型类型的过滤得到匹配的HttpMessageConverter, 若找不到可用的HttpMessageConverter 将报错。