diff --git a/jsurfer-core/src/main/java/org/jsfr/json/BuilderFactory.java b/jsurfer-core/src/main/java/org/jsfr/json/BuilderFactory.java deleted file mode 100644 index 25e5816..0000000 --- a/jsurfer-core/src/main/java/org/jsfr/json/BuilderFactory.java +++ /dev/null @@ -1,39 +0,0 @@ -/* - * The MIT License - * - * Copyright (c) 2015 WANG Lingsong - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ - -package org.jsfr.json; - -import org.jsfr.json.path.JsonPath; - -public class BuilderFactory { - - public static SurfingConfiguration.Builder config() { - return SurfingConfiguration.builder(); - } - - public static JsonPath.Builder root() { - return JsonPath.Builder.start(); - } - -} diff --git a/jsurfer-core/src/main/java/org/jsfr/json/JsonSurfer.java b/jsurfer-core/src/main/java/org/jsfr/json/JsonSurfer.java index 841f1d3..73f4aac 100644 --- a/jsurfer-core/src/main/java/org/jsfr/json/JsonSurfer.java +++ b/jsurfer-core/src/main/java/org/jsfr/json/JsonSurfer.java @@ -34,7 +34,6 @@ import java.io.StringReader; import java.util.Collection; -import static org.jsfr.json.SurfingConfiguration.builder; import static org.jsfr.json.compiler.JsonPathCompiler.compile; @@ -88,8 +87,21 @@ public JsonSurfer(JsonParserAdapter jsonParserAdapter, JsonProvider jsonProvider this.errorHandlingStrategy = errorHandlingStrategy; } + /** + * Create SurfingConfiguration builder associated with this surfer + * + * @return SurfingConfiguration builder + */ + public SurfingConfiguration.Builder builder() { + return SurfingConfiguration.builder().withSurfer(this); + } + + /** + * @param json json + * @param configuration SurfingConfiguration that holds JsonPath binding + */ public void surf(String json, SurfingConfiguration configuration) { - surf(new StringReader(json), configuration); + surf(read(json), configuration); } /** @@ -102,7 +114,7 @@ public void surf(Reader reader, SurfingConfiguration configuration) { } public Collection collectAll(String json, JsonPath... paths) { - return collectAll(new StringReader(json), paths); + return collectAll(read(json), paths); } /** @@ -116,8 +128,15 @@ public Collection collectAll(Reader reader, JsonPath... paths) { return collectAll(reader, Object.class, paths); } + /** + * @param json json + * @param tClass target class + * @param paths JsonPath + * @param target class + * @return typed value + */ public Collection collectAll(String json, Class tClass, JsonPath... paths) { - return collectAll(new StringReader(json), tClass, paths); + return collectAll(read(json), tClass, paths); } /** @@ -139,8 +158,15 @@ public Collection collectAll(Reader reader, Class tClass, JsonPath... return listener.getCollection(); } + /** + * @param json json + * @param tClass target class + * @param paths JsonPath + * @param target class + * @return typed value + */ public Collection collectAll(String json, Class tClass, String... paths) { - return collectAll(new StringReader(json), tClass, paths); + return collectAll(read(json), tClass, paths); } /** @@ -157,7 +183,7 @@ public Collection collectAll(Reader reader, Class tClass, String... pa } public Collection collectAll(String json, String... paths) { - return collectAll(new StringReader(json), paths); + return collectAll(read(json), paths); } /** @@ -172,7 +198,7 @@ public Collection collectAll(Reader reader, String... paths) { } public Object collectOne(String json, JsonPath... paths) { - return collectOne(new StringReader(json), paths); + return collectOne(read(json), paths); } /** @@ -187,7 +213,7 @@ public Object collectOne(Reader reader, JsonPath... paths) { } public T collectOne(String json, Class tClass, JsonPath... paths) { - return collectOne(new StringReader(json), tClass, paths); + return collectOne(read(json), tClass, paths); } /** @@ -212,7 +238,7 @@ public T collectOne(Reader reader, Class tClass, JsonPath... paths) { } public T collectOne(String json, Class tClass, String... paths) { - return collectOne(new StringReader(json), tClass, paths); + return collectOne(read(json), tClass, paths); } /** @@ -228,8 +254,13 @@ public T collectOne(Reader reader, Class tClass, String... paths) { return collectOne(reader, tClass, compile(paths)); } + /** + * @param json json + * @param paths JsonPath + * @return value + */ public Object collectOne(String json, String... paths) { - return collectOne(new StringReader(json), paths); + return collectOne(read(json), paths); } /** @@ -252,4 +283,8 @@ private void ensureSetting(SurfingConfiguration configuration) { } } + public Reader read(String json) { + return new StringReader(json); + } + } diff --git a/jsurfer-core/src/main/java/org/jsfr/json/SurfingConfiguration.java b/jsurfer-core/src/main/java/org/jsfr/json/SurfingConfiguration.java index 9ff61a5..81adc9f 100644 --- a/jsurfer-core/src/main/java/org/jsfr/json/SurfingConfiguration.java +++ b/jsurfer-core/src/main/java/org/jsfr/json/SurfingConfiguration.java @@ -27,6 +27,7 @@ import org.jsfr.json.path.JsonPath; import org.jsfr.json.provider.JsonProvider; +import java.io.Reader; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; @@ -78,6 +79,7 @@ public int compare(IndefinitePathBinding o1, IndefinitePathBinding o2) { public static class Builder { + private JsonSurfer jsonSurfer; private SurfingConfiguration configuration; private Map> definiteBindings = new HashMap>(); private ArrayList indefiniteBindings = new ArrayList(); @@ -96,6 +98,32 @@ public SurfingConfiguration build() { return configuration; } + /** + * Associated with a JsonSurfer + * @param jsonSurfer JsonSurfer + * @return builder + */ + public Builder withSurfer(JsonSurfer jsonSurfer) { + this.jsonSurfer = jsonSurfer; + return this; + } + + /** + * Build the configuration and then surf with it and the associated JsonSurfer + * @param json json + */ + public void surf(String json) { + this.surf(this.jsonSurfer.read(json)); + } + + /** + * Build the configuration and then surf with it and the associated JsonSurfer + * @param jsonReader jsonReader + */ + public void surf(Reader jsonReader) { + this.jsonSurfer.surf(jsonReader, this.build()); + } + public Builder bind(String path, JsonPathListener... jsonPathListeners) { return bind(compile(path), jsonPathListeners); } diff --git a/jsurfer-core/src/test/java/org/jsfr/json/JsonSurferTest.java b/jsurfer-core/src/test/java/org/jsfr/json/JsonSurferTest.java index 795b36f..e28f648 100644 --- a/jsurfer-core/src/test/java/org/jsfr/json/JsonSurferTest.java +++ b/jsurfer-core/src/test/java/org/jsfr/json/JsonSurferTest.java @@ -27,7 +27,6 @@ import com.google.common.io.Resources; import org.hamcrest.Description; import org.hamcrest.TypeSafeMatcher; -import org.jsfr.json.SurfingConfiguration.Builder; import org.jsfr.json.provider.JavaCollectionProvider; import org.jsfr.json.provider.JsonProvider; import org.jsfr.json.provider.JsonSimpleProvider; @@ -42,7 +41,6 @@ import java.util.HashMap; import java.util.Iterator; -import static org.jsfr.json.BuilderFactory.config; import static org.junit.Assert.assertEquals; import static org.mockito.Matchers.any; import static org.mockito.Matchers.anyObject; @@ -75,13 +73,12 @@ public void setUp() throws Exception { @Test public void testSampleJson() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$.store.book[0].category", mockListener) + surfer.builder().bind("$.store.book[0].category", mockListener) .bind("$.store.book[0]", mockListener) .bind("$.store.car", mockListener) - .bind("$.store.bicycle", mockListener); - surfer.surf(read("sample.json"), builder.build()); + .bind("$.store.bicycle", mockListener) + .surf(read("sample.json")); Object book = provider.createObject(); provider.put(book, "category", provider.primitive("reference")); @@ -105,22 +102,16 @@ public void testSampleJson() throws Exception { @Test public void testSample2() throws Exception { - - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$[0].aiRuleEditorOriginal.+.barrierLevel", mockListener); - surfer.surf(read("sample2.json"), builder.build()); + surfer.builder() + .bind("$[0].aiRuleEditorOriginal.+.barrierLevel", mockListener) + .surf(read("sample2.json")); verify(mockListener).onValue(eq(provider.primitive("0.8065")), any(ParsingContext.class)); - } @Test public void testStoppableParsing() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$.store.book[0,1,2]", mockListener) - .bind("$.store.book[3]", mockListener); - doNothing().when(mockListener) .onValue(anyObject(), argThat(new TypeSafeMatcher() { @@ -135,7 +126,10 @@ public void describeTo(Description description) { } })); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder() + .bind("$.store.book[0,1,2]", mockListener) + .bind("$.store.book[3]", mockListener) + .surf(read("sample.json")); verify(mockListener, times(1)) .onValue(anyObject(), any(ParsingContext.class)); @@ -143,20 +137,20 @@ public void describeTo(Description description) { @Test public void testChildNodeWildcard() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$.store.*", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder() + .bind("$.store.*", mockListener) + .surf(read("sample.json")); verify(mockListener, times(3)) .onValue(anyObject(), any(ParsingContext.class)); } @Test public void testAnyIndex() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$.store.book[*]", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder() + .bind("$.store.book[*]", mockListener) + .surf(read("sample.json")); verify(mockListener, times(4)) .onValue(anyObject(), any(ParsingContext.class)); } @@ -167,27 +161,25 @@ private String read(String resourceName) throws IOException { @Test public void testWildcardCombination() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$.store.book[*].*", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$.store.book[*].*", mockListener) + .surf(read("sample.json")); verify(mockListener, times(18)).onValue(anyObject(), any(ParsingContext.class)); } @Test public void testArraySlicing() throws Exception { - Builder builder = config(); JsonPathListener mock1 = mock(JsonPathListener.class); - builder.bind("$[:2]", mock1); JsonPathListener mock2 = mock(JsonPathListener.class); - builder.bind("$[0:2]", mock2); JsonPathListener mock3 = mock(JsonPathListener.class); - builder.bind("$[2:]", mock3); JsonPathListener mock4 = mock(JsonPathListener.class); - builder.bind("$[:]", mock4); - - surfer.surf(read("array.json"), builder.build()); + surfer.builder() + .bind("$[:2]", mock1) + .bind("$[0:2]", mock2) + .bind("$[2:]", mock3) + .bind("$[:]", mock4) + .surf(read("array.json")); verify(mock1, times(2)).onValue(anyObject(), any(ParsingContext.class)); verify(mock2, times(2)).onValue(anyObject(), any(ParsingContext.class)); verify(mock3, times(3)).onValue(anyObject(), any(ParsingContext.class)); @@ -196,7 +188,6 @@ public void testArraySlicing() throws Exception { @Test public void testParsingArray() throws Exception { - Builder builder = config(); JsonPathListener wholeArray = mock(JsonPathListener.class); JsonPathListener stringElement = mock(JsonPathListener.class); JsonPathListener numberElement = mock(JsonPathListener.class); @@ -204,13 +195,14 @@ public void testParsingArray() throws Exception { JsonPathListener nullElement = mock(JsonPathListener.class); JsonPathListener objectElement = mock(JsonPathListener.class); - builder.bind("$", wholeArray); - builder.bind("$[0]", stringElement); - builder.bind("$[1]", numberElement); - builder.bind("$[2]", booleanElement); - builder.bind("$[3]", nullElement); - builder.bind("$[4]", objectElement); - surfer.surf(read("array.json"), builder.build()); + surfer.builder().bind("$", wholeArray) + .bind("$[0]", stringElement) + .bind("$[1]", numberElement) + .bind("$[2]", booleanElement) + .bind("$[3]", nullElement) + .bind("$[4]", objectElement) + .surf(read("array.json")); + Object object = provider.createObject(); provider.put(object, "key", provider.primitive("value")); Object array = provider.createArray(); @@ -230,11 +222,10 @@ public void testParsingArray() throws Exception { @Test public void testDeepScan() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$..author", mockListener); - builder.bind("$..store..bicycle..color", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$..author", mockListener) + .bind("$..store..bicycle..color", mockListener) + .surf(read("sample.json")); verify(mockListener).onValue(eq(provider.primitive("Nigel Rees")), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive("Evelyn Waugh")), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive("Herman Melville")), any(ParsingContext.class)); @@ -245,10 +236,9 @@ public void testDeepScan() throws Exception { @Test public void testDeepScan2() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$..store..price", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$..store..price", mockListener) + .surf(read("sample.json")); verify(mockListener).onValue(eq(provider.primitive(8.95)), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive(12.99)), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive(8.99)), any(ParsingContext.class)); @@ -258,32 +248,30 @@ public void testDeepScan2() throws Exception { @Test public void testAny() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$.store..bicycle..*", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$.store..bicycle..*", mockListener) + .surf(read("sample.json")); verify(mockListener).onValue(eq(provider.primitive("red")), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive(19.95)), any(ParsingContext.class)); } @Test public void testFindEverything() throws Exception { - Builder builder = config(); - builder.bind("$..*", new JsonPathListener() { - @Override - public void onValue(Object value, ParsingContext context) { - LOGGER.trace("value: {}", value); - } - }); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder() + .bind("$..*", new JsonPathListener() { + @Override + public void onValue(Object value, ParsingContext context) { + LOGGER.trace("value: {}", value); + } + }) + .surf(read("sample.json")); } @Test public void testIndexesAndChildrenOperator() throws Exception { - Builder builder = config(); JsonPathListener mockListener = mock(JsonPathListener.class); - builder.bind("$..book[1,3][author,title]", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$..book[1,3][author,title]", mockListener) + .surf(read("sample.json")); verify(mockListener).onValue(eq(provider.primitive("Evelyn Waugh")), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive("Sword of Honour")), any(ParsingContext.class)); verify(mockListener).onValue(eq(provider.primitive("J. R. R. Tolkien")), any(ParsingContext.class)); @@ -320,117 +308,105 @@ public void testCollectOne() throws Exception { @Test public void testGetCurrentFieldName() throws Exception { - surfer.surf(read("sample.json"), config().bind("$.store.book[0].title", new JsonPathListener() { - @Override - public void onValue(Object value, ParsingContext context) throws Exception { - assertEquals(context.getCurrentFieldName(), "title"); - } - }).build()); + surfer.builder() + .bind("$.store.book[0].title", new JsonPathListener() { + @Override + public void onValue(Object value, ParsingContext context) throws Exception { + assertEquals(context.getCurrentFieldName(), "title"); + } + }) + .surf(read("sample.json")); } @Test public void testGetCurrentArrayIndex() throws Exception { - surfer.surf(read("sample.json"), config().bind("$.store.book[3]", new JsonPathListener() { + surfer.builder().bind("$.store.book[3]", new JsonPathListener() { @Override public void onValue(Object value, ParsingContext context) throws Exception { assertEquals(context.getCurrentArrayIndex(), 3); } - }).build()); + }).surf(read("sample.json")); } @Test public void testExample1() throws Exception { - Builder builder = config(); - builder.bind("$.store.book[*].author", print); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$.store.book[*].author", print).surf(read("sample.json")); } @Test public void testExample2() throws Exception { - Builder builder = config(); - builder.bind("$..author", print); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$..author", print).surf(read("sample.json")); } @Test public void testExample3() throws Exception { - Builder builder = config(); - builder.bind("$.store.*", print); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$.store.*", print).surf(read("sample.json")); } @Test public void testExample4() throws Exception { - Builder builder = config(); - builder.bind("$.store..price", print); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$.store..price", print).surf(read("sample.json")); } @Test public void testExample5() throws Exception { - Builder builder = config(); - builder.bind("$..book[2]", print); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$..book[2]", print).surf(read("sample.json")); } @Test public void testExample6() throws Exception { - Builder builder = config(); - builder.bind("$..book[0,1]", print); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$..book[0,1]", print).surf(read("sample.json")); } @Test public void testStoppable() throws Exception { - Builder builder = config(); - builder.bind("$..book[0,1]", new JsonPathListener() { + surfer.builder().bind("$..book[0,1]", new JsonPathListener() { @Override public void onValue(Object value, ParsingContext parsingContext) { parsingContext.stopParsing(); System.out.println(value); } - }); - surfer.surf(read("sample.json"), builder.build()); + }).surf(read("sample.json")); } @Test public void testPlugableProvider() throws Exception { JsonPathListener mockListener = mock(JsonPathListener.class); - Builder builder = config().withJsonProvider(JavaCollectionProvider.INSTANCE); - builder.bind("$.store", mockListener); - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().withJsonProvider(JavaCollectionProvider.INSTANCE) + .bind("$.store", mockListener) + .surf(read("sample.json")); verify(mockListener).onValue(isA(HashMap.class), any(ParsingContext.class)); } @Test public void testErrorStrategySuppressException() throws Exception { - Builder builder = config(); + JsonPathListener mock = mock(JsonPathListener.class); - builder.bind("$.store.book[*]", mock); - builder.withErrorStrategy(new ErrorHandlingStrategy() { - @Override - public void handleParsingException(Exception e) { - // suppress exception - } - - @Override - public void handleExceptionFromListener(Exception e, ParsingContext context) { - // suppress exception - } - }); doNothing().doThrow(Exception.class).doThrow(Exception.class).when(mock).onValue(anyObject(), any(ParsingContext.class)); - surfer.surf(read("sample.json"), builder.build()); + + surfer.builder().bind("$.store.book[*]", mock) + .withErrorStrategy(new ErrorHandlingStrategy() { + @Override + public void handleParsingException(Exception e) { + // suppress exception + } + + @Override + public void handleExceptionFromListener(Exception e, ParsingContext context) { + // suppress exception + } + }) + .surf(read("sample.json")); verify(mock, times(4)).onValue(anyObject(), any(ParsingContext.class)); } @Test public void testErrorStrategyThrowException() throws Exception { - Builder builder = config(); + JsonPathListener mock = mock(JsonPathListener.class); - builder.bind("$.store.book[*]", mock); doNothing().doThrow(Exception.class).doThrow(Exception.class).when(mock).onValue(anyObject(), any(ParsingContext.class)); try { - surfer.surf(read("sample.json"), builder.build()); + surfer.builder().bind("$.store.book[*]", mock).surf(read("sample.json")); } catch (Exception e) { // catch mock exception }