summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNicholas Car <nicholas.car@csiro.au>2020-03-13 21:51:03 +1000
committerNicholas Car <nicholas.car@csiro.au>2020-03-13 21:51:03 +1000
commit0b39e5efc4b6a1eab886b8adf522870c3532e86b (patch)
tree3144110b3e916bfde836a836f72a9e4a8d65d0f0
parenta7863d25dc47730f4ef8bdca91c4e35c7f7b1ccf (diff)
downloadrdflib-0b39e5efc4b6a1eab886b8adf522870c3532e86b.tar.gz
adds capability to include reified triples in cdb() extraction, as per spec, and tests for it
-rw-r--r--rdflib/graph.py11
-rw-r--r--test/test_graph_cbd.py99
2 files changed, 91 insertions, 19 deletions
diff --git a/rdflib/graph.py b/rdflib/graph.py
index eb0a556e..f68300cb 100644
--- a/rdflib/graph.py
+++ b/rdflib/graph.py
@@ -1303,6 +1303,17 @@ class Graph(Node):
# recurse 'down' through ll Blank Nodes
if type(o) == BNode and not (o, None, None) in subgraph:
add_to_cbd(o)
+
+ # for Rule 3 (reification)
+ # for any rdf:Statement in the graph with the given URI as the object of rdf:subject,
+ # get all triples with that rdf:Statement instance as subject
+
+ # find any subject s where the predicate is rdf:subject and this uri is the object
+ # (these subjects are of type rdf:Statement, given the domain of rdf:subject)
+ for s, p, o in self.triples((None, RDF.subject, uri)):
+ # find all triples with s as the subject and add these to the subgraph
+ for s2, p2, o2 in self.triples((s, None, None)):
+ subgraph.add((s2, p2, o2))
add_to_cbd(resource)
return subgraph
diff --git a/test/test_graph_cbd.py b/test/test_graph_cbd.py
index 88adf8be..aedc9dd0 100644
--- a/test/test_graph_cbd.py
+++ b/test/test_graph_cbd.py
@@ -9,29 +9,30 @@ class CbdTestCase(unittest.TestCase):
self.g = Graph()
# adding example data for testing
self.g.parse(
- data="""PREFIX ex: <http://ex/>
- PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
-
- ex:R1
+ data="""
+ PREFIX ex: <http://ex/>
+ PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
+
+ ex:R1
a rdf:Resource ;
ex:hasChild ex:R2 , ex:R3 .
-
- ex:R2
+
+ ex:R2
ex:propOne ex:P1 ;
ex:propTwo ex:P2 .
-
- ex:R3
- ex:propOne ex:P3 ;
- ex:propTwo ex:P4 ;
- ex:propThree [
- a rdf:Resource ;
- ex:propFour "Some Literal" ;
- ex:propFive ex:P5 ;
- ex:propSix [
- ex:propSeven ex:P7 ;
- ] ;
- ] .
- """,
+
+ ex:R3
+ ex:propOne ex:P3 ;
+ ex:propTwo ex:P4 ;
+ ex:propThree [
+ a rdf:Resource ;
+ ex:propFour "Some Literal" ;
+ ex:propFive ex:P5 ;
+ ex:propSix [
+ ex:propSeven ex:P7 ;
+ ] ;
+ ] .
+ """,
format="turtle",
)
@@ -55,6 +56,66 @@ class CbdTestCase(unittest.TestCase):
len(self.g.cbd(self.EX.R4)), 0, "cbd() for R4 should return 0 triples"
)
+ def testCbdReified(self):
+ # add some reified triples to the testing graph
+ self.g.parse(
+ data="""
+ PREFIX ex: <http://ex/>
+ PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
+
+ ex:R5
+ ex:propOne ex:P1 ;
+ ex:propTwo ex:P2 ;
+ ex:propRei ex:Pre1 .
+
+ ex:S
+ a rdf:Statement ;
+ rdf:subject ex:R5 ;
+ rdf:predicate ex:propRei ;
+ rdf:object ex:Pre1 ;
+ ex:otherReiProp ex:Pre2 .
+ """,
+ format="turtle",
+ )
+
+ # this cbd() call should get the 3 basic triples with ex:R5 as subject as well as 5 more from the reified
+ # statement
+ self.assertEqual(
+ len(self.g.cbd(self.EX.R5)), (3 + 5), "cbd() for R5 should return 8 triples"
+ )
+
+ # add crazy reified triples to the testing graph
+ self.g.parse(
+ data="""
+ PREFIX ex: <http://ex/>
+ PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
+
+ ex:R6
+ ex:propOne ex:P1 ;
+ ex:propTwo ex:P2 ;
+ ex:propRei ex:Pre1 .
+
+ ex:S1
+ a rdf:Statement ;
+ rdf:subject ex:R6 ;
+ rdf:predicate ex:propRei ;
+ rdf:object ex:Pre1 ;
+ ex:otherReiProp ex:Pre3 .
+
+ ex:S2
+ rdf:subject ex:R6 ;
+ rdf:predicate ex:propRei2 ;
+ rdf:object ex:Pre2 ;
+ ex:otherReiProp ex:Pre4 ;
+ ex:otherReiProp ex:Pre5 .
+ """,
+ format="turtle",
+ )
+
+ self.assertEqual(
+ len(self.g.cbd(self.EX.R6)), (3 + 5 + 5), "cbd() for R6 should return 12 triples"
+ )
+
def tearDown(self):
self.g.close()