From 1e3f11cbc24c96f9a72037493bf3db65c4177acc Mon Sep 17 00:00:00 2001 From: mchmielarz Date: Tue, 5 Jan 2016 14:16:40 +0100 Subject: [PATCH] Solution proposal for #181 --- .../internal/filter/EvaluatorFactory.java | 25 ++++-- .../internal/filter/RegexpEvaluatorTest.java | 76 +++++++++++++++++++ 2 files changed, 96 insertions(+), 5 deletions(-) create mode 100644 json-path/src/test/java/com/jayway/jsonpath/internal/filter/RegexpEvaluatorTest.java diff --git a/json-path/src/main/java/com/jayway/jsonpath/internal/filter/EvaluatorFactory.java b/json-path/src/main/java/com/jayway/jsonpath/internal/filter/EvaluatorFactory.java index 43b705a4..6831920c 100644 --- a/json-path/src/main/java/com/jayway/jsonpath/internal/filter/EvaluatorFactory.java +++ b/json-path/src/main/java/com/jayway/jsonpath/internal/filter/EvaluatorFactory.java @@ -240,13 +240,28 @@ public class EvaluatorFactory { if(!(left.isPatternNode() ^ right.isPatternNode())){ return false; } - if(!(left.isStringNode() ^ right.isStringNode())){ - return false; + + if (left.isPatternNode()) { + return matches(left.asPatternNode(), getInput(right)); + } else { + return matches(right.asPatternNode(), getInput(left)); + } + } + + private boolean matches(ValueNode.PatternNode patternNode, String inputToMatch) { + return patternNode.getCompiledPattern().matcher(inputToMatch).matches(); + } + + private String getInput(ValueNode valueNode) { + String input = ""; + + if (valueNode.isStringNode() || valueNode.isNumberNode()) { + input = valueNode.asStringNode().getString(); + } else if (valueNode.isBooleanNode()) { + input = valueNode.asBooleanNode().toString(); } - ValueNode.PatternNode patternNode = left.isPatternNode() ? left.asPatternNode() : right.asPatternNode(); - ValueNode.StringNode stringNode = left.isStringNode() ? left.asStringNode() : right.asStringNode(); - return patternNode.getCompiledPattern().matcher(stringNode.getString()).matches(); + return input; } } } diff --git a/json-path/src/test/java/com/jayway/jsonpath/internal/filter/RegexpEvaluatorTest.java b/json-path/src/test/java/com/jayway/jsonpath/internal/filter/RegexpEvaluatorTest.java new file mode 100644 index 00000000..614f6b6c --- /dev/null +++ b/json-path/src/test/java/com/jayway/jsonpath/internal/filter/RegexpEvaluatorTest.java @@ -0,0 +1,76 @@ +package com.jayway.jsonpath.internal.filter; + +import com.jayway.jsonpath.BaseTest; +import com.jayway.jsonpath.Predicate; +import com.jayway.jsonpath.internal.Path; +import com.jayway.jsonpath.internal.path.CompiledPath; +import com.jayway.jsonpath.internal.path.PathTokenFactory; +import org.assertj.core.util.Maps; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.junit.runners.Parameterized; + +import java.util.Arrays; + +import static org.hamcrest.CoreMatchers.equalTo; +import static org.hamcrest.CoreMatchers.is; +import static org.junit.Assert.assertThat; + +import static com.jayway.jsonpath.internal.filter.ValueNode.*; + +@RunWith(Parameterized.class) +public class RegexpEvaluatorTest extends BaseTest { + + private String regexp; + private ValueNode valueNode; + private boolean expectedResult; + + public RegexpEvaluatorTest(String regexp, ValueNode valueNode, boolean expectedResult) { + this.regexp = regexp; + this.valueNode = valueNode; + this.expectedResult = expectedResult; + } + + @Test + public void should_evaluate_regular_expression() { + //given + Evaluator evaluator = EvaluatorFactory.createEvaluator(RelationalOperator.REGEX); + ValueNode patternNode = createPatternNode(regexp); + Predicate.PredicateContext ctx = createPredicateContext(); + + //when + boolean result = evaluator.evaluate(patternNode, valueNode, ctx); + + //then + assertThat(result, is(equalTo(expectedResult))); + } + + @Parameterized.Parameters(name="Regexp {0} for {1} node should evaluate to {2}") + public static Iterable data() { + return Arrays.asList( + new Object[][]{ + { "/true|false/", createStringNode("true", true), true }, + { "/9.*9/", createNumberNode("9979"), true }, + { "/fa.*se/", createBooleanNode("false"), true }, + { "/Eval.*or/", createClassNode(String.class), false }, + { "/JsonNode/", createJsonNode(json()), false }, + { "/PathNode/", createPathNode(path()), false }, + { "/Undefined/", createUndefinedNode(), false }, + { "/NullNode/", createNullNode(), false } + } + ); + } + + private static Path path() { + return new CompiledPath(PathTokenFactory.createRootPathToken('$'), true); + } + + private static String json() { + return "{ 'some': 'JsonNode' }"; + } + + private Predicate.PredicateContext createPredicateContext() { + return createPredicateContext(Maps.newHashMap()); + } + +}