Skip to content

Commit 92718cf

Browse files
committed
Fix #3450
1 parent 7b6d91d commit 92718cf

File tree

3 files changed

+100
-2
lines changed

3 files changed

+100
-2
lines changed

release-notes/VERSION-2.x

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,9 @@ Project: jackson-databind
1616
JSON `null` values on reading
1717
#3445: Do not strip generic type from `Class<C>` when resolving `JavaType`
1818
(contributed by Jan J)
19+
#3450: DeserializationProblemHandler is not working with wrapper type
20+
when returning null
21+
(reported by LJeanneau@github)
1922

2023
2.13.3 (not yet released)
2124

src/main/java/com/fasterxml/jackson/databind/deser/std/StdDeserializer.java

Lines changed: 37 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -754,6 +754,7 @@ protected final int _parseIntPrimitive(DeserializationContext ctxt, String text)
754754
{
755755
try {
756756
if (text.length() > 9) {
757+
// NOTE! Can NOT call "NumberInput.parseLong()" due to lack of validation there
757758
long l = Long.parseLong(text);
758759
if (_intOverflow(l)) {
759760
Number v = (Number) ctxt.handleWeirdStringValue(Integer.TYPE, text,
@@ -817,7 +818,29 @@ protected final Integer _parseInteger(JsonParser p, DeserializationContext ctxt,
817818
if (_checkTextualNull(ctxt, text)) {
818819
return (Integer) getNullValue(ctxt);
819820
}
820-
return _parseIntPrimitive(ctxt, text);
821+
return _parseInteger(ctxt, text);
822+
}
823+
824+
/**
825+
* @since 2.14
826+
*/
827+
protected final Integer _parseInteger(DeserializationContext ctxt, String text) throws IOException
828+
{
829+
try {
830+
if (text.length() > 9) {
831+
long l = NumberInput.parseLong(text);
832+
if (_intOverflow(l)) {
833+
return (Integer) ctxt.handleWeirdStringValue(Integer.class, text,
834+
"Overflow: numeric value (%s) out of range of `java.lang.Integer` (%d -%d)",
835+
text, Integer.MIN_VALUE, Integer.MAX_VALUE);
836+
}
837+
return Integer.valueOf((int) l);
838+
}
839+
return NumberInput.parseInt(text);
840+
} catch (IllegalArgumentException iae) {
841+
return(Integer) ctxt.handleWeirdStringValue(Integer.class, text,
842+
"not a valid `java.lang.Integer` value");
843+
}
821844
}
822845

823846
protected final long _parseLongPrimitive(JsonParser p, DeserializationContext ctxt)
@@ -938,7 +961,19 @@ protected final Long _parseLong(JsonParser p, DeserializationContext ctxt,
938961
return (Long) getNullValue(ctxt);
939962
}
940963
// let's allow Strings to be converted too
941-
return _parseLongPrimitive(ctxt, text);
964+
return _parseLong(ctxt, text);
965+
}
966+
967+
/**
968+
* @since 2.14
969+
*/
970+
protected final Long _parseLong(DeserializationContext ctxt, String text) throws IOException
971+
{
972+
try {
973+
return NumberInput.parseLong(text);
974+
} catch (IllegalArgumentException iae) { }
975+
return (Long) ctxt.handleWeirdStringValue(Long.class, text,
976+
"not a valid `java.lang.Long` value");
942977
}
943978

944979
protected final float _parseFloatPrimitive(JsonParser p, DeserializationContext ctxt)
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
package com.fasterxml.jackson.databind.deser.filter;
2+
3+
import java.io.IOException;
4+
5+
import com.fasterxml.jackson.databind.*;
6+
import com.fasterxml.jackson.databind.deser.DeserializationProblemHandler;
7+
import com.fasterxml.jackson.databind.json.JsonMapper;
8+
9+
public class ProblemHandler3450Test extends BaseMapTest
10+
{
11+
// [databind#3450]
12+
13+
static class LenientDeserializationProblemHandler extends DeserializationProblemHandler {
14+
15+
@Override
16+
public Object handleWeirdStringValue(DeserializationContext ctxt, Class<?> targetType, String valueToConvert,
17+
String failureMsg) throws IOException {
18+
19+
// I just want to ignore badly formatted value
20+
return null;
21+
}
22+
}
23+
24+
static class TestPojo3450Int {
25+
public Integer myInteger;
26+
}
27+
28+
static class TestPojo3450Long {
29+
public Long myLong;
30+
}
31+
32+
private final ObjectMapper LENIENT_MAPPER =
33+
JsonMapper.builder().addHandler(new LenientDeserializationProblemHandler()).build();
34+
35+
public void testIntegerCoercion3450() throws Exception
36+
{
37+
TestPojo3450Int pojo;
38+
39+
// First expected coercion into `null` from empty String
40+
pojo = LENIENT_MAPPER.readValue("{\"myInteger\" : \"\"}", TestPojo3450Int.class);
41+
assertNull(pojo.myInteger);
42+
43+
// and then coercion into `null` by our problem handler
44+
pojo = LENIENT_MAPPER.readValue("{\"myInteger\" : \"notInt\"}", TestPojo3450Int.class);
45+
assertNull(pojo.myInteger);
46+
}
47+
48+
public void testLongCoercion3450() throws Exception
49+
{
50+
TestPojo3450Long pojo;
51+
52+
// First expected coercion into `null` from empty String
53+
pojo = LENIENT_MAPPER.readValue("{\"myLong\" : \"\"}", TestPojo3450Long.class);
54+
assertNull(pojo.myLong);
55+
56+
// and then coercion into `null` by our problem handler
57+
pojo = LENIENT_MAPPER.readValue("{\"myLong\" : \"notSoLong\"}", TestPojo3450Long.class);
58+
assertNull(pojo.myLong);
59+
}
60+
}

0 commit comments

Comments
 (0)