如何检索由Jackson @JsonDeserialize注释的类?

时间:2016-10-08 18:23:32

标签: java json jackson

我的任务是将json对象反序列化为枚举。请参阅页面末尾的示例。

但我无法定义在方法JsonEnumDeserializer.deserialize(云端硬盘或其他广告)中创建哪个枚举。

我只想注释我的枚举@JsonDeserialize(using = JsonEnumDeserializer.class),它应该按照我描述的方式反序列化所有带注释的枚举。

1)为此,我尝试了扩展org.codehaus.jackson.map.deser.std.EnumDeserializer,但它在运行时失败,不需要arg构造函数,或者在编译时失败,只需要覆盖父构造函数EnumDeserializer(EnumResolver<?> res)。 我试着深入了解EnumDeserializer如何检索Enum类,但它没有给我任何结果。

2)其他解决方案添加字段&#34; type&#34;对于json,但这是一个糟糕的解决方案。

在方法JsonEnumDeserializer.deserialize中,我想检索由@JsonDeserialize注释的类(它将解决问题)。有人能帮助我吗?

{
  "make":"Mazda",
  "model":"6",
  "drive":{
    "id":"FWD",
    "name":"Front wheel drive"
  }
}

public class Car {
    private String make;
    private String model;
    private Drive drive;

    /* setters and getters */
}

@JsonDeserialize(using = JsonEnumDeserializer.class)
public enum Drive {
    FWD, RWD, AWD
}

public class JsonEnumDeserializer extends JsonDeserializer<Enum> {
    @Override
    public Enum deserialize(JsonParser jp, DeserializationContext ctxt) throws IOException, JsonProcessingException {
        String enumName = jp.readValueAsTree().findValue("id").asText();
        return ??? /* Knowing enumName how can I figure out which enum Class return? Drive enum or other enum? I want write universal deserializer for all enum */
    }
}

2 个答案:

答案 0 :(得分:1)

我找到的一个解决方案是将杰克逊改为Gson。 Gson可以说要返回哪个Class的实例。参数Type type

public class GsonEnumDeserializer implements JsonDeserializer<Enum> {
    @Override
    public Enum deserialize(JsonElement jsonElement, Type type, JsonDeserializationContext jsonDeserializationContext) throws JsonParseException {
        try {
            Class enumClass = Class.forName(type.getTypeName());
            String enumName = jsonElement.getAsJsonObject().get("id").getAsString();
            return (Enum) enumClass.getMethod("valueOf", String.class).invoke(null, enumName);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}

/* usage */
Gson gson = new GsonBuilder()
    .registerTypeHierarchyAdapter(Enum.class, new GsonEnumDeserializer())
    .create();
Car car = gson.fromJson(carJson, Car.class);

答案 1 :(得分:0)

在这种情况下,您根本不需要自定义JsonDeserializer

drive中的Car字段是枚举,而不是对象,所以你的json应该是:

{
  "make":"Mazda",
  "model":"6",
  "drive":"FWD"
}

你的json文本或你Car类是错误的。