![](/img/trans.png)
[英]Set Calendar.DAY_OF_WEEK using java.time.DayOfWeek
[英]How to properly serialize/deserialize java.time.DayOfWeek with Jackson?
我正在開發一個存儲事件發生日期的應用程序。 我正在使用java.time.DayOfWeek
表示這一天,並將其持久化為字符串(例如MONDAY
, WEDNESDAY
)。
Jackson將這種類型序列化為字符串,因此JSON表示形式看起來像存儲在數據庫中的值。 但是,我想將其序列化/反序列化為數值。
我嘗試使用@JsonFormat
,但是可用的數字形狀基於索引,這是不希望的,因為MONDAY
值為1
,而不是0
。
編寫自定義序列化器似乎是這里唯一的解決方案,但是我覺得這個問題已經以某種方式解決了。
您可以忽略默認的getter並添加映射到DayOfWeek
字段的其他方法。 對於設置器,您可以創建一個附加int
而不是枚舉的設置器。
這是一個示例實現:
class MyDate {
private DayOfWeek dow = DayOfWeek.MONDAY;// DayOfWeek.of(LocalDate.now().getDayOfWeek());
@JsonIgnore
public DayOfWeek getDow() {
return dow;
}
public void setDow(int dow) {
this.dow = DayOfWeek.of(dow + 1);
}
@JsonProperty("dow")
public int getDayOfWeekNumber() {
return dow.getValue() - 1; //0 for Monday
}
public void setDow(DayOfWeek dow) {
this.dow = dow;
}
@Override
public String toString() {
return "[dow=" + dow + "]";
}
public static void main(String[] args) throws Exception {
System.out.println(new ObjectMapper().writeValueAsString(new MyDate()));
System.out.println(new ObjectMapper().readValue("{\"dow\":7}", MyDate.class));
}
}
DayOfWeek
不支持自定義一周的第一天或其索引。 這就是上面的代碼使用+/- 1
進行移位的原因。
為了避免在應用程序的各層和各部分之間產生任何誤解,最好是使用String
表示形式: MONDAY
, WEDNESDAY
等。如果要將此enum
序列化為int
任何數字都可以並且一樣好。 在每一層上,您都必須保留1
表示MONDAY
的信息。 無論這將是0
, 1
或10
也沒關系。 在Java
中, Calendar.MONDAY
等於2
, DayOfWeek.MONDAY
等於1
,還有WeekFields.ISO
,其中MONDAY
是第一天,而WeekFields.SUNDAY_START
,其中SUNDAY
是一周的第一天。
如果您需要為MONDAY
定義1
作為所有POJO
類的基本概念,則需要注冊自定義序列化程序。 自定義序列化器可能如下所示:
class DayOfWeekSerializer extends StdSerializer<DayOfWeek> {
public DayOfWeekSerializer() {
super(DayOfWeek.class);
}
@Override
public void serialize(DayOfWeek value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeNumber(value.getValue());
}
}
自定義解串器:
class DayOfWeekDeserializer extends StdDeserializer<DayOfWeek> {
public DayOfWeekDeserializer() {
super(DayOfWeek.class);
}
@Override
public DayOfWeek deserialize(JsonParser p, DeserializationContext ctxt) throws IOException, JsonProcessingException {
return DayOfWeek.of(p.getIntValue());
}
}
您可以像下面這樣注冊:
ObjectMapper createObjectMapper() {
SimpleModule dayOfWeeModule = new SimpleModule("DayOfWeek module");
dayOfWeeModule.addSerializer(DayOfWeek.class, new DayOfWeekSerializer());
dayOfWeeModule.addDeserializer(DayOfWeek.class, new DayOfWeekDeserializer());
ObjectMapper mapper = new ObjectMapper();
mapper.registerModule(dayOfWeeModule);
mapper.enable(SerializationFeature.INDENT_OUTPUT);
return mapper;
}
對於以下測試POJO class
:
class Days {
private DayOfWeek monday = DayOfWeek.MONDAY;
private DayOfWeek tuesday = DayOfWeek.TUESDAY;
private DayOfWeek wednesday = DayOfWeek.WEDNESDAY;
private DayOfWeek thursday = DayOfWeek.THURSDAY;
private DayOfWeek friday = DayOfWeek.FRIDAY;
private DayOfWeek saturday = DayOfWeek.SATURDAY;
private DayOfWeek sunday = DayOfWeek.SUNDAY;
// getter, setters, toString
}
用法示例:ObjectMapper mapper = createObjectMapper();
String json = mapper.writeValueAsString(new Days());
System.out.println(json);
System.out.println(mapper.readValue(json, Days.class));
上面的代碼打印:
{
"monday" : 1,
"tuesday" : 2,
"wednesday" : 3,
"thursday" : 4,
"friday" : 5,
"saturday" : 6,
"sunday" : 7
}
Days{monday=MONDAY, tuesday=TUESDAY, wednesday=WEDNESDAY, thursday=THURSDAY, friday=FRIDAY, saturday=SATURDAY, sunday=SUNDAY}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.