使用 Jackson 的 @JsonTypeInfo 反序列化时如何保留类型 属性?
How can I retain the type property when deserializing with Jackson's @JsonTypeInfo?
我有这样的设置:
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "dishName", defaultImpl = Food.class)
@JsonSubTypes(value = {
@Type(name = "fries", value = Fries.class),
@Type(name = "burger", value = Burger.class)
})
public class Food {
private String dishName;
@Override
public String toString() {
return dishName + ", type: " + this.getClass().getName();
}
}
public class Fries extends Food { /*...*/ }
public class Burger extends Food { /*...*/ }
public class TryItOut {
private static String foodString = "[ { \"dishName\":\"burger\" }, { \"dishName\":\"fries\" }, { \"dishName\":\"cabbage\" } ]";
public static void main(String[] args) {
ObjectMapper m = new ObjectMapper();
try {
Food[] food = m.readValue(foodString, Food[].class);
for (Food dish : food) {
System.out.println(dish);
}
} catch (IOException e) {
System.out.println("something went wrong");
e.printStackTrace();
}
}
}
我想用它来反序列化 json 我无法影响的内容(所以没有添加 "proper" 类型信息的选项)。我遇到的问题是,显然 dishName
json 属性 用于确定子类型,但它没有反序列化到 java 字段中。也有办法实现这一目标吗?换句话说:主要方法打印
null, type: Burger
null, type: Fries
null, type: Food
在控制台上,但我希望它打印出来
burger, type: Burger
fries, type: Fries
cabbage, type: Food
这特别讨厌,因为我无法稍后发现最后一个对象是卷心菜。这抵消了默认实现的好处。
编辑:
@Evil Raat 的回答可以解决问题。为了完整起见:Food
class 中的 dishName
字段需要 @JsonProperty
注释才能使此示例正常工作。因此,工作示例如下所示:
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "dishName", defaultImpl = Food.class, visible = true)
@JsonSubTypes(value = {
@Type(name = "fries", value = Fries.class),
@Type(name = "burger", value = Burger.class)
})
public class Food {
@JsonProperty
private String dishName;
@Override
public String toString() {
return dishName + ", type: " + this.getClass().getName();
}
}
public class Fries extends Food { /*...*/ }
public class Burger extends Food { /*...*/ }
public class TryItOut {
private static String foodString = "[ { \"dishName\":\"burger\" }, { \"dishName\":\"fries\" }, { \"dishName\":\"cabbage\" } ]";
public static void main(String[] args) {
ObjectMapper m = new ObjectMapper();
try {
Food[] food = m.readValue(foodString, Food[].class);
for (Food dish : food) {
System.out.println(dish);
}
} catch (IOException e) {
System.out.println("something went wrong");
e.printStackTrace();
}
}
}
要保持用于反序列化的 属性 的值,您只需在 @JsonSubTypes 注释上将可见的 属性 设置为 true:
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "dishName", defaultImpl = Food.class, visible = true)
我有这样的设置:
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "dishName", defaultImpl = Food.class)
@JsonSubTypes(value = {
@Type(name = "fries", value = Fries.class),
@Type(name = "burger", value = Burger.class)
})
public class Food {
private String dishName;
@Override
public String toString() {
return dishName + ", type: " + this.getClass().getName();
}
}
public class Fries extends Food { /*...*/ }
public class Burger extends Food { /*...*/ }
public class TryItOut {
private static String foodString = "[ { \"dishName\":\"burger\" }, { \"dishName\":\"fries\" }, { \"dishName\":\"cabbage\" } ]";
public static void main(String[] args) {
ObjectMapper m = new ObjectMapper();
try {
Food[] food = m.readValue(foodString, Food[].class);
for (Food dish : food) {
System.out.println(dish);
}
} catch (IOException e) {
System.out.println("something went wrong");
e.printStackTrace();
}
}
}
我想用它来反序列化 json 我无法影响的内容(所以没有添加 "proper" 类型信息的选项)。我遇到的问题是,显然 dishName
json 属性 用于确定子类型,但它没有反序列化到 java 字段中。也有办法实现这一目标吗?换句话说:主要方法打印
null, type: Burger
null, type: Fries
null, type: Food
在控制台上,但我希望它打印出来
burger, type: Burger
fries, type: Fries
cabbage, type: Food
这特别讨厌,因为我无法稍后发现最后一个对象是卷心菜。这抵消了默认实现的好处。
编辑:
@Evil Raat 的回答可以解决问题。为了完整起见:Food
class 中的 dishName
字段需要 @JsonProperty
注释才能使此示例正常工作。因此,工作示例如下所示:
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "dishName", defaultImpl = Food.class, visible = true)
@JsonSubTypes(value = {
@Type(name = "fries", value = Fries.class),
@Type(name = "burger", value = Burger.class)
})
public class Food {
@JsonProperty
private String dishName;
@Override
public String toString() {
return dishName + ", type: " + this.getClass().getName();
}
}
public class Fries extends Food { /*...*/ }
public class Burger extends Food { /*...*/ }
public class TryItOut {
private static String foodString = "[ { \"dishName\":\"burger\" }, { \"dishName\":\"fries\" }, { \"dishName\":\"cabbage\" } ]";
public static void main(String[] args) {
ObjectMapper m = new ObjectMapper();
try {
Food[] food = m.readValue(foodString, Food[].class);
for (Food dish : food) {
System.out.println(dish);
}
} catch (IOException e) {
System.out.println("something went wrong");
e.printStackTrace();
}
}
}
要保持用于反序列化的 属性 的值,您只需在 @JsonSubTypes 注释上将可见的 属性 设置为 true:
@JsonTypeInfo(use = JsonTypeInfo.Id.NAME, include = JsonTypeInfo.As.PROPERTY, property = "dishName", defaultImpl = Food.class, visible = true)