我有一个带有lombok注释的POJO,我的JSON通过Jackson反序列化,如下所示:
@Getter
@ToString
@NoArgsConstructor
@Builder
@AllArgsConstructor
@EqualsAndHashCode
@JsonIgnoreProperties(ignoreUnknown = true)
public class ResponsePOJO {
@JsonProperty("list-one")
private List<Object> list1 = Lists.newArrayList;
@JsonProperty("list-two")
private List<Object> list2 = Lists.newArrayList;
@JsonProperty("list-three")
private List<Object> list3 = Lists.newArrayList;
@JsonProperty("list-four")
private List<Object> list4 = Lists.newArrayList;
}
当杰克逊试图反序列化只有列表1和1的响应时list-two存在,我希望生成的POJO具有属性list3
和list4
作为空列表,这是默认值,而是将它们反序列化为null
。
确保所有属性都包含来自反序列化JSON的相应值或空列表(默认分配值)缺少什么?
--- ----更新 直到我从Spring 1.3.5升级到1.4.2之后才出现问题,这也将我的Jackson版本从2.6.6升级到2.8.4
答案 0 :(得分:0)
问题是您还要添加@Builder
。初始化程序将移动到构建器,因为您不想运行代码两次。
lombok的最新版本(1.16.16+)有@ Builder.Default可用于影响该行为。
您可以指示Jackson使用构建器,并使您的对象不可变。 Builder适用于不可变对象。
披露:我是一名lombok开发者。
答案 1 :(得分:0)
龙目岛的var userId = new Guid("96d5b379-7e1d-4dac-a6ba-1e50db561b04");
objDB.AddInParameter(objcmd, "@UserID", SqlDbType.UniqueIdentifier, userId);
在这里不是直接的问题,因为杰克逊并没有将它用于反序列化。但是,Jackson正在使用带有args的非默认构造函数(如果可用)用于对象实例化。否则它使用非arg构造函数。当您在@Builder
上使用@AllArgsConstructor
时,杰克逊会创建一个如下所示的构造函数:
ResponsePOJO
当调用此构造函数时,将丢弃您的默认值,并为JSON中不存在的字段分配public ResponsePOJO(List<Object> list1, List<Object> list2, List<Object> list3, List<Object> list4) {
this.list1 = list1;
this.list2 = list2;
this.list3 = list3;
this.list4 = list4;
}
。
虽然null
需要所有参数构造函数,但您无法解决问题:
@Builder
并删除@Builder
- 有时您可能不需要这些,但这取决于您的情况@AllArgsConstructor
并创建自定义构建器,该构建器不使用里面的所有参数构造函数,但是使用no-arg构造函数。使用@AllArgsConstructor
并创建与此类似的自定义所有参数构造函数:
@Builder
这里Jackson仍会调用上面的所有参数构造函数,但是如果某些字段不存在或者存在且为null(如果在某些情况下您可能期望空值,例如对无效的验证,则可能会对您的业务逻辑产生下游影响) ,它将始终分配空列表。
答案 2 :(得分:0)
我遇到了类似的问题,使用Jackson(com.fasterxml.jackson)和Lombok的@Builder注释反序列化JSON对象。我能够通过在类中创建一个用@JsonPOJOBuilder注释的空类Builder类来解决这个问题,然后添加一个带有对空类的引用的@JsonDeserialize。您可以找到更多信息here
例如,
@Getter
@ToString
@NoArgsConstructor
@Builder
@AllArgsConstructor
@EqualsAndHashCode
@JsonIgnoreProperties(ignoreUnknown = true)
@JsonDeserialize(builder = ResponsePOJO.TypeBuilder.class)
public class ResponsePOJO {
@JsonPOJOBuilder(withPrefix = "")
@JsonIgnoreProperties(ModelUtils.TYPE_INFO_PROPERTY)
public static class TypeBuilder{}//Empty builder class
//Needed just to apply annotations
//Lombok will fill it in later.
@JsonProperty("list-one")
private List<Object> list1 = Lists.newArrayList;
@JsonProperty("list-two")
private List<Object> list2 = Lists.newArrayList;
@JsonProperty("list-three")
private List<Object> list3 = Lists.newArrayList;
@JsonProperty("list-four")
private List<Object> list4 = Lists.newArrayList;
}