具有可变JsonProperty的Jackson Generics(使用generics)

我的课程看起来像这样:

public class Data { @JsonProperty("difficulties") private U[] data; // ... geter setter constructor } 

而且我不想再创建10个类似的类,因为我只需要更改一行代码(在这种情况下为@JsonProperty(“困难”))。 属性值取决于Type。 有可能把它写在一个class级吗?

基于Jackson的响应- 在运行时修改属性而没有 MichałZiober的注释 ,我可以通过覆盖PropertyNamingStrategy来更改默认字段名称值:

这些是我收到的JSON示例(简化):

 {"status": "OK","error": null,"data": { "difficulties": [{"value":"easy"},{"value":"medium"}] }} {"status": "ok", "error": null, "data": { "countries": [{"code": "AT"},{"code": "BE"}] }} 

查看数据对象包含困难或国家(或许多其他基于上下文的名称)的第二行的差异。

基于JSON响应的响应类:

 public class Response{ private String status; private String error; private Data data; // Getters Setters Constructors } 

基于JSON响应的数据类:

 public class Data { // property name, that will be changed @JsonProperty(DataNamingStrategy.DATA_FIELD) private T[] data; // Getters Setters Constructors } 

这是命名策略,它将默认值更改为运行时指定的值

 public class DataNamingStrategy extends PropertyNamingStrategy{ // used by other classes (this will be default field name that should be changed) public static final String DATA_FIELD = "variable:data"; private String fieldName; public DataNamingStrategy(String fieldName) { this.fieldName = fieldName; } // use this to change field name (format "variable":"value") not needed in my case @Override public String nameForField(MapperConfig config, AnnotatedField field, String defaultName) { return (defaultName.equals(DATA_FIELD))? fieldName : super.nameForField(config, field, defaultName); } // use this to change setter method field name (JSON -> Object with format "variable":{}) @Override public String nameForSetterMethod(MapperConfig config, AnnotatedMethod method, String defaultName) { return (defaultName.equals(DATA_FIELD))? fieldName : super.nameForGetterMethod(config, method, defaultName); } // use this to change getter method field name (Object -> JSON with format "variable":{}) // should be same as nameForSetterMethod @Override public String nameForGetterMethod(MapperConfig config, AnnotatedMethod method, String defaultName) { return nameForSetterMethod(config, method, defaultName); } } 

用法应如下所示:

 ObjectMapper mapper = new ObjectMapper(); mapper.setPropertyNamingStrategy(new DataNamingStrategy(tableName)); JavaType type = mapper.getTypeFactory().constructParametricType(Response.class, dataClass); Response u = mapper.readValue(result, type); 

result是Json为String, tableName是将在JSON中使用的String而不是默认值,而dataClassU类(例如Difficulty.class)。

更好地使用PropertyNamingStrategy应该是Map而不是一个String 。 但我只需要改变一个特定的值。

另请参阅 PropertyNamingStrategy文档或再次查看MichałZiober的答案

您可以使用@JsonAnyGetter注释。

 public class Data { @JsonIgnore private U[] data; @JsonIgnore private String propertyName; public Data(String propertyName) { this.propertyName = propertyName; } // ... geter setter @JsonAnyGetter public Map any() { return Collections.singletonMap(propertyName, data); } } 

并使用如下:

 Data difficulties = new Data<>("difficulties"); 

写任何你想要的而不是“困难”字符串。 如果需要,将列表设置为Datagenerics类而不是Difficulties对象