与Jackson和Mockito反序列化时的无限递归

时间:2018-10-05 18:01:15

标签: java hibernate jackson mockito jackson-databind

我正在尝试使用dependencies { compile 'cn.pedant.sweetalert:library:1.3' }来打印任何对象,但是在使用Mockito和Jackson进行对象反序列化时,我面临着无限递归的问题。我尝试反序列化的对象执行对数据库等的基础Hibernate调用,而我无法控制类本身。

当前,我正在使用以下版本的Mockito和Jackson,但对于较旧的1.X版本的Jackson,情况也是如此。

  • Mockito:mapper.writeValueAsString
  • Jackson:org.mockito:mockito-all:jar:1.9.5:compile

如所指定的,我不能用诸如com.fasterxml.jackson.core:jackson-databind:jar:2.9.7:compile之类的注释来修改基础类,因为它们不在我的控制范围内。我也无法为我的用例创建mixins,因为我试图以一般方式打印发送来的任何对象的内容。

我曾尝试在较旧的Jackson版本中将@JsonIgnore添加到DeserializationConfig FAIL_ON_UNKNOWN_PROPERTIES,并且尝试将false设置为DeserializationFeature FAIL_ON_MISSING_CREATOR_PROPERTIES

false

当对包含Log4j语句的方法运行Mockito测试时,可以看到无限递归终端输出,这些语句又调用PrintUtil函数。语句import com.fasterxml.jackson.core.JsonProcessingException; import com.fasterxml.jackson.databind.ObjectMapper; public static PrintUtil { public static String printJSON(Object obj) { String printstring = "printfailed"; try { ObjectMapper mapper = new ObjectMapper(); LOG.debug("formatted JSON String "); printstring = mapper.writeValueAsString(obj); } catch (JsonProcessingException e) { e.printStackTrace(); } return printstring; } } 在运行测试时开始打印。

发送到此实用程序方法的大多数对象是JAXB XML服务响应对象。

1 个答案:

答案 0 :(得分:0)

在无法自行修改类的情况下,我看到了两种可能的解决方案。

1)按照@TheHeadRush的建议将对象包装为您拥有的对象,并对其进行适当的注释。我建议使用@JsonIdentityInfo,以便将对象序列化为其ID,而不是被@JsonIgnore完全忽略。

2)对引起递归的对象使用自定义解串器。这是一个示例:

public class CustomDeserializer extends StdDeserializer<MyObject>{

   // Add constructors as necessary.

    @Override
    public List<Item> deserialize(
      JsonParser jsonparser, 
      DeserializationContext context) 
      throws IOException, JsonProcessingException {
       return null; // Return something that won't recurse here.
    }
}

然后向正在使用的ObjectMapper注册反序列化器:

// Register the deserializer:
SimpleModule module = new SimpleModule()
    .addDeserializer(MyObject.class, new CustomDeserializer());

ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(module);