【问题标题】:JSON Jackson ObjectMapper ReadValue - Error in converting dateJSON Jackson ObjectMapper ReadValue - 转换日期时出错
【发布时间】:2016-01-11 20:03:40
【问题描述】:

我在尝试将 json 字符串转换为对象时看到下面列出的错误。我没有 Data 类的源代码,它是 jar 文件的一部分。有没有办法可以使用 mixins 来解决这个问题?

代码

ObjectMapper mapper = new ObjectMapper();
mapper.readValue(request, Data.class);

错误

org.codehaus.jackson.map.JsonMappingException: 无法构造 来自 String 值的 javax.xml.datatype.XMLGregorianCalendar 的实例 '10:00:00':不是有效的表示(错误:无法解析日期 “10:00:00”:不兼容任何标准格式 ("yyyy-MM-dd'T'HH:mm:ss.SSSZ", "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'", "EEE, dd MMM yyyy HH:mm:ss zzz", "yyyy-MM-dd"))

JSON 请求

 "timeSlot":{  
       "date":"2015-10-21",
       "endTime":"10:00:00",
       "startTime":"08:00:00",   
 }

编辑

此问题类似于 this ,但是在反序列化时会发生这种情况。另一个解决方案有助于适当地序列化请求。

我已经粘贴了下面不起作用的示例代码 -

import java.io.IOException;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;

import javax.xml.datatype.DatatypeConfigurationException;
import javax.xml.datatype.DatatypeConstants;
import javax.xml.datatype.DatatypeFactory;
import javax.xml.datatype.XMLGregorianCalendar;

import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;

public class TestJSONDeserialize {

