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 2018/08/31 12:05:12 UTC
[22/27] jena git commit: JENA-1494: Handle any dataset
JENA-1494: Handle any dataset
Project: http://git-wip-us.apache.org/repos/asf/jena/repo
Commit: http://git-wip-us.apache.org/repos/asf/jena/commit/80a2f7b5
Tree: http://git-wip-us.apache.org/repos/asf/jena/tree/80a2f7b5
Diff: http://git-wip-us.apache.org/repos/asf/jena/diff/80a2f7b5
Branch: refs/heads/master
Commit: 80a2f7b543137fd35cb1e8c2b55fa432854d5f18
Parents: 2ec9065
Author: Andy Seaborne <an...@apache.org>
Authored: Sun Aug 26 21:46:07 2018 +0100
Committer: Andy Seaborne <an...@apache.org>
Committed: Sun Aug 26 23:27:13 2018 +0100
----------------------------------------------------------------------
.../sparql/core/DatasetGraphFilteredView.java | 3 ++
.../jena/fuseki/access/DataAccessCtl.java | 35 +++++++++---------
.../access/Filtered_SPARQL_QueryDataset.java | 21 +++++------
.../jena/fuseki/access/SecurityPolicy.java | 3 +-
.../fuseki/access/TestSecurityFilterFuseki.java | 18 ++++++----
.../fuseki/access/TestSecurityFilterLocal.java | 38 ++++++++++++--------
.../apache/jena/fuseki/cmds/FusekiBasicCmd.java | 4 +--
.../jena/fuseki/servlets/SPARQL_Query.java | 6 ++--
8 files changed, 69 insertions(+), 59 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-arq/src/main/java/org/apache/jena/sparql/core/DatasetGraphFilteredView.java
----------------------------------------------------------------------
diff --git a/jena-arq/src/main/java/org/apache/jena/sparql/core/DatasetGraphFilteredView.java b/jena-arq/src/main/java/org/apache/jena/sparql/core/DatasetGraphFilteredView.java
index 3084e33..4c49bd1 100644
--- a/jena-arq/src/main/java/org/apache/jena/sparql/core/DatasetGraphFilteredView.java
+++ b/jena-arq/src/main/java/org/apache/jena/sparql/core/DatasetGraphFilteredView.java
@@ -114,6 +114,9 @@ public class DatasetGraphFilteredView extends DatasetGraphReadOnly implements Da
@Override
public Graph getUnionGraph() {
+ // Does not exploit TDB-isms, but is general.
+ // To exploit TDB, we'd have to modify the dataset
+ // to set union graph but that's not per-request.
return new GraphUnionRead(this, visibleGraphs);
}
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/DataAccessCtl.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/DataAccessCtl.java b/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/DataAccessCtl.java
index dc8c913..3bc0812 100644
--- a/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/DataAccessCtl.java
+++ b/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/DataAccessCtl.java
@@ -35,20 +35,23 @@ import org.apache.jena.sparql.core.DatasetGraph;
import org.apache.jena.sparql.core.DatasetGraphFilteredView;
import org.apache.jena.sparql.util.Context;
import org.apache.jena.sparql.util.Symbol;
+import org.apache.jena.sys.JenaSystem;
import org.eclipse.jetty.security.SecurityHandler;
/** A library of operations related to data acess sexurity for Fuseki */
public class DataAccessCtl {
-
+ static { JenaSystem.init(); }
+
/**
* Flag for whether this is data access controlled or not - boolean false or undef for "not
- * controlled".
+ * controlled". This is an alternative to {@link DatasetGraphAccessControl}.
*/
public static final Symbol symControlledAccess = Symbol.create(VocabSecurity.getURI() + "controlled");
/**
* Symbol for the {@link SecurityRegistry}. Must be present if
* {@link #symControlledAccess} indicates data access control.
+ * This is an alternative to {@link DatasetGraphAccessControl}.
*/
public static final Symbol symSecurityRegistry = Symbol.create(VocabSecurity.getURI() + "registry");
@@ -56,30 +59,26 @@ public class DataAccessCtl {
public static final Function<HttpAction, String> requestUserServlet = (action)->action.request.getRemoteUser();
/**
+ * Get the user from {@code ?user} query string parameter. Use carefully; for situations where the user name has
+ * been authenticated already and is being passed on securely. Also for testing.
+ */
+ public static final Function<HttpAction, String> paramUserServlet = (action)->action.request.getParameter("user");
+
+ /**
* Add data access control information on a {@link DatasetGraph}. This modifies the
* {@link DatasetGraph}'s {@link Context}.
*/
- private static void controlledDataset(DatasetGraph dsg, SecurityRegistry reg) {
- // Or wrapper.
+ private static void addSecurityRegistry(DatasetGraph dsg, SecurityRegistry reg) {
dsg.getContext().set(symControlledAccess, true);
dsg.getContext().set(symSecurityRegistry, reg);
}
-// /**
-// * Enable data access control on a {@link Dataset}. This modifies the
-// * {@link Dataset}'s {@link Context}.
-// */
-// private static void controlledDataset(Dataset ds, SecurityRegistry reg) {
-// ds.getContext().set(symControlledAccess, true);
-// ds.getContext().set(symSecurityRegistry, reg);
-// }
-
/**
- * Return a {@link DatasetGraph} with added data access control. Use of the original
- * {@code DatasetGraph} is not controlled.
+ * Return a {@link DatasetGraph} with added data access control.
+ * Use of the original {@code DatasetGraph} is not controlled.
*/
- public static Dataset wrapControlledDataset(Dataset dsBase, SecurityRegistry reg) {
- DatasetGraph dsg = wrapControlledDataset(dsBase.asDatasetGraph(), reg);
+ public static Dataset controlledDataset(Dataset dsBase, SecurityRegistry reg) {
+ DatasetGraph dsg = controlledDataset(dsBase.asDatasetGraph(), reg);
return DatasetFactory.wrap(dsg);
}
@@ -87,7 +86,7 @@ public class DataAccessCtl {
* Return a {@link DatasetGraph} with added data access control. Use of the original
* {@code DatasetGraph} is not controlled.
*/
- public static DatasetGraph wrapControlledDataset(DatasetGraph dsgBase, SecurityRegistry reg) {
+ public static DatasetGraph controlledDataset(DatasetGraph dsgBase, SecurityRegistry reg) {
if ( dsgBase instanceof DatasetGraphAccessControl ) {
DatasetGraphAccessControl dsgx = (DatasetGraphAccessControl)dsgBase;
if ( reg == dsgx.getRegistry() )
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/Filtered_SPARQL_QueryDataset.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/Filtered_SPARQL_QueryDataset.java b/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/Filtered_SPARQL_QueryDataset.java
index 49efc4f..8162f91 100644
--- a/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/Filtered_SPARQL_QueryDataset.java
+++ b/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/Filtered_SPARQL_QueryDataset.java
@@ -18,6 +18,8 @@
package org.apache.jena.fuseki.access;
+import java.util.Collection;
+import java.util.Collections;
import java.util.function.Function;
import org.apache.jena.fuseki.servlets.ActionService;
@@ -38,6 +40,12 @@ public class Filtered_SPARQL_QueryDataset extends SPARQL_QueryDataset {
}
@Override
+ protected Collection<String> customParams() {
+ // The additional ?user.
+ return Collections.singletonList("user");
+ }
+
+ @Override
protected QueryExecution createQueryExecution(HttpAction action, Query query, Dataset dataset) {
// Server database, not the possibly dynamically built "dataset"
DatasetGraph dsg = action.getDataset();
@@ -46,20 +54,9 @@ public class Filtered_SPARQL_QueryDataset extends SPARQL_QueryDataset {
if ( ! DataAccessCtl.isAccessControlled(dsg) )
return super.createQueryExecution(action, query, dataset);
- // XXX Generalize to any DSG.
SecurityPolicy sCxt = DataAccessLib.getSecurityPolicy(action, dataset.asDatasetGraph(), requestUser);
-
+ // A QueryExecution for controlled access
QueryExecution qExec = sCxt.createQueryExecution(query, dsg);
-
-// if ( dsg instanceof DatasetGraphAccessControl ) {
-// // Take off one layer.
-// dsg = DatasetGraphAccessControl.removeWrapper(dsg);
-// // Add back the Dataset for the createQueryExecution call.
-// dataset = DatasetFactory.wrap(dsg);
-// }
-// QueryExecution qExec = super.createQueryExecution(action, query, dataset);
-// if ( sCxt != null )
-// sCxt.filterTDB(dsg, qExec);
return qExec;
}
}
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/SecurityPolicy.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/SecurityPolicy.java b/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/SecurityPolicy.java
index c0d420a..ca19794 100644
--- a/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/SecurityPolicy.java
+++ b/jena-fuseki2/jena-fuseki-access/src/main/java/org/apache/jena/fuseki/access/SecurityPolicy.java
@@ -114,8 +114,7 @@ public class SecurityPolicy {
if ( quad.isDefaultGraph() )
return matchDefaultGraph;
if ( quad.isUnionGraph() )
- // XXX What to do here.
- // Need special union graph?
+ // Union graph is automatically there but its visible contents are different.
return true;
return graphNames.contains(quad.getGraph());
};
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterFuseki.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterFuseki.java b/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterFuseki.java
index 7050ef0..c9d188a 100644
--- a/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterFuseki.java
+++ b/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterFuseki.java
@@ -41,6 +41,7 @@ import org.apache.jena.rdf.model.RDFNode;
import org.apache.jena.rdfconnection.RDFConnection;
import org.apache.jena.rdfconnection.RDFConnectionFactory;
import org.apache.jena.sparql.core.DatasetGraph;
+import org.apache.jena.sparql.core.DatasetGraphFactory;
import org.apache.jena.sparql.core.Quad;
import org.apache.jena.sparql.engine.http.QueryExceptionHTTP;
import org.apache.jena.tdb.TDBFactory;
@@ -62,14 +63,17 @@ public class TestSecurityFilterFuseki {
@Parameters(name = "{index}: {0}")
public static Iterable<Object[]> data() {
- Object[] obj1 = { "TDB", "data1" };
+ Object[] obj1 = { "TDB", "data1" };
Object[] obj2 = { "TDB2", "data2" };
- return Arrays.asList(obj1, obj2);
+ Object[] obj3 = { "TIM", "data3" };
+ return Arrays.asList(obj1, obj2, obj3);
}
private final String baseUrl;
private static DatasetGraph testdsg1 = TDBFactory.createDatasetGraph();
private static DatasetGraph testdsg2 = DatabaseMgr.createDatasetGraph();
+ private static DatasetGraph testdsg3 = DatasetGraphFactory.createTxnMem();
+
private static FusekiServer fusekiServer;
// Set up Fuseki with two datasets, "data1" backed by TDB and "data2" backed by TDB2.
@@ -77,6 +81,7 @@ public class TestSecurityFilterFuseki {
int port = FusekiLib.choosePort();
addTestData(testdsg1);
addTestData(testdsg2);
+ addTestData(testdsg3);
SecurityRegistry reg = new SecurityRegistry();
reg.put("userNone", SecurityPolicy.NONE);
@@ -85,10 +90,10 @@ public class TestSecurityFilterFuseki {
reg.put("user1", new SecurityPolicy("http://test/g1", Quad.defaultGraphIRI.getURI()));
reg.put("user2", new SecurityPolicy("http://test/g1", "http://test/g2", "http://test/g3"));
- // XXX Also need wrapped tests
- testdsg1 = DataAccessCtl.wrapControlledDataset(testdsg1, reg);
- testdsg2 = DataAccessCtl.wrapControlledDataset(testdsg2, reg);
-
+ testdsg1 = DataAccessCtl.controlledDataset(testdsg1, reg);
+ testdsg2 = DataAccessCtl.controlledDataset(testdsg2, reg);
+ testdsg3 = DataAccessCtl.controlledDataset(testdsg3, reg);
+
UserStore userStore = userStore();
SecurityHandler sh = JettyLib.makeSecurityHandler("/*", "DatasetRealm", userStore);
@@ -96,6 +101,7 @@ public class TestSecurityFilterFuseki {
.port(port)
.add("data1", testdsg1)
.add("data2", testdsg2)
+ .add("data3", testdsg3)
.build();
fusekiServer.start();
}
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterLocal.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterLocal.java b/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterLocal.java
index 0268b5b..1e03aba 100644
--- a/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterLocal.java
+++ b/jena-fuseki2/jena-fuseki-access/src/test/java/org/apache/jena/fuseki/access/TestSecurityFilterLocal.java
@@ -48,8 +48,10 @@ import org.apache.jena.sparql.core.DatasetGraph;
import org.apache.jena.sparql.core.DatasetGraphFactory;
import org.apache.jena.sparql.core.Quad;
import org.apache.jena.system.Txn;
+import org.apache.jena.tdb.TDB;
import org.apache.jena.tdb.TDBFactory;
import org.apache.jena.tdb2.DatabaseMgr;
+import org.apache.jena.tdb2.TDB2;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
@@ -86,7 +88,7 @@ public class TestSecurityFilterLocal {
private final DatasetGraph testdsg;
private SecurityRegistry reg = new SecurityRegistry();
private final boolean applyFilterDSG;
- private final boolean applyFilterQExec;
+ private final boolean applyFilterTDB;
public TestSecurityFilterLocal(String name, Creator<DatasetGraph> source, boolean applyFilterTDB) {
DatasetGraph dsgBase = source.create();
@@ -96,9 +98,9 @@ public class TestSecurityFilterLocal {
reg.put("user0", new SecurityPolicy(Quad.defaultGraphIRI.getURI()));
reg.put("user1", new SecurityPolicy("http://test/g1", Quad.defaultGraphIRI.getURI()));
reg.put("user2", new SecurityPolicy("http://test/g1", "http://test/g2", "http://test/g3"));
- testdsg = DataAccessCtl.wrapControlledDataset(dsgBase, reg);
+ testdsg = DataAccessCtl.controlledDataset(dsgBase, reg);
+ this.applyFilterTDB = applyFilterTDB;
this.applyFilterDSG = ! applyFilterTDB;
- this.applyFilterQExec = applyFilterTDB;
}
private static void assertSeen(Set<Node> visible, Node ... expected) {
@@ -121,7 +123,7 @@ public class TestSecurityFilterLocal {
return
Txn.calculateRead(ds, ()->{
try(QueryExecution qExec = QueryExecutionFactory.create(queryString, ds)) {
- if ( applyFilterQExec )
+ if ( applyFilterTDB )
sCxt.filterTDB(dsg1, qExec);
List<QuerySolution> results = Iter.toList(qExec.execSelect());
Stream<Node> stream = results.stream()
@@ -142,7 +144,7 @@ public class TestSecurityFilterLocal {
return
Txn.calculateRead(testdsg, ()->{
try(QueryExecution qExec = QueryExecutionFactory.create(queryString, model)) {
- if ( applyFilterQExec )
+ if ( applyFilterTDB )
sCxt.filterTDB(dsg1, qExec);
List<QuerySolution> results = Iter.toList(qExec.execSelect());
Stream<Node> stream = results.stream().map(qs->qs.get("s")).filter(Objects::nonNull).map(RDFNode::asNode);
@@ -159,7 +161,7 @@ public class TestSecurityFilterLocal {
return
Txn.calculateRead(ds, ()->{
try(QueryExecution qExec = QueryExecutionFactory.create(queryGraphNames, ds)) {
- if ( applyFilterQExec )
+ if ( applyFilterTDB )
sCxt.filterTDB(dsg1, qExec);
List<QuerySolution> results = Iter.toList(qExec.execSelect());
Stream<Node> stream = results.stream().map(qs->qs.get("g")).filter(Objects::nonNull).map(RDFNode::asNode);
@@ -251,15 +253,21 @@ public class TestSecurityFilterLocal {
// QueryExecution w/ Union default graph
private void filter_union_user(String user, Node ... expected) {
SecurityPolicy sCxt = reg.get(user);
- // XXX Need to set union.
-// Consumer<QueryExecution> modifier = qExec-> {
-// qExec.getContext().set(TDB.symUnionDefaultGraph, true);
-// qExec.getContext().set(TDB2.symUnionDefaultGraph, true);
-// sCxt.filterTDB(testdsg, qExec);
-// };
-// Set<Node> visible = subjects(testdsg, queryDft, sCxt);
-
- Set<Node> visible = subjects(testdsg, dsg->dsg.getUnionGraph(), queryDft, sCxt);
+ Set<Node> visible;
+ if ( applyFilterTDB ) {
+ // TDB special version. Set the TDB flags for union default graph
+ try {
+ testdsg.getContext().set(TDB.symUnionDefaultGraph, true);
+ testdsg.getContext().set(TDB2.symUnionDefaultGraph, true);
+ visible = subjects(testdsg, queryDft, sCxt);
+ } finally {
+ // And unset them.
+ testdsg.getContext().unset(TDB.symUnionDefaultGraph);
+ testdsg.getContext().unset(TDB2.symUnionDefaultGraph);
+ }
+ } else {
+ visible = subjects(testdsg, dsg->dsg.getUnionGraph(), queryDft, sCxt);
+ }
assertSeen(visible, expected);
}
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-basic/src/main/java/org/apache/jena/fuseki/cmds/FusekiBasicCmd.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-basic/src/main/java/org/apache/jena/fuseki/cmds/FusekiBasicCmd.java b/jena-fuseki2/jena-fuseki-basic/src/main/java/org/apache/jena/fuseki/cmds/FusekiBasicCmd.java
index baa3b28..f1ba1f2 100644
--- a/jena-fuseki2/jena-fuseki-basic/src/main/java/org/apache/jena/fuseki/cmds/FusekiBasicCmd.java
+++ b/jena-fuseki2/jena-fuseki-basic/src/main/java/org/apache/jena/fuseki/cmds/FusekiBasicCmd.java
@@ -510,10 +510,8 @@ public class FusekiBasicCmd {
}
if ( serverConfig.datasetPath != null ) {
- if ( mapDatasetEndpoints.size() != 1 ) {
- System.err.println(serverConfig.datasetPath);
+ if ( mapDatasetEndpoints.size() != 1 )
log.error("Expected only one dataset");
- }
List<String> endpoints = mapDatasetEndpoints.get(serverConfig.datasetPath);
FmtLog.info(log, "Dataset Type = %s", serverConfig.datasetDescription);
FmtLog.info(log, "Path = %s; Services = %s", serverConfig.datasetPath, endpoints);
http://git-wip-us.apache.org/repos/asf/jena/blob/80a2f7b5/jena-fuseki2/jena-fuseki-core/src/main/java/org/apache/jena/fuseki/servlets/SPARQL_Query.java
----------------------------------------------------------------------
diff --git a/jena-fuseki2/jena-fuseki-core/src/main/java/org/apache/jena/fuseki/servlets/SPARQL_Query.java b/jena-fuseki2/jena-fuseki-core/src/main/java/org/apache/jena/fuseki/servlets/SPARQL_Query.java
index a14e75a..931f27f 100644
--- a/jena-fuseki2/jena-fuseki-core/src/main/java/org/apache/jena/fuseki/servlets/SPARQL_Query.java
+++ b/jena-fuseki2/jena-fuseki-core/src/main/java/org/apache/jena/fuseki/servlets/SPARQL_Query.java
@@ -108,9 +108,9 @@ public abstract class SPARQL_Query extends SPARQL_Protocol
if ( acceptedParams_ == null ) {
synchronized(this) {
if ( acceptedParams_ == null )
- // Does not matter about race condition here because the same Set should be
- // created on any call to generateAcceptedParams.
- acceptedParams_ = generateAcceptedParams();
+ // Does not matter about race condition here because the same Set should be
+ // created on any call to generateAcceptedParams.
+ acceptedParams_ = generateAcceptedParams();
}
}
return acceptedParams_;