如何为日期格式动态自定义反序列化器?

时间:2019-02-24 18:23:26

标签: java json json-deserialization localdate

我正在开发自定义JSON反序列化器,并且具有以下课程

public class yyyy_MM_dd_DateDeserializer extends StdDeserializer <LocalDate> {

 public yyyy_MM_dd_DateDeserializer() {
  this(null);
 }

 public yyyy_MM_dd_DateDeserializer(Class t) {
  super(t);
 }

 @Override
 public LocalDate deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException {
  String dateString = jsonParser.getText();
  LocalDate localDate = null;
  try {
   localDate = LocalDate.parse(dateString, "yyyy-MM-dd");
  } catch (DateTimeParseException ex) {
   throw new RuntimeException("Unparsable date: " + dateString);
  }
  return localDate;
 }
}

在我的请求类中

@Valid
@JsonDeserialize(using = LocalDateDeserializer.class)
@JsonSerialize(using = LocalDateSerializer.class)
private LocalDate endDate;

它可以正常工作,但是我想知道是否可以动态传递日期格式。而不是在yyyy_MM_dd_DateDeserializer中进行硬编码。 我想从请求类中传递日期格式,以便我的反序列化器更通用,任何人都可以通过发送所需格式来使用它。

3 个答案:

答案 0 :(得分:0)

在使用活页夹库时不是(绑定的关键是它不是动态的。)

但是当使用简单的解析库(例如org.json)时,您可以

答案 1 :(得分:0)

我认为您为获得想要的东西而努力工作。没有编写自己的解串器,有一种更简单的方法。查看this question。基本上看起来像

@JsonFormat(shape= JsonFormat.Shape.STRING, pattern="EEE MMM dd HH:mm:ss Z yyyy")
@JsonProperty("created_at") 
ZonedDateTime created_at;

您只需戴上自己的面具。另外,我曾经有一个解析日期格式未知的任务,从本质上讲,我需要解析任何有效的日期。这是一篇描述如何实现它的想法的文章:Java 8 java.time package: parsing any string to date。您可能会发现它有用

答案 2 :(得分:0)

在使用java.time.*类和Jackson时,最好从注册jackson-datatype-jsr310模块来的JavaTimeModule开始。我们可以扩展它并使用提供的模式注册序列化器,如下例所示:

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer;

import java.time.LocalDate;
import java.time.format.DateTimeFormatter;

public class JsonApp {

    public static void main(String[] args) throws Exception {
        ObjectMapper mapperIso = createObjectMapper("yyyy-MM-dd");
        ObjectMapper mapperCustom0 = createObjectMapper("yyyy/MM/dd");
        ObjectMapper mapperCustom1 = createObjectMapper("MM-dd-yyyy");

        System.out.println(mapperIso.writeValueAsString(new Time()));
        System.out.println(mapperCustom0.writeValueAsString(new Time()));
        System.out.println(mapperCustom1.writeValueAsString(new Time()));
    }

    private static ObjectMapper createObjectMapper(String pattern) {
        JavaTimeModule javaTimeModule = new JavaTimeModule();
        javaTimeModule.addSerializer(LocalDate.class, new LocalDateSerializer(DateTimeFormatter.ofPattern(pattern)));

        ObjectMapper mapper = new ObjectMapper();
        mapper.registerModule(javaTimeModule);

        return mapper;
    }
}

class Time {

    private LocalDate now = LocalDate.now();

    public LocalDate getNow() {
        return now;
    }

    public void setNow(LocalDate now) {
        this.now = now;
    }

    @Override
    public String toString() {
        return "Time{" +
                "now=" + now +
                '}';
    }
}

上面的代码打印:

{"now":"2019-02-24"}
{"now":"2019/02/24"}
{"now":"02-24-2019"}