You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@jena.apache.org by an...@apache.org on 2017/12/31 10:52:40 UTC
[02/11] jena git commit: JENA-1454: Introduce builder pattern for
result set reading and writing.
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInput.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInput.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInput.java
index 322a568..d2a3ee5 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInput.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInput.java
@@ -18,231 +18,40 @@
package org.apache.jena.sparql.resultset;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kBindings;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kBnode;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kBoolean;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kDatatype;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kHead;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kLink;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kLiteral;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kResults;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kType;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kTypedLiteral;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kUri;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kValue;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kVars;
-import static org.apache.jena.sparql.resultset.JSONResultsKW.kXmlLang;
-
import java.io.InputStream;
-import java.util.*;
-import org.apache.jena.atlas.json.JSON;
-import org.apache.jena.atlas.json.JsonArray;
-import org.apache.jena.atlas.json.JsonObject;
-import org.apache.jena.atlas.json.JsonValue;
-import org.apache.jena.atlas.logging.Log;
-import org.apache.jena.datatypes.RDFDatatype;
-import org.apache.jena.datatypes.TypeMapper;
-import org.apache.jena.graph.Node;
-import org.apache.jena.graph.NodeFactory;
import org.apache.jena.query.ResultSet;
import org.apache.jena.rdf.model.Model;
-import org.apache.jena.riot.lang.LabelToNode;
-import org.apache.jena.riot.system.SyntaxLabels;
-import org.apache.jena.sparql.core.Var;
-import org.apache.jena.sparql.engine.QueryIterator;
-import org.apache.jena.sparql.engine.ResultSetStream;
-import org.apache.jena.sparql.engine.binding.Binding;
-import org.apache.jena.sparql.engine.binding.BindingFactory;
-import org.apache.jena.sparql.engine.binding.BindingMap;
-import org.apache.jena.sparql.engine.iterator.QueryIterPlainWrapper;
-import org.apache.jena.sparql.graph.GraphFactory;
+import org.apache.jena.riot.resultset.ResultSetLang;
+import org.apache.jena.riot.resultset.rw.ResultsReader;
+/**
+ * @deprecated Use ResultSetMgr.read
+ */
+@Deprecated
public class JSONInput extends SPARQLResult {
public static ResultSet fromJSON(InputStream input) {
- SPARQLResult r = new JSONInput().process(input, null);
- return r.getResultSet();
+ return
+ ResultsReader.create()
+ .lang(ResultSetLang.SPARQLResultSetJSON)
+ .read(input);
}
public static boolean booleanFromJSON(InputStream input) {
- SPARQLResult r = new JSONInput().process(input, null);
- return r.getBooleanResult();
+ return make(input).getBooleanResult();
}
public static SPARQLResult make(InputStream input) {
- return make(input, null);
+ return
+ ResultsReader.create()
+ .lang(ResultSetLang.SPARQLResultSetJSON)
+ .build()
+ .readAny(input);
}
public static SPARQLResult make(InputStream input, Model model) {
- return new JSONInput().process(input, model);
- }
-
- public JSONInput() {}
-
- public JSONInput(InputStream in) {
- this(in, null);
+ return make(input);
}
- // See also XMLInputSAX for design structure.
- public JSONInput(InputStream in, Model model) {
- if ( model == null )
- model = GraphFactory.makeJenaDefaultModel();
- process(in, model);
- }
-
- Boolean booleanResult = null; // Valid if rows is null.
- List<Binding> rows = null;
- List<Var> vars = null;
-
- // TODO Streaming version of JSON Result set processing
-
- private SPARQLResult process(InputStream in, Model model) {
- parse(in);
- if ( model == null )
- model = GraphFactory.makeJenaDefaultModel();
- if ( rows != null ) {
- QueryIterator qIter = new QueryIterPlainWrapper(rows.iterator());
- ResultSet rs = new ResultSetStream(Var.varNames(vars), model, qIter);
- super.set(rs);
- } else
- super.set(booleanResult);
- return this;
- }
-
- private void parse(InputStream in) {
- JsonObject obj = JSON.parse(in);
-
- if ( obj.hasKey(kBoolean) ) {
- checkContains(obj, true, true, kHead, kBoolean);
- booleanResult = obj.get(kBoolean).getAsBoolean().value();
- rows = null;
- return;
- }
-
- rows = new ArrayList<>(1000);
-
- checkContains(obj, true, true, kHead, kResults);
-
- // process head
- if ( !obj.get(kHead).isObject() )
- throw new ResultSetException("Key 'head' must have a JSON object as value: found: " + obj.get(kHead));
- JsonObject head = obj.get(kHead).getAsObject();
-
- // ---- Head
- // -- Link - array.
- if ( head.hasKey(kLink) ) {
- List<String> links = new ArrayList<>();
-
- if ( head.get(kLink).isString() ) {
- Log.warn(this, "Link field is a string, should be an array of strings");
- links.add(head.get(kLink).getAsString().value());
- } else {
- if ( !head.get(kLink).isArray() )
- throw new ResultSetException("Key 'link' must have be an array: found: " + obj.get(kLink));
-
- for ( JsonValue v : head.get(kLink).getAsArray() ) {
- if ( !v.isString() )
- throw new ResultSetException("Key 'link' must have be an array of strings: found: " + v);
- links.add(v.getAsString().value());
- }
- }
- }
- // -- Vars
- vars = parseVars(head);
-
- // ---- Results
- JsonObject results = obj.get(kResults).getAsObject();
- if ( !results.get(kBindings).isArray() )
- throw new ResultSetException("'bindings' must be an array");
- JsonArray array = results.get(kBindings).getAsArray();
- Iterator<JsonValue> iter = array.iterator();
-
- for ( ; iter.hasNext() ; ) {
- BindingMap b = BindingFactory.create();
- JsonValue v = iter.next();
- if ( !v.isObject() )
- throw new ResultSetException("Entry in 'bindings' array must be an object {}");
- JsonObject x = v.getAsObject();
- Set<String> varNames = x.keys();
- for ( String vn : varNames ) {
- // if ( ! vars.contains(vn) ) {}
- JsonValue vt = x.get(vn);
- if ( !vt.isObject() )
- throw new ResultSetException("Binding for variable '" + vn + "' is not a JSON object: " + vt);
- Node n = parseOneTerm(vt.getAsObject());
- b.add(Var.alloc(vn), n);
- }
- rows.add(b);
- }
- }
-
- private List<Var> parseVars(JsonObject obj) {
- if ( !obj.get(kVars).isArray() )
- throw new ResultSetException("Key 'vars' must be a JSON array");
- JsonArray a = obj.get(kVars).getAsArray();
- Iterator<JsonValue> iter = a.iterator();
- List<Var> vars = new ArrayList<>();
- for ( ; iter.hasNext() ; ) {
- JsonValue v = iter.next();
- if ( !v.isString() )
- throw new ResultSetException("Entries in vars array must be strings");
- Var var = Var.alloc(v.getAsString().value());
- vars.add(var);
- }
- return vars;
- }
-
- LabelToNode labelMap = SyntaxLabels.createLabelToNode();
-
- private Node parseOneTerm(JsonObject term) {
- checkContains(term, false, false, kType, kValue, kXmlLang, kDatatype);
-
- String type = stringOrNull(term, kType);
- String v = stringOrNull(term, kValue);
-
- if ( kUri.equals(type) ) {
- checkContains(term, false, true, kType, kValue);
- String uri = v;
- Node n = NodeFactory.createURI(v);
- return n;
- }
-
- if ( kLiteral.equals(type) || kTypedLiteral.equals(type) ) {
- String lang = stringOrNull(term, kXmlLang);
- String dtStr = stringOrNull(term, kDatatype);
- if ( lang != null && dtStr != null )
- throw new ResultSetException("Both language and datatype defined: " + term);
- RDFDatatype dt = TypeMapper.getInstance().getSafeTypeByName(dtStr);
- return NodeFactory.createLiteral(v, lang, dt);
- }
-
- if ( kBnode.equals(type) )
- return labelMap.get(null, v);
-
- throw new ResultSetException("Object key not recognized as valid for an RDF term: " + term);
- }
-
- private static String stringOrNull(JsonObject obj, String key) {
- JsonValue v = obj.get(key);
- if ( v == null )
- return null;
- if ( !v.isString() )
- throw new ResultSetException("Not a string: key: " + key);
- return v.getAsString().value();
-
- }
-
- private static void checkContains(JsonObject term, boolean allowUndefinedKeys, boolean requireAllExpectedKeys, String... keys) {
- List<String> expectedKeys = Arrays.asList(keys);
- Set<String> declared = new HashSet<>();
- for ( String k : term.keys() ) {
- if ( !expectedKeys.contains(k) && !allowUndefinedKeys )
- throw new ResultSetException("Expected only object keys " + Arrays.asList(keys) + " but encountered '" + k + "'");
- if ( expectedKeys.contains(k) )
- declared.add(k);
- }
-
- if ( requireAllExpectedKeys && declared.size() < expectedKeys.size() )
- throw new ResultSetException("One or more of the required keys " + expectedKeys + " was not found");
- }
+ private JSONInput() {}
}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInputIterator.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInputIterator.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInputIterator.java
deleted file mode 100644
index c8f89f1..0000000
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONInputIterator.java
+++ /dev/null
@@ -1,657 +0,0 @@
-/**
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.jena.sparql.resultset;
-
-import java.io.InputStream;
-import java.util.*;
-
-import org.apache.jena.atlas.AtlasException;
-import org.apache.jena.atlas.io.IO;
-import org.apache.jena.atlas.io.IndentedWriter;
-import org.apache.jena.atlas.io.PeekReader;
-import org.apache.jena.atlas.iterator.PeekIterator;
-import org.apache.jena.atlas.json.io.parser.TokenizerJSON;
-import org.apache.jena.datatypes.TypeMapper;
-import org.apache.jena.graph.Node;
-import org.apache.jena.graph.NodeFactory;
-import org.apache.jena.query.QueryException;
-import org.apache.jena.riot.RiotParseException;
-import org.apache.jena.riot.tokens.Token;
-import org.apache.jena.riot.tokens.TokenType;
-import org.apache.jena.sparql.core.Var;
-import org.apache.jena.sparql.engine.binding.Binding;
-import org.apache.jena.sparql.engine.binding.BindingFactory;
-import org.apache.jena.sparql.engine.binding.BindingMap;
-import org.apache.jena.sparql.engine.iterator.QueryIteratorBase;
-import org.apache.jena.sparql.serializer.SerializationContext;
-
-/**
- * Streaming Iterator over SPARQL JSON results, not yet fully implemented (see
- * JENA-267)
- * <p>
- * Creating the Iterator automatically causes it to parse a small chunk of the
- * stream to determine the variables in the result set either by reading the
- * header or reading some portion of the results if the results appear before
- * the header since JSON does not guarantee the order of keys within an object
- * </p>
- */
-public class JSONInputIterator extends QueryIteratorBase {
-
- private InputStream input;
-
- private boolean isBooleanResults = false,
- boolResult = false, headerSeen = false;
- private Binding binding = null;
- private TokenizerJSON tokens;
- private PeekIterator<Token> peekIter;
-
- private Queue<Binding> cache = new LinkedList<>();
- private Set<String> vars = new HashSet<>();
-
- /**
- * Creates a SPARQL JSON Iterator
- * <p>
- * Automatically parses some portion of the input to determine the variables
- * in use
- * </p>
- */
- public JSONInputIterator(InputStream input) {
- this.input = input;
- this.tokens = new TokenizerJSON(PeekReader.makeUTF8(input));
- this.peekIter = new PeekIterator<>(this.tokens);
-
- // We should always parse the first little bit to see the head stuff or
- // to cache a chunk of results and infer the headers
- // Primarily we are trying to find out what the variables are
- preParse();
- }
-
- /**
- * Returns the variables present in the result sets
- */
- public Iterator<String> getVars() {
- return vars.iterator();
- }
-
- /**
- * Gets whether the SPARQL JSON represents a boolean result set
- */
- public boolean isBooleanResult() {
- return isBooleanResults;
- }
-
- /**
- * Does the pre-parsing which attempts to read the header of the results
- * file and determine variables present
- * <p>
- * If the header is encountered first then we read this, if the results are
- * encountered first we parse the first 100 results and determine the
- * variables present from those instead
- * </p>
- */
- private void preParse() {
- // First off the { to start the object
- expect("Expected the start of the JSON Results Object", TokenType.LBRACE);
-
- // Then expect to see a Property Name
- // Loop here because we might see some things we can discard first
- do {
- if ( !isPropertyName() ) {
- Token t = nextToken();
- String name = t.getImage();
- checkColon();
-
- if ( name.equals("head") ) {
- if ( headerSeen )
- exception(t, "Invalid duplicate header property");
- parseHeader();
- // Continue afterwards because we want to be in place to
- // start streaming results
- } else if ( name.equals("boolean") ) {
- parseBoolean();
- // Afterwards we continue because we want to see an empty
- // head
- } else if ( name.equals("results") ) {
- if ( isBooleanResults )
- exception(t, "Encountered results property when boolean property has already been countered");
-
- // Scroll to first result
- parseToFirstResult();
-
- // If we already saw the header then exit at this point
- if ( headerSeen )
- return;
-
- // If not we're going to pre-cache some chunk of results so
- // we can infer the variable names
- boolean complete = cacheResults(100);
-
- // If this exhausted the result set then we can continue
- // looking for the header
- // Otherwise we should exit as we may eventually see the
- // header later...
- if ( !complete ) {
- // TODO Now determine variables present from this
- return;
- }
- } else {
- ignoreValue();
- }
- checkComma(TokenType.RBRACE);
- } else if ( lookingAt(TokenType.RBRACE) ) {
- // We hit the end of the result object already
- if ( !headerSeen )
- exception(peekToken(), "End of JSON Results Object encountered before a valid header was seen");
- nextToken();
-
- // Shouldn't be any further content
- if ( !lookingAt(TokenType.EOF) )
- exception(peekToken(), "Unexpected content after end of JSON Results Object");
-
- // Can stop our initial buffering at this stage
- return;
- } else {
- exception(peekToken(), "Expected a JSON property name but got %s", peekToken());
- }
- } while (true);
- }
-
- private void parseHeader() {
- do {
- if ( isPropertyName() ) {
- Token t = nextToken();
- String name = t.getImage();
- checkColon();
-
- if ( name.equals("vars") ) {
- parseVars();
- } else if ( name.equals("link") ) {
- // Throw away the links
- skipLinks();
- } else {
- exception(t, "Unexpected property %s encountered in head object", name);
- }
- checkComma(TokenType.RBRACE);
- } else if ( lookingAt(TokenType.RBRACE) ) {
- nextToken();
- return;
- } else {
- exception(peekToken(), "Unexpected Token encountered while parsing head object");
- }
- } while (true);
- }
-
- private void parseVars() {
- if ( lookingAt(TokenType.LBRACKET) ) {
- nextToken();
- vars.clear();
- do {
- if ( lookingAt(TokenType.STRING) ) {
- Token t = nextToken();
- String var = t.getImage();
- vars.add(var);
- checkComma(TokenType.RBRACKET);
- } else if ( lookingAt(TokenType.RBRACKET) ) {
- nextToken();
- return;
- } else {
- exception(peekToken(), "Unexpected Token encountered while parsing the variables list in the head object");
- }
- } while (true);
- } else {
- exception(peekToken(), "Unexpected Token ecountered, expected a [ to start the array of variables in the head object");
- }
- }
-
- private void skipLinks() {
- if ( lookingAt(TokenType.LBRACKET) ) {
- nextToken();
- do {
- if ( lookingAt(TokenType.RBRACKET) ) {
- // End of links
- nextToken();
- return;
- } else if ( lookingAt(TokenType.STRING) ) {
- // Ignore link and continue
- nextToken();
- } else {
- exception(peekToken(), "Unexpected Token when a Link URI was expected");
- }
- checkComma(TokenType.RBRACKET);
- } while (true);
- } else {
- exception(peekToken(), "Unexpected token when a [ was expected to start the list of URIs for a link property");
- }
- }
-
- private void parseToFirstResult() {
- if ( lookingAt(TokenType.LBRACE) ) {
- nextToken();
- if ( isPropertyName() ) {
- Token t = nextToken();
- String name = t.getImage();
- if ( name.equals("bindings") ) {
- checkColon();
- if ( lookingAt(TokenType.LBRACKET) ) {
- nextToken();
- } else {
- exception(peekToken(), "Unexpected Token encountered, expected a [ for the start of the bindings array");
- }
- } else {
- exception(t, "Unexpected Token encountered, expected the bindings property");
- }
- } else {
- exception(peekToken(), "Unexpected Token ecnountered, expected the bindings property");
- }
- } else {
- exception(peekToken(), "Unexpected Token encountered, expected a { to start the results list object");
- }
- }
-
- private void parseToEnd() {
- // TODO Parse through to end of the JSON document consuming the header
- // if we haven't seen it already
- checkComma(TokenType.RBRACE);
- }
-
- private void ignoreValue() {
- if ( isPropertyName() ) {
- // Just a string value so can discard and then check for the
- // subsequent comma
- nextToken();
- checkComma(TokenType.RBRACE);
- } else if ( lookingAt(TokenType.DECIMAL) || lookingAt(TokenType.INTEGER) || lookingAt(TokenType.DOUBLE)
- || lookingAt(TokenType.KEYWORD) ) {
- // Just a numeric/keyword (boolean) value do discard and check for
- // subsequent comma
- nextToken();
- checkComma(TokenType.RBRACE);
- } else if ( lookingAt(TokenType.LBRACE) ) {
- // Start of an Object
- nextToken();
-
- // TODO We should really care about the syntactic validity of
- // objects we are ignoring but that seems like a bit too much effort
- int openBraces = 1;
- while (openBraces >= 1) {
- Token next = nextToken();
- if ( next.getType().equals(TokenType.LBRACE) ) {
- openBraces++;
- } else if ( next.getType().equals(TokenType.RBRACE) ) {
- openBraces--;
- }
- }
- checkComma(TokenType.RBRACE);
- } else if ( lookingAt(TokenType.LBRACKET) ) {
- // Start of an Array
- nextToken();
-
- // TODO We should really care about the syntactic validity of
- // objects we are ignoring but that seems like a bit too much effort
- int openBraces = 1;
- while (openBraces >= 1) {
- Token next = nextToken();
- if ( next.getType().equals(TokenType.LBRACKET) ) {
- openBraces++;
- } else if ( next.getType().equals(TokenType.RBRACKET) ) {
- openBraces--;
- }
- }
- checkComma(TokenType.RBRACE);
- } else {
- exception(peekToken(), "Unexpected Token");
- }
- }
-
- /**
- * Caches the first N results so we can infer variables, indicates whether
- * the caching exhausted the result set
- *
- * @param n
- * Number of results to cache
- */
- private boolean cacheResults(int n) {
- for ( int i = 0 ; i < n ; i++ ) {
- if ( parseNextBinding() ) {
- this.cache.add(this.binding);
- this.binding = null;
- } else {
- return true;
- }
- }
- return false;
- }
-
- private void parseBoolean() {
- isBooleanResults = true;
- if ( lookingAt(TokenType.KEYWORD) ) {
- Token t = nextToken();
- String keyword = t.getImage();
- if ( keyword.equals("true") ) {
- boolResult = true;
- } else if ( keyword.equals("false") ) {
- boolResult = false;
- } else {
- exception(t, "Unexpected keyword %s encountered, expected true or false", keyword);
- }
- } else {
- exception(peekToken(), "Unexpected token when a true/false keyword was expected for the value of the boolean property");
- }
- }
-
- @Override
- public void output(IndentedWriter out, SerializationContext sCxt) {
- // Not needed - only called as part of printing/debugging query plans.
- out.println("JSONInputIterator");
- }
-
- @Override
- protected boolean hasNextBinding() {
- if ( isBooleanResults )
- return false;
-
- if ( this.input != null ) {
- if ( this.cache.size() > 0 ) {
- this.binding = this.cache.remove();
- return true;
- } else if ( this.binding == null ) {
- return this.parseNextBinding();
- } else {
- return true;
- }
- } else {
- return false;
- }
- }
-
- private boolean parseNextBinding() {
- if ( lookingAt(TokenType.LBRACE) ) {
- nextToken();
- BindingMap b = BindingFactory.create();
- do {
- if ( isPropertyName() ) {
- Token t = nextToken();
- String var = t.getImage();
- checkColon();
-
- Node n = parseNode();
- b.add(Var.alloc(var), n);
-
- checkComma(TokenType.RBRACE);
- } else if ( lookingAt(TokenType.RBRACE) ) {
- nextToken();
- checkComma(TokenType.RBRACKET);
- break;
- } else {
- exception(peekToken(), "Unexpected Token encountered, expected a property name to indicate the value for a variable");
- }
- } while (true);
-
- this.binding = b;
- return true;
- } else if ( lookingAt(TokenType.RBRACKET) ) {
- // End of Bindings Array
- nextToken();
- if ( lookingAt(TokenType.RBRACE) ) {
- nextToken();
- parseToEnd();
- } else {
- exception(peekToken(), "Unexpected Token encountered, expected a } to end the results object");
- }
- } else {
- exception(peekToken(),
- "Unexpected Token encountered, expected a { for the start of a binding of ] to end the array of bindings");
- }
- return false;
- }
-
- private Node parseNode() {
- String type, value, lang, datatype;
- type = value = lang = datatype = null;
-
- if ( lookingAt(TokenType.LBRACE) ) {
- Token pos = nextToken();
-
- // Collect the Properties
- do {
- if ( isPropertyName() ) {
- Token t = nextToken();
- String name = t.getImage();
- checkColon();
-
- if ( name.equals("type") ) {
- if ( type != null )
- exception(t, "Illegal duplicate type property");
- type = parseNodeInfo("type");
- } else if ( name.equals("value") ) {
- if ( value != null )
- exception(t, "Illegal duplicate value property");
- value = parseNodeInfo("value");
- } else if ( name.equals("datatype") ) {
- if ( datatype != null )
- exception(t, "Illegal duplicate datatype property");
- datatype = parseNodeInfo("datatype");
- } else if ( name.equals("xml:lang") ) {
- if ( lang != null )
- exception(t, "Illegal duplicate xml:lang property");
- lang = parseNodeInfo("xml:lang");
- } else {
- exception(t, "Unexpected Property Name '%s', expected one of type, value, datatype or xml:lang", name);
- }
- } else if ( lookingAt(TokenType.RBRACE) ) {
- nextToken();
- break;
- } else {
- exception(peekToken(), "Unexpected Token, expected a property name as part of a Node object");
- }
- } while (true);
-
- // Error if missing type or value
- if ( type == null )
- exception(pos, "Encountered a Node object with no type property");
- if ( value == null )
- exception(pos, "Encountered a Node object with no value property");
-
- // Generate a Node based on the properties we saw
- if ( type.equals("uri") ) {
- return NodeFactory.createURI(value);
- } else if ( type.equals("literal") ) {
- if ( datatype != null ) {
- return NodeFactory.createLiteral(value, TypeMapper.getInstance().getSafeTypeByName(datatype));
- } else if ( lang != null ) {
- return NodeFactory.createLiteral(value, lang);
- } else {
- return NodeFactory.createLiteral(value);
- }
- } else if ( type.equals("bnode") ) {
- return NodeFactory.createBlankNode(value);
- } else {
- exception(pos, "Encountered a Node object with an invalid type value '%s', expected one of uri, literal or bnode", type);
- }
- } else {
- exception(peekToken(), "Unexpected Token, expected a { for the start of a Node object");
- }
- return null;
- }
-
- private String parseNodeInfo(String name) {
- if ( lookingAt(TokenType.STRING) ) {
- Token t = nextToken();
- String value = t.getImage();
- checkComma(TokenType.RBRACE);
- return value;
- } else {
- exception(peekToken(), "Unexpected Token, expected a string as the value for the %s property", name);
- return null;
- }
- }
-
- @Override
- protected Binding moveToNextBinding() {
- if ( !hasNext() )
- throw new NoSuchElementException();
- Binding b = this.binding;
- this.binding = null;
- return b;
- }
-
- @Override
- protected void closeIterator() {
- IO.close(input);
- input = null;
- }
-
- @Override
- protected void requestCancel() {
- // Don't need to do anything special to cancel
- // Superclass should take care of that and call closeIterator() where we
- // do our actual clean up
- }
-
- // JSON Parsing Helpers taken from LangRDFJSON
-
- private boolean isPropertyName() {
- return lookingAt(TokenType.STRING);
- }
-
- private Token checkValidForStringProperty(String property) {
- Token t = null;
- if ( lookingAt(TokenType.STRING) ) {
- t = nextToken();
- } else {
- exception(peekToken(), "JSON Values given for property " + property + " must be Strings");
- }
- return t;
- }
-
- private void checkColon() {
- if ( !lookingAt(TokenType.COLON) ) {
- exception(peekToken(), "Expected a : character after a JSON Property Name but got %s", peekToken());
- }
- nextToken();
- }
-
- private void checkComma(TokenType terminator) {
- if ( lookingAt(TokenType.COMMA) ) {
- nextToken();
- } else if ( lookingAt(terminator) ) {
- return;
- } else {
- exception(peekToken(), "Unexpected Token encountered, expected a , or a %s", terminator);
- }
- }
-
- // Streaming Parsing Helper Functions nicked from LangEngine
-
- // ---- Managing tokens.
-
- protected final Token peekToken() {
- // Avoid repeating.
- if ( eof() )
- return tokenEOF;
- return peekIter.peek();
- }
-
- // Set when we get to EOF to record line/col of the EOF.
- private Token tokenEOF = null;
-
- protected final boolean eof() {
- if ( tokenEOF != null )
- return true;
-
- if ( !moreTokens() ) {
- tokenEOF = new Token(tokens.getLine(), tokens.getColumn());
- tokenEOF.setType(TokenType.EOF);
- return true;
- }
- return false;
- }
-
- protected final boolean moreTokens() {
- return peekIter.hasNext();
- }
-
- protected final boolean lookingAt(TokenType tokenType) {
- if ( eof() )
- return tokenType == TokenType.EOF;
- if ( tokenType == TokenType.NODE )
- return peekToken().isNode();
- return peekToken().hasType(tokenType);
- }
-
- // Remember line/col of last token for messages
- protected long currLine = -1;
- protected long currCol = -1;
-
- protected final Token nextToken() {
- if ( eof() )
- return tokenEOF;
-
- // Tokenizer errors appear here!
- try {
- Token t = peekIter.next();
- currLine = t.getLine();
- currCol = t.getColumn();
- return t;
- }
- catch (RiotParseException ex) {
- // Intercept to log it.
- raiseException(ex);
- throw ex;
- }
- catch (AtlasException ex) {
- // Bad I/O
- RiotParseException ex2 = new RiotParseException(ex.getMessage(), -1, -1);
- raiseException(ex2);
- throw ex2;
- }
- }
-
- protected final void expectOrEOF(String msg, TokenType tokenType) {
- // DOT or EOF
- if ( eof() )
- return;
- expect(msg, tokenType);
- }
-
- protected final void expect(String msg, TokenType ttype) {
-
- if ( !lookingAt(ttype) ) {
- Token location = peekToken();
- exception(location, msg);
- }
- nextToken();
- }
-
- protected final void exception(Token token, String msg, Object... args) {
- if ( token != null )
- exceptionDirect(String.format(msg, args), token.getLine(), token.getColumn());
- else
- exceptionDirect(String.format(msg, args), -1, -1);
- }
-
- protected final void exceptionDirect(String msg, long line, long col) {
- raiseException(new RiotParseException(msg, line, col));
- }
-
- protected final void raiseException(RiotParseException ex) {
- throw new QueryException("Error passing SPARQL JSON results", ex);
- }
-
-}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutput.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutput.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutput.java
index f894f80..9898d54 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutput.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutput.java
@@ -21,22 +21,29 @@ package org.apache.jena.sparql.resultset;
import java.io.OutputStream;
import org.apache.jena.query.ResultSet;
+import org.apache.jena.riot.resultset.ResultSetLang;
+import org.apache.jena.riot.resultset.rw.ResultsWriter;
+/**
+ * @deprecated Use ResultSetMgr.write(,,ResultSetLang.SPARQLResultSetJSON)
+ */
+@Deprecated
public class JSONOutput extends OutputBase {
public JSONOutput() {}
@Override
public void format(OutputStream out, ResultSet resultSet) {
- // Use direct string output - more control
-
- JSONOutputResultSet jsonOut = new JSONOutputResultSet(out);
- ResultSetApply a = new ResultSetApply(resultSet, jsonOut);
- a.apply();
+ ResultsWriter.create()
+ .lang(ResultSetLang.SPARQLResultSetJSON)
+ .build()
+ .write(out, resultSet);
}
@Override
public void format(OutputStream out, boolean booleanResult) {
- JSONOutputASK jsonOut = new JSONOutputASK(out);
- jsonOut.exec(booleanResult);
+ ResultsWriter.create()
+ .lang(ResultSetLang.SPARQLResultSetJSON)
+ .build()
+ .write(out, booleanResult);
}
}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputASK.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputASK.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputASK.java
deleted file mode 100644
index 4b030e2..0000000
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputASK.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.jena.sparql.resultset;
-
-import static org.apache.jena.sparql.resultset.JSONResultsKW.*;
-
-import java.io.OutputStream;
-
-import org.apache.jena.atlas.io.IO;
-import org.apache.jena.atlas.json.io.JSWriter;
-
-/** JSON Output (ASK format) */
-
-public class JSONOutputASK {
- private OutputStream outStream;
-
- public JSONOutputASK(OutputStream outStream) {
- this.outStream = outStream;
-
- }
-
- public void exec(boolean result) {
- JSWriter out = new JSWriter(outStream);
-
- out.startOutput();
-
- out.startObject();
- out.key(kHead);
- out.startObject();
- out.finishObject();
- out.pair(kBoolean, result);
- out.finishObject();
-
- out.finishOutput();
-
- IO.flush(outStream);
- }
-}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputResultSet.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputResultSet.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputResultSet.java
deleted file mode 100644
index ff86222..0000000
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONOutputResultSet.java
+++ /dev/null
@@ -1,266 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.jena.sparql.resultset;
-
-import static org.apache.jena.sparql.resultset.JSONResultsKW.*;
-
-import java.io.OutputStream;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-
-import org.apache.jena.atlas.io.IndentedWriter;
-import org.apache.jena.atlas.json.io.JSWriter;
-import org.apache.jena.atlas.logging.Log;
-import org.apache.jena.query.ARQ;
-import org.apache.jena.query.QuerySolution;
-import org.apache.jena.query.ResultSet;
-import org.apache.jena.rdf.model.Literal;
-import org.apache.jena.rdf.model.RDFNode;
-import org.apache.jena.rdf.model.Resource;
-import org.apache.jena.rdf.model.impl.Util;
-
-/**
- * A JSON writer for SPARQL Result Sets. Uses Jena Atlas JSON support.
- *
- * Format: <a href="http://www.w3.org/TR/sparql11-results-json/">SPARQL 1.1
- * Query Results JSON Format</a>
- */
-
-public class JSONOutputResultSet implements ResultSetProcessor {
- static boolean multiLineValues = false;
- static boolean multiLineVarNames = false;
-
- private boolean outputGraphBNodeLabels = false;
- private IndentedWriter out;
- private int bNodeCounter = 0;
- private Map<Resource, String> bNodeMap = new HashMap<>();
-
- JSONOutputResultSet(OutputStream outStream) {
- this(new IndentedWriter(outStream));
- }
-
- JSONOutputResultSet(IndentedWriter indentedOut) {
- out = indentedOut;
- outputGraphBNodeLabels = ARQ.isTrue(ARQ.outputGraphBNodeLabels);
- }
-
- @Override
- public void start(ResultSet rs) {
- out.println("{");
- out.incIndent();
- doHead(rs);
- out.println(quoteName(kResults) + ": {");
- out.incIndent();
- out.println(quoteName(kBindings) + ": [");
- out.incIndent();
- firstSolution = true;
- }
-
- @Override
- public void finish(ResultSet rs) {
- // Close last binding.
- out.println();
-
- out.decIndent(); // bindings
- out.println("]");
- out.decIndent();
- out.println("}"); // results
- out.decIndent();
- out.println("}"); // top level {}
- out.flush();
- }
-
- private void doHead(ResultSet rs) {
- out.println(quoteName(kHead) + ": {");
- out.incIndent();
- doLink(rs);
- doVars(rs);
- out.decIndent();
- out.println("} ,");
- }
-
- private void doLink(ResultSet rs) {
- // ---- link
- // out.println("\"link\": []") ;
- }
-
- private void doVars(ResultSet rs) {
- // On one line.
- out.print(quoteName(kVars) + ": [ ");
- if ( multiLineVarNames )
- out.println();
- out.incIndent();
- for ( Iterator<String> iter = rs.getResultVars().iterator() ; iter.hasNext() ; ) {
- String varname = iter.next();
- out.print("\"" + varname + "\"");
- if ( multiLineVarNames )
- out.println();
- if ( iter.hasNext() )
- out.print(" , ");
- }
- out.println(" ]");
- out.decIndent();
- }
-
- boolean firstSolution = true;
- boolean firstBindingInSolution = true;
-
- // NB assumes are on end of previous line.
- @Override
- public void start(QuerySolution qs) {
- if ( !firstSolution )
- out.println(" ,");
- firstSolution = false;
- out.println("{");
- out.incIndent();
- firstBindingInSolution = true;
- }
-
- @Override
- public void finish(QuerySolution qs) {
- out.println(); // Finish last binding
- out.decIndent();
- out.print("}"); // NB No newline
- }
-
- @Override
- public void binding(String varName, RDFNode value) {
- if ( value == null )
- return;
-
- if ( !firstBindingInSolution )
- out.println(" ,");
- firstBindingInSolution = false;
-
- // Do not use quoteName - varName may not be JSON-safe as a bare name.
- out.print(quote(varName) + ": { ");
- if ( multiLineValues )
- out.println();
-
- out.incIndent();
- // Old, explicit unbound
- // if ( value == null )
- // printUnbound() ;
- // else
- if ( value.isLiteral() )
- printLiteral((Literal)value);
- else if ( value.isResource() )
- printResource((Resource)value);
- else
- Log.warn(this, "Unknown RDFNode type in result set: " + value.getClass());
- out.decIndent();
-
- if ( !multiLineValues )
- out.print(" ");
- out.print("}"); // NB No newline
- }
-
- // private void printUnbound()
- // {
- // out.print(quoteName(kType)+ ": "+quote(kUnbound)+" , ") ;
- // if ( multiLineValues ) out.println() ;
- // out.print(quoteName(kValue)+": null") ;
- // if ( multiLineValues ) out.println() ;
- // }
-
- private void printLiteral(Literal literal) {
- String datatype = literal.getDatatypeURI();
- String lang = literal.getLanguage();
-
- if ( Util.isSimpleString(literal) || Util.isLangString(literal) ) {
- out.print(quoteName(kType) + ": " + quote(kLiteral) + " , ");
- if ( multiLineValues )
- out.println();
-
- if ( lang != null && !lang.equals("") ) {
- out.print(quoteName(kXmlLang) + ": " + quote(lang) + " , ");
- if ( multiLineValues )
- out.println();
- }
- } else {
- out.print(quoteName(kType) + ": " + quote(kLiteral) + " , ");
- if ( multiLineValues )
- out.println();
-
- out.print(quoteName(kDatatype) + ": " + quote(datatype) + " , ");
- if ( multiLineValues )
- out.println();
- }
-
- out.print(quoteName(kValue) + ": " + quote(literal.getLexicalForm()));
- if ( multiLineValues )
- out.println();
- }
-
- private void printResource(Resource resource) {
- if ( resource.isAnon() ) {
- String label;
- if ( outputGraphBNodeLabels )
- label = resource.getId().getLabelString();
- else {
- if ( !bNodeMap.containsKey(resource) )
- bNodeMap.put(resource, "b" + (bNodeCounter++));
- label = bNodeMap.get(resource);
- }
-
- out.print(quoteName(kType) + ": " + quote(kBnode) + " , ");
- if ( multiLineValues )
- out.println();
-
- out.print(quoteName(kValue) + ": " + quote(label));
-
- if ( multiLineValues )
- out.println();
- } else {
- out.print(quoteName(kType) + ": " + quote(kUri) + " , ");
- if ( multiLineValues )
- out.println();
- out.print(quoteName(kValue) + ": " + quote(resource.getURI()));
- if ( multiLineValues )
- out.println();
- return;
- }
- }
-
- private static String quote(String string) {
- return JSWriter.outputQuotedString(string);
- }
-
- // Quote a name (known to be JSON-safe)
- // Never the RHS of a member entry (for example "false")
- // Some (the Java JSON code for one) JSON parsers accept an unquoted
- // string as a name of a name/value pair.
-
- private static String quoteName(String string) {
- // Safest to quote anyway.
- return quote(string);
-
- // Assumes only called with safe names
- // return string ;
-
- // Better would be:
- // starts a-z, constains a-z,0-9, not a keyword(true, false, null)
- // if ( string.contains(something not in a-z0-9)
- // and
- // //return "\""+string+"\"" ;
- // return JSONObject.quote(string) ;
- }
-
-}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONResultsKW.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONResultsKW.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONResultsKW.java
deleted file mode 100644
index 897ca6d..0000000
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/JSONResultsKW.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.jena.sparql.resultset;
-
-//Keywords for JSON:
-//Taken from:
-//From http://www.w3.org/TR/sparql11-results-json/ (Oct 2011)
-
-public class JSONResultsKW
-{
- public static String kHead = "head" ;
- public static String kVars = "vars" ;
- public static String kLink = "link" ;
- public static String kResults = "results" ;
- public static String kBindings = "bindings" ;
- public static String kType = "type" ;
- public static String kUri = "uri" ;
- public static String kValue = "value" ;
- public static String kLiteral = "literal" ;
- // Legacy.
- public static String kTypedLiteral = "typed-literal" ;
- public static String kXmlLang = "xml:lang" ;
- public static String kDatatype = "datatype" ;
- public static String kBnode = "bnode" ;
- public static String kBoolean = "boolean" ;
-}
-
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/SPARQLResult.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/SPARQLResult.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/SPARQLResult.java
index fcabe74..77c7ae2 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/SPARQLResult.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/SPARQLResult.java
@@ -18,13 +18,9 @@
package org.apache.jena.sparql.resultset;
-import org.apache.jena.atlas.logging.Log;
-import org.apache.jena.graph.Node;
import org.apache.jena.query.Dataset;
import org.apache.jena.query.ResultSet;
import org.apache.jena.rdf.model.Model;
-import org.apache.jena.sparql.core.Var;
-import org.apache.jena.sparql.engine.binding.BindingMap;
/**
* The class "ResultSet" is reserved for the SELECT result format. This class
@@ -95,7 +91,7 @@ public class SPARQLResult {
return resultSet;
}
- public boolean getBooleanResult() {
+ public Boolean getBooleanResult() {
if ( !hasBeenSet )
throw new ResultSetException("Not set");
if ( !isBoolean() )
@@ -146,18 +142,4 @@ public class SPARQLResult {
booleanResult = r;
hasBeenSet = true;
}
-
- static protected void addBinding(BindingMap binding, Var var, Node value) {
- Node n = binding.get(var);
- if ( n != null ) {
- // Same - silently skip.
- if ( n.equals(value) )
- return;
- Log.warn(SPARQLResult.class,
- String.format("Multiple occurences of a binding for variable '%s' with different values - ignored", var.getName()));
- return;
- }
- binding.add(var, value);
- }
-
}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInput.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInput.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInput.java
index 192e4b3..469a466 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInput.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInput.java
@@ -20,15 +20,17 @@ package org.apache.jena.sparql.resultset;
import java.io.InputStream;
import java.io.Reader;
+import java.io.StringReader;
import org.apache.jena.query.ResultSet;
import org.apache.jena.rdf.model.Model;
+import org.apache.jena.riot.resultset.rw.ResultsStAX;
import org.apache.jena.sparql.SystemARQ;
/**
* Code that reads an XML Result Set and builds the ARQ structure for the same.
*/
-
+@Deprecated
public class XMLInput {
public static ResultSet fromXML(InputStream in) {
return fromXML(in, null);
@@ -71,7 +73,7 @@ public class XMLInput {
public static SPARQLResult make(InputStream in, Model model) {
if ( SystemARQ.UseSAX )
return new XMLInputSAX(in, model);
- return new XMLInputStAX(in, model);
+ return ResultsStAX.read(in, model, null);
}
public static SPARQLResult make(Reader in) {
@@ -81,7 +83,7 @@ public class XMLInput {
public static SPARQLResult make(Reader in, Model model) {
if ( SystemARQ.UseSAX )
return new XMLInputSAX(in, model);
- return new XMLInputStAX(in, model);
+ return ResultsStAX.read(in, model, null);
}
public static SPARQLResult make(String str) {
@@ -91,7 +93,7 @@ public class XMLInput {
public static SPARQLResult make(String str, Model model) {
if ( SystemARQ.UseSAX )
return new XMLInputSAX(str, model);
- return new XMLInputStAX(str, model);
+ return ResultsStAX.read(new StringReader(str), model, null);
}
}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputSAX.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputSAX.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputSAX.java
index cb3d160..e9952bf 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputSAX.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputSAX.java
@@ -30,6 +30,9 @@ import org.apache.jena.datatypes.TypeMapper ;
import org.apache.jena.graph.Node ;
import org.apache.jena.graph.NodeFactory ;
import org.apache.jena.rdf.model.Model ;
+import org.apache.jena.riot.lang.LabelToNode;
+import org.apache.jena.riot.resultset.rw.XMLResults;
+import org.apache.jena.riot.system.SyntaxLabels;
import org.apache.jena.sparql.core.Var ;
import org.apache.jena.sparql.engine.ResultSetStream ;
import org.apache.jena.sparql.engine.binding.Binding ;
@@ -38,7 +41,6 @@ import org.apache.jena.sparql.engine.binding.BindingMap ;
import org.apache.jena.sparql.engine.iterator.QueryIterPlainWrapper ;
import org.apache.jena.sparql.graph.GraphFactory ;
import org.apache.jena.sparql.util.FmtUtils ;
-import org.apache.jena.sparql.util.LabelToNodeMap ;
import org.apache.jena.vocabulary.RDF ;
import org.xml.sax.* ;
import org.xml.sax.helpers.XMLReaderFactory ;
@@ -102,7 +104,7 @@ class XMLInputSAX extends SPARQLResult {
boolean askResult = false ;
int rowCount = 0 ;
- LabelToNodeMap bNodes = LabelToNodeMap.createBNodeMap() ;
+ LabelToNode bNodes = SyntaxLabels.createLabelToNode();
boolean accumulate = false ;
StringBuffer buff = new StringBuffer() ;
@@ -342,7 +344,7 @@ class XMLInputSAX extends SPARQLResult {
private void endElementBNode(String ns, String localName, String name) {
endAccumulate() ;
String bnodeId = buff.toString() ;
- Node node = bNodes.asNode(bnodeId) ;
+ Node node = bNodes.get(null, bnodeId) ;
if ( checkVarName("BNode: " + bnodeId) )
addBinding(binding, Var.alloc(varName), node) ;
}
@@ -373,5 +375,20 @@ class XMLInputSAX extends SPARQLResult {
@Override
public void skippedEntity(String name) throws SAXException {}
+
+ static protected void addBinding(BindingMap binding, Var var, Node value) {
+ Node n = binding.get(var);
+ if ( n != null ) {
+ // Same - silently skip.
+ if ( n.equals(value) )
+ return;
+ Log.warn(SPARQLResult.class,
+ String.format("Multiple occurences of a binding for variable '%s' with different values - ignored", var.getName()));
+ return;
+ }
+ binding.add(var, value);
+ }
+
+
}
}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputStAX.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputStAX.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputStAX.java
deleted file mode 100644
index 78da74a..0000000
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLInputStAX.java
+++ /dev/null
@@ -1,516 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.jena.sparql.resultset ;
-
-import java.io.InputStream ;
-import java.io.Reader ;
-import java.io.StringReader ;
-import java.util.ArrayList ;
-import java.util.List ;
-import java.util.NoSuchElementException ;
-
-import javax.xml.namespace.QName ;
-import javax.xml.stream.XMLInputFactory ;
-import javax.xml.stream.XMLStreamConstants ;
-import javax.xml.stream.XMLStreamException ;
-import javax.xml.stream.XMLStreamReader ;
-
-import org.apache.jena.atlas.lib.Closeable ;
-import org.apache.jena.atlas.logging.Log ;
-import org.apache.jena.datatypes.RDFDatatype ;
-import org.apache.jena.datatypes.TypeMapper ;
-import org.apache.jena.graph.Node ;
-import org.apache.jena.graph.NodeFactory ;
-import org.apache.jena.query.ARQ ;
-import org.apache.jena.query.QuerySolution ;
-import org.apache.jena.query.ResultSet ;
-import org.apache.jena.rdf.model.Model ;
-import org.apache.jena.sparql.ARQConstants ;
-import org.apache.jena.sparql.core.ResultBinding ;
-import org.apache.jena.sparql.core.Var ;
-import org.apache.jena.sparql.engine.binding.Binding ;
-import org.apache.jena.sparql.engine.binding.BindingFactory ;
-import org.apache.jena.sparql.engine.binding.BindingMap ;
-import org.apache.jena.sparql.graph.GraphFactory ;
-import org.apache.jena.sparql.util.LabelToNodeMap ;
-
-/**
- * Code that reads an XML Results format and builds the ARQ structure for the
- * same. Can read result set and boolean result forms. This is a streaming
- * implementation.
- */
-
-class XMLInputStAX extends SPARQLResult {
- private static final String XML_NS = ARQConstants.XML_NS ;
-
- public static ResultSet fromXML(InputStream in) {
- return fromXML(in, null) ;
- }
-
- public static ResultSet fromXML(InputStream in, Model model) {
- XMLInputStAX x = new XMLInputStAX(in, model) ;
- if ( !x.isResultSet() )
- throw new ResultSetException("Not a result set") ;
- return x.getResultSet() ;
- }
-
- public static ResultSet fromXML(String str) {
- return fromXML(str, null) ;
-
- }
-
- public static ResultSet fromXML(String str, Model model) {
- XMLInputStAX x = new XMLInputStAX(str, model) ;
- if ( !x.isResultSet() )
- throw new ResultSetException("Not a result set") ;
- return x.getResultSet() ;
- }
-
- public static boolean booleanFromXML(InputStream in) {
- XMLInputStAX x = new XMLInputStAX(in) ;
- return x.getBooleanResult() ;
- }
-
- public static boolean booleanFromXML(String str) {
- XMLInputStAX x = new XMLInputStAX(str) ;
- return x.getBooleanResult() ;
- }
-
- public XMLInputStAX(InputStream in) {
- this(in, null) ;
- }
-
- public XMLInputStAX(InputStream in, Model model) {
- XMLInputFactory xf = XMLInputFactory.newInstance() ;
- try {
- XMLStreamReader xReader = xf.createXMLStreamReader(in) ;
- worker(xReader, model) ;
- } catch (XMLStreamException e) {
- throw new ResultSetException("Can't initialize StAX parsing engine", e) ;
- } catch (Exception ex) {
- throw new ResultSetException("Failed when initializing the StAX parsing engine", ex) ;
- }
- }
-
- public XMLInputStAX(Reader in, Model model) {
- XMLInputFactory xf = XMLInputFactory.newInstance() ;
- try {
- XMLStreamReader xReader = xf.createXMLStreamReader(in) ;
- worker(xReader, model) ;
- } catch (XMLStreamException e) {
- throw new ResultSetException("Can't initialize StAX parsing engine", e) ;
- } catch (Exception ex) {
- throw new ResultSetException("Failed when initializing the StAX parsing engine", ex) ;
- }
- }
-
- public XMLInputStAX(String str) {
- this(str, null) ;
- }
-
- public XMLInputStAX(String str, Model model) {
- XMLInputFactory xf = XMLInputFactory.newInstance() ;
- try {
- Reader r = new StringReader(str) ;
- XMLStreamReader xReader = xf.createXMLStreamReader(r) ;
- worker(xReader, model) ;
- } catch (XMLStreamException e) {
- throw new ResultSetException("Can't initialize StAX parsing engine", e) ;
- } catch (Exception ex) {
- throw new ResultSetException("Failed when initializing the StAX parsing engine", ex) ;
- }
- }
-
- private void worker(XMLStreamReader xReader, Model model) {
- if ( model == null )
- model = GraphFactory.makeJenaDefaultModel() ;
-
- ResultSetStAX rss = new ResultSetStAX(xReader, model) ;
- if ( rss.isResultSet )
- set(rss) ;
- else
- set(rss.askResult) ;
- }
-
- // private XMLInputStAX()
-
- // -------- Result Set
-
- static class ResultSetStAX implements ResultSet, Closeable {
- // ResultSet variables
- QuerySolution current = null ;
- XMLStreamReader parser = null ;
- List<String> variables = new ArrayList<>() ;
- Binding binding = null ; // Current
- // binding
- // RefBoolean inputGraphLabels = new
- // RefBoolean(ARQ.inputGraphBNodeLabels, false) ;
- boolean inputGraphLabels = ARQ.isTrue(ARQ.inputGraphBNodeLabels) ;
-
- LabelToNodeMap bNodes = LabelToNodeMap.createBNodeMap() ;
-
- // Type
- boolean isResultSet = false ;
-
- // Result set
- boolean ordered = false ;
- boolean distinct = false ;
- boolean finished = false ;
- Model model = null ;
- int row = 0 ;
-
- // boolean
- boolean askResult = false ;
-
- ResultSetStAX(XMLStreamReader reader, Model model) {
- parser = reader ;
- this.model = model ;
- init() ;
- }
-
- private void init() {
- try {
- // Because all the tags are different, we could use one big
- // switch statement!
- skipTo(XMLResults.dfHead) ;
- processHead() ;
- skipTo(new String[]{XMLResults.dfResults, XMLResults.dfBoolean}, new String[]{XMLResults.dfResults}) ;
- // Next should be a <result>, <boolean> element or </results>
-
- // Need to decide what sort of thing we are reading.
-
- String tag = parser.getLocalName() ;
- if ( tag.equals(XMLResults.dfResults) ) {
- isResultSet = true ;
- processResults() ;
- }
- if ( tag.equals(XMLResults.dfBoolean) ) {
- isResultSet = false ;
- processBoolean() ;
- }
-
- } catch (XMLStreamException ex) {
- Log.warn(this, "XMLStreamException: " + ex.getMessage(), ex) ;
- }
- }
-
- @Override
- public boolean hasNext() {
- if ( !isResultSet )
- throw new ResultSetException("Not an XML result set") ;
-
- if ( finished )
- return false ;
-
- try {
- if ( binding == null )
- binding = getOneSolution() ;
- } catch (XMLStreamException ex) {
- staxError("XMLStreamException: " + ex.getMessage(), ex) ;
- }
- boolean b = (binding != null) ;
- if ( !b )
- close() ;
- return b ;
- }
-
- @Override
- public QuerySolution next() {
- return nextSolution() ;
- }
-
- @Override
- public Binding nextBinding() {
- if ( finished )
- throw new NoSuchElementException("End of XML Results") ;
- if ( !hasNext() )
- throw new NoSuchElementException("End of XML Results") ;
- Binding r = binding ;
- row++ ;
- binding = null ;
- return r ;
- }
-
- @Override
- public QuerySolution nextSolution() {
- Binding r = nextBinding() ;
- ResultBinding currentEnv = new ResultBinding(model, r) ;
- return currentEnv ;
- }
-
- @Override
- public int getRowNumber() {
- return row ;
- }
-
- @Override
- public List<String> getResultVars() {
- return variables ;
- }
-
- public boolean isOrdered() {
- return ordered ;
- }
-
- public boolean isDistinct() {
- return distinct ;
- }
-
- // No model - it was from a stream
- @Override
- public Model getResourceModel() {
- return null ;
- }
-
- @Override
- public void remove() {
- throw new UnsupportedOperationException(XMLInputStAX.class.getName()) ;
- }
-
- @Override
- public void close() {
- if ( finished )
- return ;
- finished = true ;
- try { parser.close() ; } catch (XMLStreamException ex) {}
- }
-
- // -------- Boolean stuff
-
- private void processBoolean() throws XMLStreamException {
- try {
- // At start of <boolean>
- String s = parser.getElementText() ;
- if ( s.equalsIgnoreCase("true") ) {
- askResult = true ;
- return ;
- }
- if ( s.equalsIgnoreCase("false") ) {
- askResult = false ;
- return ;
- }
- throw new ResultSetException("Unknown boolean value: " + s) ;
- } finally {
- close() ;
- }
- }
-
- // --------
-
- private void skipTo(String tag1) throws XMLStreamException {
- skipTo(new String[]{tag1}, null) ;
- }
-
- private void skipTo(String[] startElementNames, String[] stopElementNames) throws XMLStreamException {
- boolean found = false ;
- loop : while (parser.hasNext()) {
- int event = parser.next() ;
- switch (event) {
- case XMLStreamConstants.END_DOCUMENT :
- break loop ;
- case XMLStreamConstants.END_ELEMENT :
- if ( stopElementNames == null )
- break ;
-
- String endTag = parser.getLocalName() ;
- if ( endTag != null && containsName(stopElementNames, endTag) )
- return ;
- break ;
- case XMLStreamConstants.START_ELEMENT :
- if ( startElementNames == null )
- break ;
- QName qname = parser.getName() ;
- if ( !qname.getNamespaceURI().equals(XMLResults.baseNamespace) )
- staxError("skipToHead: Unexpected tag: " + qname) ;
- if ( containsName(startElementNames, qname.getLocalPart()) )
- return ;
- break ;
- default :
- // Skip stuff
- }
- }
-
- if ( !found ) {
- String s1 = "" ;
- if ( startElementNames != null )
- s1 = String.join(", ", startElementNames) ;
-
- String s2 = "" ;
- if ( stopElementNames != null )
- s2 = String.join(", ", stopElementNames) ;
- Log.warn(this, "Failed to find start and stop of specified elements: " + s1 + " :: " + s2) ;
- }
- }
-
- private boolean containsName(String[] elementNames, String eName) {
- for ( String s : elementNames )
- {
- if ( s.equals( eName ) )
- {
- return true;
- }
- }
- return false ;
- }
-
- private void processHead() throws XMLStreamException {
- // Should be at the start of head
-
- loop : while (parser.hasNext()) {
- int event = parser.next() ;
- String tag = null ;
-
- switch (event) {
- case XMLStreamConstants.END_DOCUMENT :
- break loop ;
- case XMLStreamConstants.END_ELEMENT :
- tag = parser.getLocalName() ;
- if ( isTag(tag, XMLResults.dfHead) )
- break loop ;
- break ;
- case XMLStreamConstants.START_ELEMENT :
- tag = parser.getLocalName() ;
- if ( isTag(tag, XMLResults.dfHead) )
- break ; // This switch statement
- if ( isTag(tag, XMLResults.dfVariable) ) {
- String varname = parser.getAttributeValue(null, XMLResults.dfAttrVarName) ;
- variables.add(varname) ;
- break ;
- }
- if ( isTag(tag, XMLResults.dfLink) )
- break ;
-
- staxError("Unknown XML element: " + tag) ;
- break ;
- default :
- }
- }
- }
-
- // -------- Result Set
-
- private void processResults() {
- return ;
- }
-
- private Binding getOneSolution() throws XMLStreamException {
- if ( finished )
- return null ;
- // At the start of <result>
- BindingMap binding = BindingFactory.create() ;
- String varName = null ;
- while (parser.hasNext()) {
- int event = parser.next() ;
- String tag = null ;
-
- switch (event) {
- case XMLStreamConstants.END_DOCUMENT :
- staxError("End of document while processing solution") ;
- return null ;
- case XMLStreamConstants.END_ELEMENT :
- tag = parser.getLocalName() ;
- if ( isTag(tag, XMLResults.dfSolution) )
- return binding ;
- if ( isTag(tag, XMLResults.dfResults) )
- // Hit the end of solutions.
- return null ;
- break ;
- case XMLStreamConstants.START_ELEMENT :
- tag = parser.getLocalName() ;
- if ( isTag(tag, XMLResults.dfSolution) ) {
- binding = BindingFactory.create() ;
- break ;
- }
- if ( isTag(tag, XMLResults.dfBinding) ) {
- varName = parser.getAttributeValue(null, XMLResults.dfAttrVarName) ;
- break ;
- }
- // URI, literal, bNode, unbound.
- if ( isTag(tag, XMLResults.dfBNode) ) {
- String label = parser.getElementText() ;
- Node node = null ;
- // if ( inputGraphLabels.getValue() )
- if ( inputGraphLabels )
- node = NodeFactory.createBlankNode(label) ;
- else
- node = bNodes.asNode(label) ;
- addBinding(binding, Var.alloc(varName), node) ;
- break ;
- }
-
- if ( isTag(tag, XMLResults.dfLiteral) ) {
- String datatype = parser.getAttributeValue(null, XMLResults.dfAttrDatatype) ;
-
- // String langTag = parser.getAttributeValue(null,
- // "lang") ;
-
- // Woodstox needs XML_NS despite the javadoc of StAX
- // "If the namespaceURI is null the namespace is not checked for equality"
- // StAX(.codehaus.org) copes both ways round
- String langTag = parser.getAttributeValue(XML_NS, "lang") ;
-
- // Works for XML literals (returning them as a
- // string)
- String text = parser.getElementText() ;
-
- RDFDatatype dType = null ;
- if ( datatype != null )
- dType = TypeMapper.getInstance().getSafeTypeByName(datatype) ;
-
- Node n = NodeFactory.createLiteral(text, langTag, dType) ;
- if ( varName == null )
- throw new ResultSetException("No name for variable") ;
- addBinding(binding, Var.alloc(varName), n) ;
- break ;
- }
-
- if ( isTag(tag, XMLResults.dfUnbound) ) {
- break ;
- }
- if ( isTag(tag, XMLResults.dfURI) ) {
- String uri = parser.getElementText() ;
- Node node = NodeFactory.createURI(uri) ;
- addBinding(binding, Var.alloc(varName), node) ;
- break ;
- }
- break ;
- default :
- }
- }
- staxError("getOneSolution: Hit end unexpectedly") ;
- return null ;
- }
-
- private boolean isTag(String localName, String expectedName) {
- if ( !parser.getNamespaceURI().equals(XMLResults.baseNamespace) )
- return false ;
- return localName.equals(expectedName) ;
- }
-
- private void staxError(String msg) {
- Log.warn(this, "StAX error: " + msg) ;
- throw new ResultSetException(msg) ;
- }
-
- private void staxError(String msg, Throwable th) {
- Log.warn(this, "StAX error: " + msg, th) ;
- throw new ResultSetException(msg, th) ;
- }
- }
-}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutput.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutput.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutput.java
index a30d5ae..48e85f1 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutput.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutput.java
@@ -20,8 +20,12 @@ package org.apache.jena.sparql.resultset;
import java.io.OutputStream ;
+import org.apache.jena.query.ARQ;
import org.apache.jena.query.ResultSet ;
-
+import org.apache.jena.riot.resultset.ResultSetLang;
+import org.apache.jena.riot.resultset.rw.ResultSetWriterXML;
+import org.apache.jena.riot.resultset.rw.ResultsWriter;
+import org.apache.jena.sparql.util.Context;
public class XMLOutput extends OutputBase
{
@@ -45,11 +49,14 @@ public class XMLOutput extends OutputBase
@Override
public void format(OutputStream out, ResultSet resultSet) {
- XMLOutputResultSet xOut = new XMLOutputResultSet(out);
- xOut.setStylesheetURL(stylesheetURL);
- xOut.setXmlInst(includeXMLinst);
- ResultSetApply a = new ResultSetApply(resultSet, xOut);
- a.apply();
+ Context cxt = ARQ.getContext().copy();
+ if ( stylesheetURL != null )
+ cxt.set(ResultSetWriterXML.xmlStylesheet, stylesheetURL);
+ cxt.set(ResultSetWriterXML.xmlInstruction, includeXMLinst);
+ ResultsWriter.create()
+ .context(cxt)
+ .lang(ResultSetLang.SPARQLResultSetXML)
+ .write(out, resultSet);
}
/** @return Returns the includeXMLinst. */
@@ -70,7 +77,14 @@ public class XMLOutput extends OutputBase
@Override
public void format(OutputStream out, boolean booleanResult) {
- XMLOutputASK xOut = new XMLOutputASK(out);
- xOut.exec(booleanResult);
+ Context cxt = ARQ.getContext().copy();
+ if ( stylesheetURL != null )
+ cxt.set(ResultSetWriterXML.xmlStylesheet, stylesheetURL);
+ cxt.set(ResultSetWriterXML.xmlInstruction, includeXMLinst);
+ ResultsWriter.create()
+ .context(cxt)
+ .lang(ResultSetLang.SPARQLResultSetXML)
+ .build()
+ .write(out, booleanResult);
}
}
http://git-wip-us.apache.org/repos/asf/jena/blob/716b86cf/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutputASK.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutputASK.java b/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutputASK.java
deleted file mode 100644
index 66ffe81..0000000
--- a/jena-arq/src/main/java/org/apache/jena/sparql/resultset/XMLOutputASK.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.apache.jena.sparql.resultset;
-
-import java.io.OutputStream;
-
-import org.apache.jena.atlas.io.IndentedWriter;
-
-/** XML Output (ASK format) */
-
-public class XMLOutputASK implements XMLResults {
- String stylesheetURL = null;
- IndentedWriter out;
- int bNodeCounter = 0;
- boolean xmlInst = true;
-
- public XMLOutputASK(OutputStream outStream) {
- this(outStream, null);
- }
-
- public XMLOutputASK(OutputStream outStream, String stylesheetURL) {
- this(new IndentedWriter(outStream), stylesheetURL);
- }
-
- public XMLOutputASK(IndentedWriter indentedOut, String stylesheetURL) {
- out = indentedOut;
- this.stylesheetURL = stylesheetURL;
- }
-
- public void exec(boolean result) {
- if ( xmlInst )
- out.println("<?xml version=\"1.0\"?>");
-
- if ( stylesheetURL != null )
- out.println("<?xml-stylesheet type=\"text/xsl\" href=\"" + stylesheetURL + "\"?>");
-
- out.println("<" + dfRootTag + " xmlns=\"" + dfNamespace + "\">");
- out.incIndent(INDENT);
-
- // Head
- out.println("<" + dfHead + ">");
- out.incIndent(INDENT);
- if ( false ) {
- String link = "UNSET";
- out.println("<link href=\"" + link + "\"/>");
- }
- out.decIndent(INDENT);
- out.println("</" + dfHead + ">");
-
- if ( result )
- out.println("<boolean>true</boolean>");
- else
- out.println("<boolean>false</boolean>");
- out.decIndent(INDENT);
- out.println("</" + dfRootTag + ">");
- out.flush();
- }
-}