有时在Spring MVC中返回JSON格式的response的时候会使用@ResponseBody注解,不过在处理java8中时间的时候会很麻烦,一般我们使用的HTTPMessageConverter是MappingJackson2HttpMessageConverter,它默认返回的时间格式是这种:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
"startDate" : {
"year" : 2010,
"month" : "JANUARY" ,
"dayOfMonth" : 1,
"dayOfWeek" : "FRIDAY" ,
"dayOfYear" : 1,
"monthValue" : 1,
"hour" : 2,
"minute" : 2,
"second" : 0,
"nano" : 0,
"chronology" : {
"id" : "ISO" ,
"calendarType" : "iso8601"
}
}
|
但是我们不会返回这种给前端使用,针对LocalDate想要返回的格式是2016-11-26,而LocalDateTime想要返回的格式是2016-11-26 21:04:34这样的数据。通过项目研究并查阅相关资料,这里介绍下个人研究中实现的两种方式。
解决方法一:
若是maven项目,在pom中引入下面的jar包:
1
2
3
4
5
|
< dependency >
< groupId >com.fasterxml.jackson.datatype</ groupId >
< artifactId >jackson-datatype-jsr310</ artifactId >
< version >2.8.5</ version >
</ dependency >
|
然后在你想要JSON化的POJO字段的get函数上加上一个@JsonSerializer注解,如下
1
2
3
4
5
6
7
8
9
10
11
|
import com.fasterxml.jackson.annotation.JsonFormat;
@JsonFormat (shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd" )
public LocalDateTime getBirthday() {
return this .loginTime;
}
@JsonFormat (shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd HH:mm:ss" )
public LocalDateTime getLastLoginTime() {
return this .loginTime;
}
|
这种方式的优点是可以针对具体域类型设置不同显示方式,然而优点也是缺点,因为每个日期属性都要手动添加,实际中日期属性又是普遍必备,并且需要额外引入jsr310的jar包。
解决方法二:
继承ObjectMapper来实现返回json字符串。MappingJackson2HttpMessageConverter主要通过ObjectMapper来实现返回json字符串。这里我们编写一个JsonUtil类,获取ObjectMapper以针对java8中新的日期时间API,注册相应的JsonSerializer<T>。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
|
/**
* json处理工具类
*
*
*/
@Component
public class JsonUtil {
private static final ObjectMapper mapper;
public ObjectMapper getMapper() {
return mapper;
}
static {
mapper = new ObjectMapper();
SimpleModule module = new SimpleModule();
module.addSerializer(LocalDate. class , new LocalDateSerializer());
module.addSerializer(LocalTime. class , new LocalTimeSerializer());
module.addSerializer(LocalDateTime. class , new LocalDateTimeSerializer());
mapper.registerModule(module);
}
public static String toJson(Object obj) {
try {
return mapper.writeValueAsString(obj);
} catch (Exception e) {
throw new RuntimeException( "转换json字符失败!" );
}
}
public <T> T toObject(String json, Class<T> clazz) {
try {
return mapper.readValue(json, clazz);
} catch (IOException e) {
throw new RuntimeException( "将json字符转换为对象时失败!" );
}
}
}
class LocalDateSerializer extends JsonSerializer<LocalDate> {
private static final DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern( "yyyy-MM-dd" );
@Override
public void serialize(LocalDate value, JsonGenerator jgen, SerializerProvider provider)
throws IOException, JsonProcessingException {
jgen.writeString(dateFormatter.format(value));
}
}
class LocalDateTimeSerializer extends JsonSerializer<LocalDateTime> {
private static final DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern( "yyyy-MM-dd HH:mm:ss" );
@Override
public void serialize(LocalDateTime value, JsonGenerator jgen, SerializerProvider provider)
throws IOException, JsonProcessingException {
jgen.writeString(dateTimeFormatter.format(value));
}
}
class LocalTimeSerializer extends JsonSerializer<LocalTime> {
private static final DateTimeFormatter timeFormatter = DateTimeFormatter.ofPattern( "HH:mm:ss" );
@Override
public void serialize(LocalTime value, JsonGenerator jgen, SerializerProvider provider)
throws IOException, JsonProcessingException {
jgen.writeString(timeFormatter.format(value));
}
}
|
然后在springmvc的配置文件中,再将<mvc:annotation-driven/>改为以下配置,配置一个新的json转换器,将它的ObjectMapper对象设置为JsonUtil中的objectMapper对象,此转换器比spring内置的json转换器优先级更高,所以与json有关的转换,spring会优先使用它。
1
2
3
4
5
6
7
8
9
10
11
12
13
|
< mvc:annotation-driven >
< mvc:message-converters >
< bean
class = "org.springframework.http.converter.json.MappingJackson2HttpMessageConverter" >
< property name = "objectMapper" value = "#{jsonUtil.mapper}" />
< property name = "supportedMediaTypes" >
< list >
< value >application/json;charset=UTF-8</ value >
</ list >
</ property >
</ bean >
</ mvc:message-converters >
</ mvc:annotation-driven >
|
然后java8中的几种日期和时间类型就可以正常友好的显示了。优点是全局统一管理日期和时间等类型,缺点对pojo中的某个域做特殊处理。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持服务器之家。
原文链接:http://www.cnblogs.com/jicp/p/6387757.html