ObjectIdWithReader5542Test.java
package tools.jackson.databind.objectid;
import org.junit.jupiter.api.Test;
import com.fasterxml.jackson.annotation.JsonIdentityInfo;
import com.fasterxml.jackson.annotation.ObjectIdGenerators;
import tools.jackson.core.JsonParser;
import tools.jackson.databind.*;
import tools.jackson.databind.deser.UnresolvedForwardReference;
import tools.jackson.databind.testutil.DatabindTestUtil;
import static org.junit.jupiter.api.Assertions.*;
/**
* [databind#5542]
* Test to verify that {@link ObjectReader} properly handles
* {@link DeserializationFeature#FAIL_ON_UNRESOLVED_OBJECT_IDS}
* when using {@code readValue(JsonParser)}.
*/
public class ObjectIdWithReader5542Test extends DatabindTestUtil
{
static class Wrapper {
public ValueNode node;
}
@JsonIdentityInfo(generator=ObjectIdGenerators.IntSequenceGenerator.class, property="@id")
static class ValueNode {
public int value;
public Wrapper next;
}
private final ObjectMapper MAPPER = newJsonMapper();
/**
* Test that ObjectMapper.readValue() correctly throws exception for unresolved object IDs
* when FAIL_ON_UNRESOLVED_OBJECT_IDS is enabled (default).
*/
@Test
public void testObjectMapperFailsOnUnresolvedObjectIds() throws Exception {
String json = a2q("{'node':{'@id':1,'value':7,'next':{'node':2}}}");
try {
MAPPER.readValue(json, Wrapper.class);
fail("Should have thrown UnresolvedForwardReference");
} catch (UnresolvedForwardReference e) {
verifyException(e, "Unresolved forward reference");
}
}
/**
* Test that ObjectReader.readValue(JsonParser) also throws exception for unresolved object IDs
* when FAIL_ON_UNRESOLVED_OBJECT_IDS is enabled (default).
*
* This is the bug: ObjectReader.readValue(JsonParser) doesn't call checkUnresolvedObjectId()
*/
@Test
public void testObjectReaderFailsOnUnresolvedObjectIds() throws Exception {
String json = a2q("{'node':{'@id':1,'value':7,'next':{'node':2}}}");
ObjectReader reader = MAPPER.readerFor(Wrapper.class);
try (JsonParser p = MAPPER.createParser(json)) {
reader.readValue(p);
fail("Should have thrown UnresolvedForwardReference");
} catch (UnresolvedForwardReference e) {
verifyException(e, "Unresolved forward reference");
}
}
/**
* Test that ObjectReader with disabled FAIL_ON_UNRESOLVED_OBJECT_IDS
* returns null for unresolved object IDs.
*/
@Test
public void testObjectReaderWithDisabledFeature() throws Exception {
String json = a2q("{'node':{'@id':1,'value':7,'next':{'node':2}}}");
ObjectReader reader = MAPPER.readerFor(Wrapper.class)
.without(DeserializationFeature.FAIL_ON_UNRESOLVED_OBJECT_IDS);
try (JsonParser p = MAPPER.createParser(json)) {
Wrapper wrapper = reader.readValue(p);
assertNotNull(wrapper);
assertNotNull(wrapper.node);
assertNull(wrapper.node.next.node); // Unresolved reference should be null
}
}
/**
* Test that ObjectReader works correctly when all object IDs are resolved.
*/
@Test
public void testObjectReaderWithResolvedObjectIds() throws Exception {
String json = a2q("{'node':{'@id':1,'value':7,'next':{'node':1}}}");
ObjectReader reader = MAPPER.readerFor(Wrapper.class);
try (JsonParser p = MAPPER.createParser(json)) {
Wrapper wrapper = reader.readValue(p);
assertNotNull(wrapper);
assertNotNull(wrapper.node);
assertSame(wrapper.node, wrapper.node.next.node); // Should be same object
}
}
}