    public static void main(String[] args){

        ObjectMapper mapper = new ObjectMapper();
        mapper.addMixIn(Data.class, MyMixin.class);

        String jsonString = "{\"date\":\"2014-02-10\",\"time\":\"16:15:00\"}";
        try {
            mapper.readValue(jsonString, Data.class);
        } catch (JsonParseException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (JsonMappingException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

    }


}

数据类(我无法更改此文件)

import javax.xml.datatype.XMLGregorianCalendar;

public class Data {

    private XMLGregorianCalendar date;
    private XMLGregorianCalendar time;

    public XMLGregorianCalendar getDate() {
        return date;
    }
    public void setDate(XMLGregorianCalendar date) {
        this.date = date;
    }
    public XMLGregorianCalendar getTime() {
        return time;
    }
    public void setTime(XMLGregorianCalendar time) {
        this.time = time;
    }



}

我在运行时看到以下错误:

com.fasterxml.jackson.databind.exc.InvalidFormatException: 不能 构造 javax.xml.datatype.XMLGregorianCalendar 的实例 字符串值“16:15:00”:不是有效的表示(错误:无法 解析日期值“16:15:00”:无法解析日期“16:15:00”:不是 兼容任何标准形式(“yyyy-MM-dd'T'HH:mm:ss.SSSZ”, "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'", "EEE, dd MMM yyyy HH:mm:ss zzz", "yyyy-MM-dd")) 在 [来源:{"date":"2014-02-10","time":"16:15:00"}; 行:1,列:21](通过参考链: com.comcast.json.test.Data["time"])

【问题讨论】:

    标签: java json jackson spring-boot


    【解决方案1】:

    已在此旧帖子中回答,但希望这对将来的某人有所帮助。

    ObjectMapper 中指定DateFormat 解决了我的问题。

    objectMapper.setDateFormat(new SimpleDateFormat(MY_FORMAT));
    

    【讨论】:

      【解决方案2】:

      我能够使用自定义反序列化器和 mixins 来完成这项工作。下面的代码 -

      import java.io.IOException;
      import java.text.DateFormat;
      import java.text.ParseException;
      import java.text.SimpleDateFormat;
      import java.util.Calendar;
      import java.util.Date;
      import java.util.GregorianCalendar;
      
      import javax.xml.datatype.DatatypeConfigurationException;
      import javax.xml.datatype.DatatypeConstants;
      import javax.xml.datatype.DatatypeFactory;
      import javax.xml.datatype.XMLGregorianCalendar;
      
      import com.fasterxml.jackson.core.JsonParseException;
      import com.fasterxml.jackson.core.JsonProcessingException;
      import com.fasterxml.jackson.databind.JsonMappingException;
      import com.fasterxml.jackson.databind.ObjectMapper;
      import com.fasterxml.jackson.databind.SerializationFeature;
      
      public class TestJSONDeserialize {
      
          public static void main(String[] args){
      
              ObjectMapper mapper = new ObjectMapper();
              mapper.addMixIn(Data.class, NewMixin.class);
      
              String jsonString = "{\"date\":\"2014-02-10\",\"time\":\"16:15:00\"}";
              Data data = null;
              try {
                  data = mapper.readValue(jsonString, Data.class);
              } catch (JsonParseException e) {
                  // TODO Auto-generated catch block
                  e.printStackTrace();
              } catch (JsonMappingException e) {
                  // TODO Auto-generated catch block
                  e.printStackTrace();
              } catch (IOException e) {
                  // TODO Auto-generated catch block
                  e.printStackTrace();
              }
      
              if(data != null){
                  System.out.println(" Data " + data.getDate());
                  System.out.println(" Data " + data.getTime());
              }   
          }
      
      
      }
      
      
      
      import java.io.IOException;
      import java.text.ParseException;
      import java.text.SimpleDateFormat;
      import java.util.Date;
      import java.util.GregorianCalendar;
      
      import javax.xml.datatype.DatatypeConfigurationException;
      import javax.xml.datatype.DatatypeFactory;
      import javax.xml.datatype.XMLGregorianCalendar;
      
      import com.fasterxml.jackson.core.JsonParser;
      import com.fasterxml.jackson.core.JsonProcessingException;
      import com.fasterxml.jackson.databind.DeserializationContext;
      import com.fasterxml.jackson.databind.JsonDeserializer;
      
      public class CustomDateDeserializer extends JsonDeserializer<XMLGregorianCalendar> {
      
          private static SimpleDateFormat formatter = 
            new SimpleDateFormat("yyyy-MM-dd");
      
      
          @Override
          public XMLGregorianCalendar deserialize(JsonParser jsonparser, DeserializationContext arg1) throws IOException, JsonProcessingException {
              // TODO Auto-generated method stub
              String date = jsonparser.getText();
              try {
      
                  GregorianCalendar c = new GregorianCalendar();
                  c.setTime(formatter.parse(date));
                  XMLGregorianCalendar date2 = null;
                  try {
                      date2 = DatatypeFactory.newInstance().newXMLGregorianCalendar(c);
                  } catch (DatatypeConfigurationException e) {
                      // TODO Auto-generated catch block
                      e.printStackTrace();
                  }
      
                  return date2;
              } catch (ParseException e) {
                  throw new RuntimeException(e);
              }
          }
      }
      
      
      
      
      import java.io.IOException;
      import java.text.ParseException;
      import java.text.SimpleDateFormat;
      import java.util.Date;
      import java.util.GregorianCalendar;
      
      import javax.xml.datatype.DatatypeConfigurationException;
      import javax.xml.datatype.DatatypeFactory;
      import javax.xml.datatype.XMLGregorianCalendar;
      
      import com.fasterxml.jackson.core.JsonParser;
      import com.fasterxml.jackson.core.JsonProcessingException;
      import com.fasterxml.jackson.databind.DeserializationContext;
      import com.fasterxml.jackson.databind.JsonDeserializer;
      
      public class CustomTimeDeserializer extends JsonDeserializer<XMLGregorianCalendar> {
      
          private static SimpleDateFormat formatter = 
            new SimpleDateFormat("hh:mm:ss");
      
      
          @Override
          public XMLGregorianCalendar deserialize(JsonParser jsonparser, DeserializationContext arg1) throws IOException, JsonProcessingException {
              // TODO Auto-generated method stub
              String date = jsonparser.getText();
              try {
      
                  GregorianCalendar c = new GregorianCalendar();
                  c.setTime(formatter.parse(date));
                  XMLGregorianCalendar date2 = null;
                  try {
                      date2 = DatatypeFactory.newInstance().newXMLGregorianCalendar(c);
                  } catch (DatatypeConfigurationException e) {
                      // TODO Auto-generated catch block
                      e.printStackTrace();
                  }
      
                  return date2;
              } catch (ParseException e) {
                  throw new RuntimeException(e);
              }
          }
      }
      
      
      
      import javax.xml.datatype.XMLGregorianCalendar;
      
      import com.fasterxml.jackson.annotation.JsonFormat;
      import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
      
      abstract class NewMixin {
      
          @JsonDeserialize(using = CustomDateDeserializer.class)
          public abstract void setDate(XMLGregorianCalendar date);
      
          @JsonDeserialize(using = CustomTimeDeserializer.class)
          public abstract void setTime(XMLGregorianCalendar time);
      }
      

      【讨论】:

        【解决方案3】:

        here。在您的字段上粘贴日期格式化程序:

        @JsonFormat(shape=JsonFormat.Shape.STRING, pattern="HH:mm:ss", timezone="CET")
        private Date startTime;
        

        【讨论】:

        • 谢谢。我没有 java 文件,但我使用的类是不同团队提供的 jar 的一部分。我将无法修改包含该字段的类。我也无法为整个班级设置通用日期时间格式,因为日期是 yyyy-MM-dd 而时间是 hh:mm:ss
        猜你喜欢
        • 1970-01-01
        • 2019-04-10
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-07-30
        • 2020-08-24
        • 2017-05-20
        相关资源
        最近更新 更多