@@ -29,7 +29,7 @@ public class MinimumValidator extends BaseJsonValidator implements JsonValidator
2929 private static final Logger logger = LoggerFactory .getLogger (MinimumValidator .class );
3030 private static final String PROPERTY_EXCLUSIVE_MINIMUM = "exclusiveMinimum" ;
3131
32- private boolean excluded = false ;
32+ private boolean excludeEqual = false ;
3333
3434 /**
3535 * In order to limit number of `if` statements in `validate` method, all the
@@ -46,25 +46,32 @@ public MinimumValidator(String schemaPath, JsonNode schemaNode, JsonSchema paren
4646
4747 JsonNode exclusiveMinimumNode = getParentSchema ().getSchemaNode ().get (PROPERTY_EXCLUSIVE_MINIMUM );
4848 if (exclusiveMinimumNode != null && exclusiveMinimumNode .isBoolean ()) {
49- excluded = exclusiveMinimumNode .booleanValue ();
49+ excludeEqual = exclusiveMinimumNode .booleanValue ();
5050 }
5151
5252 parseErrorCode (getValidatorType ().getErrorCodeKey ());
5353
54- if ( schemaNode .isLong () || schemaNode .isInt () && JsonType .INTEGER .toString ().equals (getNodeFieldType ())) {
54+ final String minimumText = schemaNode .asText ();
55+ if ((schemaNode .isLong () || schemaNode .isInt ()) && JsonType .INTEGER .toString ().equals (getNodeFieldType ())) {
5556 // "integer", and within long range
5657 final long lmin = schemaNode .asLong ();
5758 typedMinimum = new ThresholdMixin () {
5859 @ Override
5960 public boolean crossesThreshold (JsonNode node ) {
60- long val = node .asLong ();
61- if (node .isBigInteger ()) {
61+ if (node .isBigInteger ()) {
6262 //node.isBigInteger is not trustable, the type BigInteger doesn't mean it is a big number.
63- if (node .bigIntegerValue ().compareTo (new BigInteger (String .valueOf (Long .MIN_VALUE ))) < 0 ) {
64- return true ;
65- }
63+ int compare = node .bigIntegerValue ().compareTo (new BigInteger (minimumText ));
64+ return compare < 0 || (excludeEqual && compare == 0 );
65+
66+ } else if (node .isTextual ()) {
67+ BigDecimal min = new BigDecimal (minimumText );
68+ BigDecimal value = new BigDecimal (node .asText ());
69+ int compare = value .compareTo (min );
70+ return compare < 0 || (excludeEqual && compare == 0 );
71+
6672 }
67- return lmin > val || (excluded && lmin >= val );
73+ long val = node .asLong ();
74+ return lmin > val || (excludeEqual && lmin == val );
6875 }
6976
7077 @ Override
@@ -77,18 +84,28 @@ public String thresholdValue() {
7784 typedMinimum = new ThresholdMixin () {
7885 @ Override
7986 public boolean crossesThreshold (JsonNode node ) {
80- if (schemaNode .doubleValue () == Double .NEGATIVE_INFINITY ) {
87+ // jackson's BIG_DECIMAL parsing is limited. see https://github.com/FasterXML/jackson-databind/issues/1770
88+ if (schemaNode .isDouble () && schemaNode .doubleValue () == Double .NEGATIVE_INFINITY ) {
89+ return false ;
90+ }
91+ if (schemaNode .isDouble () && schemaNode .doubleValue () == Double .POSITIVE_INFINITY ) {
92+ return true ;
93+ }
94+ if (node .isDouble () && node .doubleValue () == Double .NEGATIVE_INFINITY ) {
95+ return true ;
96+ }
97+ if (node .isDouble () && node .doubleValue () == Double .POSITIVE_INFINITY ) {
8198 return false ;
8299 }
83- final BigDecimal min = new BigDecimal (schemaNode .asText ());
84- if (node .doubleValue () == Double .NEGATIVE_INFINITY ) {return true ;}
100+ final BigDecimal min = new BigDecimal (minimumText );
85101 BigDecimal value = new BigDecimal (node .asText ());
86- return value .compareTo (min ) < 0 || (excluded && value .compareTo (min ) == 0 );
102+ int compare = value .compareTo (min );
103+ return compare < 0 || (excludeEqual && compare == 0 );
87104 }
88105
89106 @ Override
90107 public String thresholdValue () {
91- return schemaNode . asText () ;
108+ return minimumText ;
92109 }
93110 };
94111 }
0 commit comments