这是我的课程(省略了getter和setter的内容):
public class ClassWithAMap {
@JsonProperty("map")
@JsonDeserialize(keyUsing = RangeDeserializer.class)
private Map<Range<Instant>, String> map;
@JsonCreator
public ClassWithAMap(Map<Range<Instant>, String> map) {
this.map = map;
}
}
RangeSerializer看起来像这样:
public class RangeDeserializer extends KeyDeserializer {
public ObjectMapper objectMapper() {
return new ObjectMapper()
.registerModules(
new JavaTimeModule(),
new Jdk8Module(),
new GuavaModule(),
new ParameterNamesModule());
}
@Override
public Range<Instant> deserializeKey(String key, DeserializationContext ctxt)
throws IOException, JsonProcessingException {
TypeReference<Range<Instant>> typeRef = new TypeReference<Range<Instant>>() {
};
Range<Instant> range = objectMapper().readValue(key, typeRef);
return range;
}
}
使用这些代码的主要代码如下:
Map<Range<Instant>,String> map = new HashMap<>();
Range<Instant> key = Range.greaterThan(Instant.now());
map.put(key, "some value");
ClassWithAMap classWithAMap = new ClassWithAMap(map);
String jsonInput = objectMapper()
.writerWithDefaultPrettyPrinter()
.writeValueAsString(classWithAMap);
ClassWithAMap classWithMap = objectMapper()
.readValue(jsonInput,
ClassWithAMap.class);
最后一条语句给我这个错误:
InvalidDefinitionException: Cannot find a (Map) Key deserializer for type [simple type, class com.google.common.collect.Range<java.time.Instant>]
而且,可以肯定的是,它从不调用我的解串器。我已经错过了注册反序列化器的步骤,尽管我将其与使用自定义类而不是Range<Instant>
的类似设置进行了比较,但效果很好,我看不出有什么区别。有人知道我做错了吗?我猜想与泛型有关,但是我还没有进一步。
我正在使用杰克逊2.9.9和Java 1.8。
答案 0 :(得分:1)
您需要将所有注释移至构造函数:
class ClassWithAMap {
private Map<Range<Instant>, String> map;
@JsonCreator
public ClassWithAMap(
@JsonProperty("map")
@JsonDeserialize(keyUsing = RangeDeserializer.class)
Map<Range<Instant>, String> map) {
this.map = map;
}
}