I want to create a SPARQL queries from Java (particularly, Jena and ARQ). I want to make it possible for a user who may not know anything about SPARQL to make a query by just writing (eg, in a console from Eclipse) the word he wants to search for. The following code gives an example of what I'm looking for. How can I interpolate the string word
into the query?
String word="someThingToFind"; // a variable entered by the user who want to request my data
String queryString =
"Select ?a ?b"+
" Where { ...."+
" Filter (regex(?a = ".concat(word)+ "))"+// word is the String variable
" }";
Query query = QueryFactory.create(queryString, Syntax.syntaxARQ);
QueryExecution qe = QueryExecutionFactory.create(query, model);
ResultSet results = qe.execSelect();
ResultSetFormatter.out(System.out, results, query);
qe.close();
This line in your code
Filter (regex(?a = ".concat(word)+ "))"+// word is the String variable
will produce SPARQL text like (assuming that word
is banana):
Filter (regex(?a = banana))
That's not how regex
is used in SPARQL. When you're trying to parameterize queries, it's a good idea to make sure that you've got a working form to begin with, and then you can start making parts of it parameterized. Sure enough, if you take a stripped down version of your query:
select * where { filter(regex(?a = "banana")) }
and paste it into the sparql.org's validator , you'll see that it's a syntax error. However, the documentation for regex
has some examples. regex
takes two required arguments, and one optional argument:
"i"
, for case insensitive matching) To use regex
, you'd need to do something like:
"filter(regex(?a, \"" + word + "\"))"
so that you can get
filter(regex(?a,"banana"))
in the query. Of course, this opens you up to a classic injection problems, since you've got a problem if word
contains "
. This is why you should use a ParameterizedSparqlString ; you can have
filter(regex(?a,?word))
and then just replace ?word
with the value of word
, and all the escaping will be handled correctly.
There are two options to include parameters in query strings. You don't need to use the filter unless you want to use more advanced functions, like patterns. When selecting triples, you can just use the user provided value as the triple's object:
... WHERE {
?subject pred:somePred "value"
}
To include the value in the query it is best to use a QuerySolutionMap to bind a SPARQL parameter to some value, as documented on http://jena.apache.org/documentation/query/parameterized-sparql-strings.html Otherwise, escape all special characters in the user provided string (" most important) and use Java string concatenation to include the value. The above example would become
... WHERE {
?subject pred:somePred ?value
}
Later you would bind the name "value" to the user provided value.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.