【问题标题】:Jackson with JSON: private attributes instead of public杰克逊与 JSON:私有属性而不是公共
【发布时间】:2018-07-17 23:29:27
【问题描述】:

我正在尝试反序列化以下 JSON:

{
   "name": "TEST",
   "data": [["Toto", true, 42], ["ABC", "DEF", false]]
}

“data”值是 JSON 元素列表(字符串、整数或布尔值)。

我使用具有公共属性的简单 POJO 使其工作:

public class MyDecoder {
  public String name;
  public List<List<Object>> data;
}

但是现在,我希望我的属性是私有的,所以我使用了构造函数:

public class MyDecoder {
  private String name;
  private List<List<Object>> data;

  public MyDecoder() {
  }

  @JsonCreator
  public MyDecoder(
      @JsonProperty("name") String name,
      @JsonProperty("data") List<List<Object>> data)
  {
    this.name = name;
    this.data = data;
  }
}

但这失败了:

org.codehaus.jackson.map.exc.UnrecognizedPropertyException: 无法识别的字段“数据”(Class XXX.MyDecoder),未标记为 无视

我错过了什么? 我猜它与List&lt;List&lt;Object&gt;&gt; data 有关,因为Jackson 对String name 没有任何问题。 但是,我不明白为什么它在具有公共属性的版本中起作用。

我正在使用杰克逊 2.7.5。

谢谢!

【问题讨论】:

  • 也许吧。吸气剂和二传手。 .

标签: java json jackson


【解决方案1】:

关于警告,如果有一个 JSON 属性没有任何方法可以设置(通过可见的 setter 或字段,或带有 @JsonProperty 注释参数的 @JsonCreator 注释构造函数),将抛出异常 -- 除非配置已更改为忽略此类“未知”属性。

你试过这种方法吗

public class MyDecoder {

@JsonProperty("name")
private String name;
@JsonProperty("data")
  private List<List<Object>> data;

  public MyDecoder() {
  }

  @JsonCreator
  public MyDecoder(
       String name,
       List<List<Object>> data)
  {
    this.name = name;
    this.data = data;
  }
}

【讨论】:

  • 同样的问题...谢谢。
  • 可能是对象的问题:D
【解决方案2】:

尝试添加 getter 和 setter:

public class MyDecoder {
    public String name;
    public List<List<Object>> data;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public List<List<Object>> getData() {
        return data;
    }

    public void setData(List<List<Object>> data) {
        this.data = data;
    }
}

并对其进行测试:

public class Test {

    public static void main(String[] args) throws IOException {
        ObjectMapper objectMapper = new ObjectMapper();
        MyDecoder myDecoder = objectMapper.readValue("{\n" +
                "   \"name\": \"TEST\",\n" +
                "   \"data\": [[\"Toto\", true, 42], [\"ABC\", \"DEF\", false]]\n" +
                "}", MyDecoder.class);

        System.out.println(myDecoder.toString());
    }

}

【讨论】:

  • 谢谢,成功了!令人惊讶的是,添加“void setData(List> data)”并删除构造函数完成了这项工作,即使没有 setName()!如果有人能解释为什么...
  • 但是,我仍然想让它与构造函数一起使用。添加 get/set 就像将属性公开...
猜你喜欢
  • 1970-01-01
  • 2017-12-09
  • 2020-04-16
  • 2017-09-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多