package com.bigdata.blueprints;
import java.util.Properties;
import junit.framework.TestCase;
import org.apache.log4j.Logger;
import org.openrdf.query.QueryLanguage;
import com.bigdata.rdf.sail.BigdataSailRepositoryConnection;
import com.bigdata.rdf.sail.BigdataSailTupleQuery;
import com.bigdata.rdf.sparql.ast.QueryRoot;
import com.bigdata.rdf.store.BDS;
import com.tinkerpop.blueprints.Edge;
import com.tinkerpop.blueprints.Vertex;
import cutthecrap.utils.striterators.ICloseableIterator;
public class TestPathConstraints extends TestCase {
private static final transient Logger log =
Logger.getLogger(TestPathConstraints.class);
public void testPathLength() throws Exception {
final Properties props = new Properties();
props.setProperty(BigdataGraph.Options.LAX_EDGES, "true");
final BigdataGraphEmbedded graph = (BigdataGraphEmbedded)
BigdataGraphFactory.create(
SimpleBlueprintsValueFactory.INSTANCE, props);
try {
for (int i = 0; i < 5; i++) {
graph.addVertex(""+i);
if (i > 0) {
final PartialVertex from = new PartialVertex(""+(i-1));
final PartialVertex to = new PartialVertex(""+i);
final PartialVertex edge = new PartialVertex((i-1)+""+i);
final PartialVertex foo = new PartialVertex("test:foo");
final Edge e = graph.addEdge((i-1)+""+i, from, to, "foo");
graph.addEdge("test:foo", from, to, null);
graph.addEdge(SimpleBlueprintsValueFactory.TYPE.toString(), edge, foo, null);
e.setProperty("some:prop", "someVal");
}
}
graph.commit();
if (log.isDebugEnabled()) {
log.debug("\n"+graph.dumpStore());
}
{ // path limits and constraints
final String queryStr =
"select * " +
"where { " +
" service bd:alp { " +
" <id:0> ?eid ?to . " +
" hint:Prior hint:alp.pathExpr \"true\" . " +
" ?eid <bigdata:type> <test:foo> . " +
" ?eid <some:prop> \"someVal\" . " +
" hint:Group hint:alp.lowerBound 1 . " +
" hint:Group hint:alp.upperBound ?upper . " +
" } " +
"}";
// final BigdataSailRepositoryConnection cxn = graph
// .getReadConnection();
// try {
// final BigdataSailTupleQuery query = (BigdataSailTupleQuery) cxn
// .prepareQuery(QueryLanguage.SPARQL, queryStr);
// final QueryRoot optimized = query.optimize();
// if (log.isDebugEnabled()) {
// log.debug("optimized:\n" + optimized);
// }
// } finally {
// cxn.close();
// }
for (int i = 1; i < 5; i++) {
final ICloseableIterator<BigdataBindingSet> selection =
graph.select(queryStr.replace("?upper", ""+i));
try {
int n = 0;
while (selection.hasNext()) {
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
n++;
}
assertTrue(n == i);
} finally {
selection.close();
}
}
}
{ // go bi-directional one-hop from v2 with a ZLP
final String queryStr =
"select * " +
"where { " +
" service bd:alp { " +
" <id:2> <test:foo> ?to . " +
" hint:Prior hint:alp.pathExpr true . " +
" hint:Group hint:alp.lowerBound 0 . " +
" hint:Group hint:alp.upperBound 1 . " +
" hint:Group hint:alp.bidirectional true . " +
" } " +
"}";
// final BigdataSailRepositoryConnection cxn = graph
// .getReadConnection();
// try {
// final BigdataSailTupleQuery query = (BigdataSailTupleQuery) cxn
// .prepareQuery(QueryLanguage.SPARQL, queryStr);
// final QueryRoot optimized = query.optimize();
// if (log.isDebugEnabled()) {
// log.debug("optimized:\n" + optimized);
// }
// } finally {
// cxn.close();
// }
final ICloseableIterator<BigdataBindingSet> selection = graph.select(queryStr);
try {
int n = 0;
while (selection.hasNext()) {
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
n++;
}
assertTrue(n == 3);
} finally {
selection.close();
}
}
} finally {
graph.shutdown();
}
}
public void testPathFilters() throws Exception {
final Properties props = new Properties();
props.setProperty(BigdataGraph.Options.LAX_EDGES, "true");
final BigdataGraphEmbedded graph = (BigdataGraphEmbedded)
BigdataGraphFactory.create(
SimpleBlueprintsValueFactory.INSTANCE, props);
try {
for (int i = 0; i < 5; i++) {
graph.addVertex(""+i);
if (i > 0) {
final PartialVertex from = new PartialVertex(""+(i-1));
final PartialVertex to = new PartialVertex(""+i);
final PartialVertex edge = new PartialVertex((i-1)+""+i);
final PartialVertex foo = new PartialVertex("test:foo");
final Edge e = graph.addEdge((i-1)+""+i, from, to, "foo");
graph.addEdge("test:foo", from, to, null);
graph.addEdge(SimpleBlueprintsValueFactory.TYPE.toString(), edge, foo, null);
e.setProperty("some:prop", i);
}
}
graph.commit();
if (log.isDebugEnabled()) {
log.debug("\n"+graph.dumpStore());
}
{ // path filter
final String queryStr =
"select * " +
"where { " +
" service bd:alp { " +
" <id:0> ?eid ?to . " +
" hint:Prior hint:alp.pathExpr \"true\" . " +
" ?eid <bigdata:type> <test:foo> . " +
" ?eid <some:prop> ?val . " +
" filter(?val < 3) . " +
" hint:Group hint:alp.lowerBound 0 . " +
" hint:Group hint:alp.upperBound 100 . " +
" } " +
"}";
// showOptimizedAST(graph, queryStr);
final ICloseableIterator<BigdataBindingSet> selection = graph.select(queryStr);
try {
int n = 0;
while (selection.hasNext()) {
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
n++;
}
assertTrue(n == 3);
} finally {
selection.close();
}
}
{ // path filter + incoming bindings
/*
* This tests whether vars used by the service are projected
* in correctly.
*/
final String queryStr =
"select * " +
"where { " +
" values (?max) { " +
" (3) " +
" } " +
" service bd:alp { " +
" <id:0> ?eid ?to . " +
" hint:Prior hint:alp.pathExpr \"true\" . " +
" ?eid <bigdata:type> <test:foo> . " +
" ?eid <some:prop> ?val . " +
" filter(?val < ?max) . " +
" hint:Group hint:alp.lowerBound 0 . " +
" hint:Group hint:alp.upperBound 100 . " +
" } " +
"}";
showOptimizedAST(graph, queryStr);
final ICloseableIterator<BigdataBindingSet> selection = graph.select(queryStr);
try {
int n = 0;
while (selection.hasNext()) {
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
n++;
}
assertTrue(n == 3);
} finally {
selection.close();
}
}
} finally {
graph.shutdown();
}
}
public void testPred() throws Exception {
final Properties props = new Properties();
props.setProperty(BigdataGraph.Options.LAX_EDGES, "true");
final BigdataGraphEmbedded graph = (BigdataGraphEmbedded)
BigdataGraphFactory.create(
SimpleBlueprintsValueFactory.INSTANCE, props);
try {
// for (int i = 0; i < 5; i++) {
// graph.addVertex("v"+i);
// if (i > 0) {
// final PartialVertex from = new PartialVertex("v"+(i-1));
// final PartialVertex to = new PartialVertex("v"+i);
// final Edge e = graph.addEdge("e"+(i-1)+""+i, from, to, "edge");
// }
// }
/*
* Create more than one path to v4 and see if the ALP op can
* handle it.
*/
final Vertex v0 = graph.addVertex("v0");
final Vertex v1 = graph.addVertex("v1");
final Vertex v2 = graph.addVertex("v2");
final Vertex v3a = graph.addVertex("v3a");
final Vertex v3b = graph.addVertex("v3b");
final Vertex v4 = graph.addVertex("v4");
graph.addEdge("e01", v0, v1, "edge");
graph.addEdge("e12", v1, v2, "edge");
graph.addEdge("e23a", v2, v3a, "edge");
graph.addEdge("e23b", v2, v3b, "edge");
graph.addEdge("e3a4", v3a, v4, "edge");
graph.addEdge("e3b4", v3b, v4, "edge");
graph.commit();
if (log.isDebugEnabled()) {
log.debug("\n"+graph.dumpStore());
}
{ // path predecessor
final String queryStr =
"select ?from ?edge ?to " +
"where { " +
" service bd:alp { " +
" <id:v0> ?e ?to . " +
" hint:Prior hint:alp.pathExpr \"true\" . " +
" filter(?e != <bigdata:type>) . " +
" hint:Group hint:alp.lowerBound 0 . " +
" hint:Group hint:alp.upperBound 10 . " +
" hint:Group hint:alp.edgeVar ?edge . " +
" } " +
// " ?from ?edge ?to . " +
// " filter(?to = <id:v4>) . " +
"}";
// final BigdataSailRepositoryConnection cxn = graph
// .getReadConnection();
// try {
// final BigdataSailTupleQuery query = (BigdataSailTupleQuery) cxn
// .prepareQuery(QueryLanguage.SPARQL, queryStr);
// final QueryRoot optimized = query.optimize();
// if (log.isDebugEnabled()) {
// log.debug("optimized:\n" + optimized);
// }
// } finally {
// cxn.close();
// }
final ICloseableIterator<BigdataBindingSet> selection =
graph.select(queryStr);
try {
int n = 0;
while (selection.hasNext()) {
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
n++;
}
// assertTrue(n == 2);
} finally {
selection.close();
}
}
if (false) { // node and optionally any edges using ZLP
final String queryStr =
"select ?from ?edge ?to " +
"where { " +
" service bd:alp { " +
" ?id ?e ?to . " +
" hint:Prior hint:alp.pathExpr \"true\" . " +
" filter(?e != <bigdata:type>) . " +
" hint:Group hint:alp.lowerBound 0 . " +
" hint:Group hint:alp.upperBound 1 . " +
" hint:Group hint:alp.edgeVar ?edge . " +
" } " +
// " optional { ?from ?edge ?to . } " +
"}";
// final BigdataSailRepositoryConnection cxn = graph
// .getReadConnection();
// try {
// final BigdataSailTupleQuery query = (BigdataSailTupleQuery) cxn
// .prepareQuery(QueryLanguage.SPARQL, queryStr);
// final QueryRoot optimized = query.optimize();
// if (log.isDebugEnabled()) {
// log.debug("optimized:\n" + optimized);
// }
// } finally {
// cxn.close();
// }
{ // v0 has an edge
final ICloseableIterator<BigdataBindingSet> selection =
graph.select(queryStr.replace("?id", "<id:v0>"));
try {
int n = 0;
while (selection.hasNext()) {
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
n++;
}
assertTrue(n == 2);
} finally {
selection.close();
}
}
{ // v4 has no edge
final ICloseableIterator<BigdataBindingSet> selection =
graph.select(queryStr.replace("?id", "<id:v4>"));
try {
assertTrue(selection.hasNext());
final BigdataBindingSet bbs = selection.next();
if (log.isDebugEnabled()) {
log.debug(bbs);
}
assertFalse(selection.hasNext());
assertFalse(bbs.isBound("edge"));
} finally {
selection.close();
}
}
}
} finally {
graph.shutdown();
}
}
public void testJoinOrder() throws Exception {
final Properties props = new Properties();
props.setProperty(BigdataGraph.Options.LAX_EDGES, "true");
final BigdataGraphEmbedded graph = (BigdataGraphEmbedded)
BigdataGraphFactory.create(
SimpleBlueprintsValueFactory.INSTANCE, props);
try {
for (int i = 0; i < 5; i++) {
final Vertex v = graph.addVertex("v"+i);
if (i > 0) {
final PartialVertex from = new PartialVertex("v"+(i-1));
final PartialVertex to = new PartialVertex("v"+i);
graph.addEdge("e"+(i-1)+""+i, from, to, "edge");
} else {
v.setProperty("foo", "bar");
}
}
graph.commit();
if (log.isDebugEnabled()) {
log.debug("\n"+graph.dumpStore());
}
{ // join ordering
final String queryStr =
"select ?from ?edge ?to " +
"where { " +
" ?id <"+BDS.SEARCH+"> \"bar\" . " +
" service bd:alp { " +
" ?id ?e ?to . " +
" hint:Prior hint:alp.pathExpr \"true\" . " +
" filter(?e != <bigdata:type>) . " +
" hint:Group hint:alp.lowerBound 0 . " +
" hint:Group hint:alp.upperBound 10 . " +
" hint:Group hint:alp.edgeVar ?edge . " +
" } " +
" ?from ?edge ?to . " +
" ?from <bigdata:type> <bigdata:Vertex> . " +
"}";
final BigdataSailRepositoryConnection cxn = graph.cxn();
try {
final BigdataSailTupleQuery query = (BigdataSailTupleQuery) cxn
.prepareQuery(QueryLanguage.SPARQL, queryStr);
final QueryRoot optimized = query.optimize();
if (log.isDebugEnabled()) {
log.debug("optimized:\n" + optimized);
}
} finally {
cxn.close();
}
// final ICloseableIterator<BigdataBindingSet> selection =
// graph.select(queryStr);
// try {
// int n = 0;
// while (selection.hasNext()) {
// final BigdataBindingSet bbs = selection.next();
// if (log.isDebugEnabled()) {
// log.debug(bbs);
// }
// n++;
// }
//// assertTrue(n == 2);
// } finally {
// selection.close();
// }
}
} finally {
graph.shutdown();
}
}
private void showOptimizedAST(final BigdataGraph graph,
final String queryStr) throws Exception {
final BigdataSailRepositoryConnection cxn = (BigdataSailRepositoryConnection) graph.cxn();
try {
final BigdataSailTupleQuery query = (BigdataSailTupleQuery) cxn
.prepareQuery(QueryLanguage.SPARQL, queryStr);
final QueryRoot optimized = query.optimize();
if (log.isDebugEnabled()) {
log.debug("optimized:\n" + optimized);
}
} finally {
cxn.close();
}
}
}