赞
踩
背景:fastjson2在处理时间日期格式时,输入非法的日期字符串字符串,转成Date、LocalDateTime等类型时,有时候不会报错,为处理这样的情况,需要增加反序列化处理。
本文使用的fastjson2版本依赖
<dependency>
<groupId>com.alibaba.fastjson2</groupId>
<artifactId>fastjson2</artifactId>
<version>2.0.49</version>
</dependency>
@Data class A { @JSONField(format = "yyyy-MM-dd HH:mm:ss") private Date key1; } @Test public void test(){ String json1 = "{\"key1\": \"1\"}"; // 无异常,时间格式不符合 不符合预期 结果:A(key1=Thu Jan 01 08:00:00 CST 1970) System.out.println(JSON.parseObject(json1, A.class)); String json2 = "{\"key1\": \"2024-05-01\"}"; // 无异常,时间格式不符合 不符合预期 结果:A(key1=Wed May 01 00:00:00 CST 2024) System.out.println(JSON.parseObject(json2, A.class)); String json3 = "{\"key1\": \"2024-05-01 66\"}"; // 这种情况下会抛出异常 java.time.format.DateTimeParseException: Text '2024-05-01 66' could not be parsed at index 10 System.out.println(JSON.parseObject(json3, A.class)); }
@JSONField(format = "日期格式")
可以用来指定期望的时间格式,但是在某些情况下不会报错。
@Data
class A {
@JSONField(format = "yyyy-MM-dd HH:mm:ss")
private LocalDateTime key1;
}
@Test
public void test() {
String json1 = "{\"key1\": \"1\"}";
// 无异常,时间格式不符合 不符合预期 结果:A(key1=Thu Jan 01 08:00:00 CST 1970)
System.out.println(JSON.parseObject(json1, A.class));
String json2 = "{\"key1\": \"2024-05-01\"}";
// 无异常,时间格式不符合 不符合预期 结果:A(key1=Wed May 01 00:00:00 CST 2024)
System.out.println(JSON.parseObject(json2, A.class));
String json3 = "{\"key1\": \"2024-05-01T00:00:00.222\"}";
// 无异常,时间格式不符合 不符合预期 A(key1=2024-05-01T00:00:00.222)
System.out.println(JSON.parseObject(json3, A.class));
}
可以看到@JSONField(format = "日期格式")
在解析成LocalDateTime 类型时并没有生效,查看源码中对JSONField类中format的注释:
说明该属性仅对Date生效,那怎么处理上述不会报错的情况呢?
以LocalDateTime作为参考:
public class LocalDateTimeReader implements ObjectReader<LocalDateTime> { public static final LocalDateTimeReader INSTANCE = new LocalDateTimeReader(); private static final String DATE_PATTERN = "yyyy-MM-dd HH:mm:ss"; @Override public LocalDateTime readObject(JSONReader jsonReader, Type fieldType, Object fieldName, long features) { if (jsonReader.nextIfNull()) { return null; } String dateTimeStr = jsonReader.readString(); DateTimeFormatter formatter = DateTimeFormatter.ofPattern(DATE_PATTERN); LocalDateTime validDateTime; try { validDateTime = LocalDateTime.parse(dateTimeStr, formatter); } catch (Exception e) { throw new RuntimeException(String.format("时间格式有误,请检查时间格式:%s", DATE_PATTERN)); } return validDateTime; } }
在需要校验的日期格式上加上注解:
@JSONField(deserializeUsing = LocalDateTimeReader.class)
或者全局注册(但是会影响到所有的该类型,需要慎重):
JSON.register(LocalDateTime.class, LocalDateTimeReader.INSTANCE);
@Data
class A {
private LocalDateTime key1;
}
@Test
public void test1() {
JSON.register(LocalDateTime.class, LocalDateTimeReader.INSTANCE);
String json1 = "{\"key1\": \"1\"}";
// 有异常,时间格式不符合 符合预期 结果:com.alibaba.fastjson2.JSONException... Caused by: java.lang.RuntimeException: 时间格式有误,请检查时间格式:yyyy-MM-dd HH:mm:ss
// System.out.println(JSON.parseObject(json1, A.class));
String json2 = "{\"key1\": \"2024-05-01\"}";
// 有异常,时间格式不符合 符合预期 结果:com.alibaba.fastjson2.JSONException... Caused by: java.lang.RuntimeException: 时间格式有误,请检查时间格式:yyyy-MM-dd HH:mm:ss
// System.out.println(JSON.parseObject(json2, A.class));
String json3 = "{\"key1\": \"2024-05-01T00:00:00.222\"}";
// 有异常,时间格式不符合 符合预期 结果:com.alibaba.fastjson2.JSONException... Caused by: java.lang.RuntimeException: 时间格式有误,请检查时间格式:yyyy-MM-dd HH:mm:ss
System.out.println(JSON.parseObject(json3, A.class));
}
@Data
class A {
@JSONField(deserializeUsing = LocalDateTimeReader.class)
private LocalDateTime key1;
}
@Test
public void test2() {
String json1 = "{\"key1\": \"1\"}";
// 有异常,时间格式不符合 符合预期 结果:com.alibaba.fastjson2.JSONException... Caused by: java.lang.RuntimeException: 时间格式有误,请检查时间格式:yyyy-MM-dd HH:mm:ss
// System.out.println(JSON.parseObject(json1, A.class));
String json2 = "{\"key1\": \"2024-05-01\"}";
// 有异常,时间格式不符合 符合预期 结果:com.alibaba.fastjson2.JSONException... Caused by: java.lang.RuntimeException: 时间格式有误,请检查时间格式:yyyy-MM-dd HH:mm:ss
// System.out.println(JSON.parseObject(json2, A.class));
String json3 = "{\"key1\": \"2024-05-01T00:00:00.222\"}";
// 有异常,时间格式不符合 符合预期 结果:com.alibaba.fastjson2.JSONException... Caused by: java.lang.RuntimeException: 时间格式有误,请检查时间格式:yyyy-MM-dd HH:mm:ss
System.out.println(JSON.parseObject(json3, A.class));
}
测试完毕,都能够抛出异常
参考链接:
https://github.com/alibaba/fastjson2/wiki/register_custom_reader_writer_cn
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。