更新:
私はジャクソンのソースコードでデバッグして、メソッドでそれを見つけようとしました
deserialize(JsonParser jp, DeserializationContext ctxt)
SettableBeanProperty.Java
_valueTypeDeserializer
がnullでない場合、_valueDeserializer
は使用されません。
これは、TypeDeserializerがValueDeserializerより適切であるという正しい仮定ですか?
@JsonDeserialize
を使用して、多相型を持つ1つのフィールドのカスタムデシリアライザーを定義しようとしています。 @JsonDeserialize
と@JsonTypeInfo
を別々に使用できます。しかし、それらを一緒に使用すると、@JsonDeserialize
注釈は無視されるようです。
クラス階層は次のとおりです。
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "type", defaultImpl = Definition.class)
@JsonSubTypes({@Type(value = Definition.class, name = "normal"),
@Type(value = FormDefinition.class, name = "form")})
public class Definition {
private String name;
private String description;
// getter&setter for name&description
}
public class FormDefinition extends Definition {
private String formName;
@JsonDeserialize(using = DefinitionDeserializer.class)
private Definition definition;
public String getFormName() {
return formName;
}
public void setFormName(String formName) {
this.formName = formName;
}
public void setDefinition(Definition definition) {
this.definition = definition;
}
}
public class DefinitionDeserializer extends JsonDeserializer<Definition> {
@Override
public Definition deserialize(JsonParser jsonParser, DeserializationContext deserializationContext)
throws IOException, JsonProcessingException {
Definition definition = new Definition();
String name = jsonParser.readValueAs(String.class);
definition.setName(name);
return definition;
}
}
public class App
{
public static void main( String[] args ) throws IOException {
String sampleData = "{\"type\":\"form\",\"definition\":\"super\",\"formName\":\"FormName\"}";
ObjectMapper mapper = new ObjectMapper();
Definition definition = mapper.readValue(sampleData, Definition.class);
System.out.println(definition);
}
}
サンプルのメインアプリを実行すると、例外がスローされます。
Exception in thread "main" com.fasterxml.jackson.databind.JsonMappingException: Can not instantiate value of type [simple type, class jp.co.worksap.model.Definition] from String value ('super'); no single-String constructor/factory method (through reference chain: jp.co.worksap.model.FormDefinition["definition"])
これは、注釈付きデシリアライザAsPropertyTypeDeserializer
の代わりにdefinition
クラスのFormDefinition
フィールドを逆シリアル化するためにDefinitionDeserializer
を使用しているようです。
ここで注意が必要なのは、カスタムデシリアライザーを使用するフィールドも、@JsonTypeInfo
を使用して多相性の問題を解決するDefinition
のタイプであると思います。
それらを一緒に使用する方法はありますか?ありがとう。
ジャクソンプロセス@JsonTypeInfo
使用するデシリアライザーを選択する前。おそらく、デシリアライザーの選択は一般的にタイプに依存する可能性があるためです。ただし、カスタムデシリアライザーを指定するのと同じ方法で、フィールドに直接注釈を付けることで、フィールドごとに簡単に無効にすることができます。
@JsonDeserialize(using = DefinitionDeserializer.class)
@JsonTypeInfo(use = JsonTypeInfo.Id.NONE)
private Definition definition;