Skip to content

Commit

Permalink
Fix NumberInput.looksLikeValidNumber() implementation (#1241)
Browse files Browse the repository at this point in the history
  • Loading branch information
pjfanning authored Mar 23, 2024
1 parent 1c656ae commit c73bde2
Show file tree
Hide file tree
Showing 5 changed files with 37 additions and 7 deletions.
5 changes: 5 additions & 0 deletions release-notes/VERSION-2.x
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,11 @@ a pure JSON library.
=== Releases ===
------------------------------------------------------------------------

2.17.1 (not yet released)

#1241: Fix `NumberInput.looksLikeValidNumber()` implementation
(contributed by @pjfanning)

2.17.0 (12-Mar-2024)

#507: Add `JsonWriteFeature.ESCAPE_FORWARD_SLASHES` to allow escaping of '/' for
Expand Down
15 changes: 13 additions & 2 deletions src/main/java/com/fasterxml/jackson/core/io/NumberInput.java
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ public final class NumberInput
* @since 2.17
*/
private final static Pattern PATTERN_FLOAT = Pattern.compile(
"[+-]?[0-9]+(\\.[0-9]+)?([eE][+-]?[0-9]+)?");
"[+-]?[0-9]*[\\.]?[0-9]+([eE][+-]?[0-9]+)?");

/**
* Fast method for parsing unsigned integers that are known to fit into
Expand Down Expand Up @@ -570,6 +570,9 @@ public static BigInteger parseBigIntegerWithRadix(final String s, final int radi
*<p>
* Note: no trimming ({@code String.trim()}) nor null checks are performed
* on String passed.
*<p>
* Note: this method returning {@code true} DOES NOT GUARANTEE String is valid
* number but just that it looks close enough.
*
* @param s String to validate
*
Expand All @@ -578,6 +581,14 @@ public static BigInteger parseBigIntegerWithRadix(final String s, final int radi
* @since 2.17
*/
public static boolean looksLikeValidNumber(final String s) {
return (s != null) && PATTERN_FLOAT.matcher(s).matches();
// While PATTERN_FLOAT handles most cases we can optimize some simple ones:
if (s == null || s.isEmpty()) {
return false;
}
if (s.length() == 1) {
char c = s.charAt(0);
return (c <= '9') && (c >= '0');
}
return PATTERN_FLOAT.matcher(s).matches();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@
import com.fasterxml.jackson.core.testsupport.TestSupport;
import com.fasterxml.jackson.core.testsupport.ThrottledInputStream;
import com.fasterxml.jackson.core.testsupport.ThrottledReader;
import org.junit.jupiter.api.Test;

import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.fail;
Expand Down
17 changes: 16 additions & 1 deletion src/test/java/com/fasterxml/jackson/core/io/NumberInputTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
import static org.junit.jupiter.api.Assertions.*;

class NumberInputTest
extends com.fasterxml.jackson.core.JUnit5TestBase
extends com.fasterxml.jackson.core.JUnit5TestBase
{
@Test
void nastySmallDouble()
Expand Down Expand Up @@ -78,12 +78,24 @@ void looksLikeValidNumber()
assertTrue(NumberInput.looksLikeValidNumber("0"));
assertTrue(NumberInput.looksLikeValidNumber("1"));
assertTrue(NumberInput.looksLikeValidNumber("-1"));
assertTrue(NumberInput.looksLikeValidNumber("+1")); // non-JSON
assertTrue(NumberInput.looksLikeValidNumber("0001")); // non-JSON

// https://github.com/FasterXML/jackson-databind/issues/4435
assertTrue(NumberInput.looksLikeValidNumber(".0"));
assertTrue(NumberInput.looksLikeValidNumber(".01"));
assertTrue(NumberInput.looksLikeValidNumber("+.01"));
assertTrue(NumberInput.looksLikeValidNumber("-.01"));
assertTrue(NumberInput.looksLikeValidNumber("-.0"));

assertTrue(NumberInput.looksLikeValidNumber("0.01"));
assertTrue(NumberInput.looksLikeValidNumber("-0.10"));
assertTrue(NumberInput.looksLikeValidNumber("+0.25")); // non-JSON

assertTrue(NumberInput.looksLikeValidNumber("10.33"));
assertTrue(NumberInput.looksLikeValidNumber("-1.39"));
assertTrue(NumberInput.looksLikeValidNumber("+125.0")); // non-JSON

assertTrue(NumberInput.looksLikeValidNumber("1E10"));
assertTrue(NumberInput.looksLikeValidNumber("-1E10"));
assertTrue(NumberInput.looksLikeValidNumber("1e-10"));
Expand All @@ -93,7 +105,10 @@ void looksLikeValidNumber()
assertTrue(NumberInput.looksLikeValidNumber("1.4e+45"));

assertFalse(NumberInput.looksLikeValidNumber(""));
assertFalse(NumberInput.looksLikeValidNumber(" "));
assertFalse(NumberInput.looksLikeValidNumber(" "));
assertFalse(NumberInput.looksLikeValidNumber("."));
assertFalse(NumberInput.looksLikeValidNumber("0."));
assertFalse(NumberInput.looksLikeValidNumber("10_000"));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,9 @@
@SuppressWarnings("resource")
public class TrailingCommasTest extends JUnit5TestBase {

private JsonFactory factory;
private Set<JsonReadFeature> features;
private int mode;
JsonFactory factory;
Set<JsonReadFeature> features;
int mode;

public void initTrailingCommasTest(int mode, List<JsonReadFeature> features) {
this.features = new HashSet<>(features);
Expand Down

0 comments on commit c73bde2

Please sign in to comment.