com.fasterxml.jackson.databind.exc.InvalidFormatException

目录

异常描述

错误位置初现

追根溯源

解决过程

解决方案


 

 

  • 异常描述:

com.fasterxml.jackson.databind.exc.InvalidFormatException: Cannot deserialize value of type `java.util.Date` from String "2020-06-29T02:49:17.340+0000": not a valid representation (error: Failed to parse Date value '2020-06-29T02:49:17.340+0000': Unparseable date: "2020-06-29T02:49:17.340+0000")
 at [Source: (String)"{"models":[{"id":"754a1728-a539-11ea-8ce9-c01885024e2c","name":"model_request","version":3,"modelType":0,"description":"model_request","stencilSetId":null,"createdBy":"admin","lastUpdatedBy":"bpmUser","lastUpdated":"2020-06-29T02:49:17.340+0000"}],"name":"bpm_dev","key":"bpm_dev","theme":"theme-4","icon":"glyphicon-asterisk","groupsAccess":"manager"}"; line: 1, column: 216] (through reference chain: org.flowable.ui.modeler.domain.AppDefinition["models"]->java.util.ArrayList[0]->org.flowable.ui.modeler.domain.AppModelDefinition["lastUpdated"])
	at com.fasterxml.jackson.databind.exc.InvalidFormatException.from(InvalidFormatException.java:67)
	at com.fasterxml.jackson.databind.DeserializationContext.weirdStringException(DeserializationContext.java:1676)
	at com.fasterxml.jackson.databind.DeserializationContext.handleWeirdStringValue(DeserializationContext.java:932)
	at com.fasterxml.jackson.databind.deser.std.StdDeserializer._parseDate(StdDeserializer.java:550)
	at com.fasterxml.jackson.databind.deser.std.StdDeserializer._parseDate(StdDeserializer.java:491)
	at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateBasedDeserializer._parseDate(DateDeserializers.java:195)
	at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateDeserializer.deserialize(DateDeserializers.java:285)
	at com.fasterxml.jackson.databind.deser.std.DateDeserializers$DateDeserializer.deserialize(DateDeserializers.java:268)
	at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:129)
	at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:369)
	at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:159)
	at com.fasterxml.jackson.databind.deser.std.CollectionDeserializer.deserialize(CollectionDeserializer.java:286)
	at com.fasterxml.jackson.databind.deser.std.CollectionDeserializer.deserialize(CollectionDeserializer.java:245)
	at com.fasterxml.jackson.databind.deser.std.CollectionDeserializer.deserialize(CollectionDeserializer.java:27)
	at com.fasterxml.jackson.databind.deser.impl.MethodProperty.deserializeAndSet(MethodProperty.java:129)
	at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserializeFromObject(BeanDeserializer.java:369)
	at com.fasterxml.jackson.databind.deser.BeanDeserializer.deserialize(BeanDeserializer.java:159)
	at com.fasterxml.jackson.databind.ObjectMapper._readMapAndClose(ObjectMapper.java:4202)
	at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:3205)
	at com.fasterxml.jackson.databind.ObjectMapper.readValue(ObjectMapper.java:3173)
	at org.ups.modules.bpm.controller.RegisterApprovalController.testTime(RegisterApprovalController.java:200)


反序列化失败字段:lastUpdated (java.util.Date)
反序列化失败值:2020-06-29T02:49:17.340+0000
  • 错误位置初现:

伪代码:类中注入objectMapper
@Autowired
private ObjectMapper objectMapper;

伪代码:方法中调用objectMapper.readValue() 反序列化json
AppDefinition appDefinition = null;
try {
    appDefinition = objectMapper.readValue(json, AppDefinition.class);
} catch (JsonProcessingException e) {
    e.printStackTrace();
}
  • 追根溯源:

com.fasterxml.jackson.databind.DeserializationContext#parseDate():705行

public Date parseDate(String dateStr) throws IllegalArgumentException
{
   try {
        DateFormat df = getDateFormat();
        return df.parse(dateStr);
   } catch (ParseException e) {
        throw new IllegalArgumentException(String.format(
                    "Failed to parse Date value '%s': %s", dateStr,
                    ClassUtil.exceptionMessage(e)));
   }
}

在这里抛出异常IllegalArgumentException

发现这里df 获取的DateFormat的实现是 SimpleDateFormat,
formatdate是 “yyyy-MM-dd HH:mm:ss” 
而需要反序列化的日期是 “2020-06-29T02:49:17.340+0000” 因此反序列化失败
  • 解决过程:

    经测试发现 当创建ObjectMapper时 
    
    1.如果使用无参构造创建:
    ObjectMapper objectMapper = new ObjectMapper();
    
    则DeserializationConfig中_base._dateFormat 是 StdDateFormat
    
    2.如果使用注入创建
    @Autowired
    private ObjectMapper objectMapper;
    
    则DeserializationConfig中_base._dateFormat 是 SimpleDateFormat
    
    使用注入创建时,会在spring-boot-autoconfigure包下的JacksonAutoConfiguration 中获取bean
    org.springframework.boot.autoconfigure.jackson.JacksonAutoConfiguration#305
    
    @Bean
    @Primary
    @ConditionalOnMissingBean
    ObjectMapper jacksonObjectMapper(Jackson2ObjectMapperBuilder builder) {
         return builder.createXmlMapper(false).build();
    }
    
    

    解决方案:

1.创建ObjectMapper时 使用构造函数创建 即new出一个ObjectMapper

 

你可能感兴趣的:(json,SpringBoot)