通过Jackson的String转joda.DateTime的采坑记录

希-望圆满-
背景:最近公司在做秒杀活动,刚好我做的活动时间处理那块;其中一块是负责把前台的json通过Jackson转为joda.DateTime,但是就在这中间出现了问题

问题描述

直接把"2019-10-24 00:00:00"通过Jackson转为DateTime时,会产生如下错误:

org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Cannot construct instance of `org.joda.time.DateTime` (although at least one Creator exists): no String-argument constructor/factory method to deserialize from String value ('2019-10-24 00:00:00'); nested exception is com.fasterxml.jackson.databind.exc.MismatchedInputException: Cannot construct instance of `org.joda.time.DateTime` (although at least one Creator exists): no String-argument constructor/factory method to deserialize from String value ('2019-10-24 00:00:00')
 at ...
Caused by: com.fasterxml.jackson.databind.exc.MismatchedInputException: Cannot construct instance of `org.joda.time.DateTime` (although at least one Creator exists): no String-argument constructor/factory method to deserialize from String value ('2019-10-24 00:00:00')
 at ...

感觉是构造器出了问题,导入了jackson-core,jackson-databind ,jackson-datatype-joda三个包后,同时,又在application.properties中配置了time-format:spring.jackson.joda-date-time-format="yyyy-MM-dd HH:mm:ss"后,重新运行,发现仍然有问题:

org.springframework.http.converter.HttpMessageNotReadableException: JSON parse error: Invalid format: "2019-10-24 00:00:00" is malformed at " 00:00:00"; nested exception is com.fasterxml.jackson.databind.JsonMappingException: Invalid format: "2019-10-24 00:00:00" is malformed at " 00:00:00" (through reference chain: com.savannah.service.model.PromoDTO["startDate"])
	at ...
Caused by: com.fasterxml.jackson.databind.JsonMappingException: Invalid format: "2019-10-24 00:00:00" is malformed at " 00:00:00" (through reference chain: com.savannah.service.model.PromoDTO["startDate"])
	at ...
Caused by: java.lang.IllegalArgumentException: Invalid format: "2019-10-24 00:00:00" is malformed at " 00:00:00"
	at...

可以看出,是格式转换不正确,但是我找了好久也没找到正确转换格式的办法

产生原因

容易发现,Jackson内置的没有转换joda.DateTime的方式,需要通过第三个Jar包或者自定义序列化/反序列化来解决这个问题

解决方案

  • 自定义Jackson中实体类的序列化和反序列化方式:
public class CustomDateSerializer extends JsonSerializer<DateTime> {

    private static DateTimeFormatter formatter = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss");

    @Override
    public void serialize(DateTime value, JsonGenerator gen, SerializerProvider arg2) throws IOException {
        gen.writeString(formatter.print(value));
    }
}
public class CustomDateDeserializer extends JsonDeserializer<DateTime> {

    private static DateTimeFormatter formatter = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss");

    @Override
    public DateTime deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
        JsonNode node = jsonParser.getCodec().readTree(jsonParser);
        String s = node.asText();
        return DateTime.parse(s, formatter);
    }
}
  • 在DateTime类型的字段中加入注解:
	/**
     * 秒杀开始时间
     */
    @JsonSerialize(using = CustomDateSerializer.class)
    @JsonDeserialize(using = CustomDateDeserializer.class)
    private DateTime startDate;

    /**
     * 秒杀活动结束时间
     */
    @JsonSerialize(using = CustomDateSerializer.class)
    @JsonDeserialize(using = CustomDateDeserializer.class)
    private DateTime endDate;

这样的话基本就完工了,同时也可以尝试加入:

<dependency>
      <groupId>com.fasterxml.jackson.datatypegroupId>
      <artifactId>jackson-datatype-jodaartifactId>
      <version>2.9.8version>
dependency>

这个jar包,反序列化的结果会不一样哦

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: org.joda.time.datetime是一个Java类,用于处理日期和时间。它是Joda-Time库中的一个类,提供了许多有用的方法和功能,如日期和时间的解析、格式化、计算、比较等。它可以帮助开发人员更方便地处理日期和时间,避免了一些常见的错误和问题。 ### 回答2: org.joda.time.DateTime是一个Java日期和时间库中的一个类。它提供了对日期、时间、时间区域和持续时间的处理和操作。 DateTime类是不可变的,它包含了日期和时间的信息。它可以用于表示一个特定的时间点,例如某个事件发生的时间,或者表示一个时间范围,例如某个任务的开始时间和结束时间。 在使用DateTime类时,可以通过构造函数传递日期和时间的具体数值来创建一个DateTime对象。DateTime类提供了各种方法来获取和设置日期和时间的各个部分,例如获取年、月、日、小时、分钟、秒等。 DateTime类还提供了一系列的计算和比较方法,用于处理日期和时间之间的计算和比较。可以使用这些方法来计算两个日期之间的差距,比较两个日期的先后顺序,或者判断某个日期是否在一个时间范围内。 此外,DateTime类还支持时区的处理。它可以使用不同的时区来表示日期和时间,并支持将日期和时间换到不同的时区中。 总之,org.joda.time.DateTime是一个强大的日期和时间处理工具,它提供了丰富的功能和灵活的操作,可以满足各种日期和时间处理的需求。它是开发人员在Java应用程序中进行日期和时间处理的一个好选择。 ### 回答3: org.joda.time.DateTimeJoda-Time库中一个重要的类,用于表示日期和时间。它提供了许多有用的方法来处理和操作日期和时间。 首先,DateTime类可以通过构造函数创建一个具体的日期和时间对象。可以使用传入年、月、日、时、分、秒等参数的方式创建。例如,可以通过以下方式创建一个DateTime对象: DateTime dateTime = new DateTime(2022, 3, 15, 10, 30, 0); 此外,DateTime类还提供了许多方法来获取日期和时间的不同部分。例如,可以使用getYear()、getMonthOfYear()、getDayOfMonth()等方法来获取年、月、日的值。还可以使用getHourOfDay()、getMinuteOfHour()、getSecondOfMinute()等方法来获取时、分、秒的值。 DateTime类还支持日期和时间的比较。可以使用isBefore()、isAfter()、isEqual()等方法来比较两个DateTime对象的先后顺序或是否相等。 另外,DateTime类还具有许多方便的方法来进行日期和时间的操作。例如,可以使用plusDays()、minusHours()等方法来增加或减少日期和时间的值。还可以使用withDayOfWeek()、withMonthOfYear()等方法来设置特定的日期部分的值。 最后,DateTime类还提供了格式化日期和时间的功能。可以使用toString()方法将DateTime对象换为字符串表示形式。还可以使用format()方法将DateTime对象按照指定的格式换为字符串。 总之,org.joda.time.DateTime类是Joda-Time库中用于处理日期和时间的重要类,提供了许多方便的方法来表示、操作和比较日期和时间。它是Java中处理日期和时间的一个强大的替代品。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值