【问题标题】:Can't get Jackson filtering to work无法让杰克逊过滤工作
【发布时间】:2017-12-21 06:35:19
【问题描述】:

第一次使用 Jackson 过滤器时,我很惊讶地发现它根本不起作用。这是我刚刚写的测试代码:

@Test
public void testJsonSerialization() throws JsonProcessingException {
    Principal princi = Principal.builder().fullName("John Smith").role(Role.USER).build().setAccountType(CHILD)
        .setClassAttended(Classes.C10);

    SimpleBeanPropertyFilter filter = SimpleBeanPropertyFilter.filterOutAllExcept("fullName");
    FilterProvider provider = new SimpleFilterProvider().addFilter("bareBonesFilter", filter);
    JsonFilter jFilter = Principal.class.getAnnotation(JsonFilter.class);
    assertNotNull(jFilter); // passes
    assertEquals("bareBonesFilter", jFilter.value()); // passes
    provider.findPropertyFilter("bareBonesFilter", princi); // doesn't throw exception, therefore a filter was found

    ObjectWriter writer = (new ObjectMapper()).setSerializationInclusion(Include.NON_ABSENT)
        .enable(SerializationFeature.INDENT_OUTPUT).writer(provider);
    String json = writer.writeValueAsString(princi);
    assertFalse(json.contains("accountType")); //this fails
}

使用杰克逊 2.7.1。

我错过了什么?我需要在某处添加一些特殊配置以启用过滤器吗?

更新 1

按照@StaxMan 的建议,我用 2.7.9 和 2.9.4 尝试了上述代码,但都没有成功。

然后,我没有使用Principal 类(它变得庞大而复杂),而是使用更简单的SgEmailInfo 类(它只是一个数据持有者)尝试了上面的代码,并且过滤按预期工作!

@Data
@Accessors(chain = true)
@JsonFilter("bareBonesFilter")
public class SgEmailInfo {

    private long created;

    private String email;

    private String reason;

    private String status;

}

@Data@AccessorsLombok 注释,用于自动生成一些代码。 Principal 类也使用这些注解以及其他 Lombok 注解:

@Entity //Objectify annotation
@Cache(expirationSeconds = 600) //Objectify annotation
@Data
@EqualsAndHashCode(of = "id", callSuper = false) // Lombok
@ToString(callSuper = true, doNotUseGetters = true, of = { "id", "firstName", "middleName",
        "lastName", "profileName", "roles" }) // Lombok
@Accessors(chain = true)
@JsonFilter("bareBonesFilter")
public class Principal extends AccountEntity<Principal, EmailPrincipal>
        implements Serializable, ProfileShort, ProfileMedium

我还在Principal 的许多属性和吸气剂上使用@JsonIgnore 注释。

Principal 的构造函数上还有 @Builder 注释:

@Builder
private Principal(String fullName, @Singular List<Role> roles)

Lombok 生成的这些注释或代码是否会干扰过滤?

【问题讨论】:

  • 首先要使用更现代的版本。在 2.7 中,有很多很多补丁(2.7.9),最新的一般是 2.9.4。
  • 是的,Lombok 是...有点 PITA,因为它以一种可能无法与其他库配合使用(或至少不会立即可见)的方式增加注释。

标签: java json lombok jackson2


【解决方案1】:

代码对我来说似乎是合法的。在尝试了更新的版本(以确保它不是已经修复的错误)之后,您可以针对jackson-databind 提交错误吗?可能我在上面的代码中遗漏了一些问题,但这并不是很明显,所以它有可能是一个错误。

【讨论】:

  • 我尝试使用 2.7.9 和 2.9.4,但无法正确过滤 Principal 类的属性。一个更简单的SgEmailInfo 类可以正确过滤。请参阅上面的更新 1
  • 我怀疑 Lombok 参与其中,但不知道具体如何:它更常见地导致反序列化期间的创建问题。如果将 Lombok 构造替换为等效(隐式添加到字节码)的测试用例可以重现问题,那么提交问题是有意义的。
  • JsonIgnore 的存在应该不会对过滤产生任何影响?
  • @markvgti 应该;任何@JsonIgnores 都应该被完全忽略,而不是提交给过滤器。它是静态设置,基本上删除属性(或访问它,无论如何,并在反序列化的情况下添加到“已知和可忽略”集)。
猜你喜欢
  • 2013-12-12
  • 1970-01-01
  • 1970-01-01
  • 2017-01-15
  • 2021-07-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-04-02
相关资源
最近更新 更多