Skip to content

Commit

Permalink
Use the property built-in as a decorator
Browse files Browse the repository at this point in the history
The use of the `property` built-in as a function does not allow for
the same type annotations as using `property` as a deocorator.

This change should not affect runtime behaviour and there is test
coverage for all properties that were changed to decorators.

There are still other places where `property` is used as a function but
this is outside of the core parts of RDFLib.
  • Loading branch information
aucampia committed Feb 1, 2022
1 parent b2cae90 commit 0d2c762
Show file tree
Hide file tree
Showing 7 changed files with 165 additions and 24 deletions.
25 changes: 11 additions & 14 deletions rdflib/graph.py
Original file line number Diff line number Diff line change
Expand Up @@ -350,30 +350,27 @@ def __init__(
self.formula_aware = False
self.default_union = False

def __get_store(self):
@property
def store(self):
return self.__store

store = property(__get_store) # read-only attr

def __get_identifier(self):
@property
def identifier(self):
return self.__identifier

identifier = property(__get_identifier) # read-only attr

def _get_namespace_manager(self):
@property
def namespace_manager(self):
"""
this graph's namespace-manager
"""
if self.__namespace_manager is None:
self.__namespace_manager = NamespaceManager(self)
return self.__namespace_manager

def _set_namespace_manager(self, nm):
@namespace_manager.setter
def namespace_manager(self, nm):
self.__namespace_manager = nm

namespace_manager = property(
_get_namespace_manager,
_set_namespace_manager,
doc="this graph's namespace-manager",
)

def __repr__(self):
return "<Graph identifier=%s (%s)>" % (self.identifier, type(self))

Expand Down
13 changes: 7 additions & 6 deletions rdflib/query.py
Original file line number Diff line number Diff line change
Expand Up @@ -177,24 +177,25 @@ def __init__(self, type_: str):
self.askAnswer: bool = None # type: ignore[assignment]
self.graph: "Graph" = None # type: ignore[assignment]

def _get_bindings(self):
@property
def bindings(self):
"""
a list of variable bindings as dicts
"""
if self._genbindings:
self._bindings += list(self._genbindings)
self._genbindings = None

return self._bindings

def _set_bindings(self, b):
@bindings.setter
def bindings(self, b):
if isinstance(b, (types.GeneratorType, itertools.islice)):
self._genbindings = b
self._bindings = []
else:
self._bindings = b

bindings = property(
_get_bindings, _set_bindings, doc="a list of variable bindings as dicts"
)

@staticmethod
def parse(
source=None,
Expand Down
8 changes: 6 additions & 2 deletions rdflib/resource.py
Original file line number Diff line number Diff line change
Expand Up @@ -298,9 +298,13 @@ def __init__(self, graph, subject):
self._graph = graph
self._identifier = subject

graph = property(lambda self: self._graph)
@property
def graph(self):
return self._graph

identifier = property(lambda self: self._identifier)
@property
def identifier(self):
return self._identifier

def __hash__(self):
return hash(Resource) ^ hash(self._graph) ^ hash(self._identifier)
Expand Down
4 changes: 2 additions & 2 deletions rdflib/store.py
Original file line number Diff line number Diff line change
Expand Up @@ -151,7 +151,8 @@ def __init__(self, configuration=None, identifier=None):
if configuration:
self.open(configuration)

def __get_node_pickler(self):
@property
def node_pickler(self):
if self.__node_pickler is None:
from rdflib.term import URIRef
from rdflib.term import BNode
Expand All @@ -169,7 +170,6 @@ def __get_node_pickler(self):
np.register(Variable, "V")
return self.__node_pickler

node_pickler = property(__get_node_pickler)

# Database management methods
def create(self, configuration):
Expand Down
9 changes: 9 additions & 0 deletions test/consistent_test_data/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
# Consistent Test Data

This directory contains consistent graphs that can be used inside tests, the
graphs in this directory should not change.


## File origins

- `rdfs.ttl`: `http://www.w3.org/2000/01/rdf-schema#`
109 changes: 109 additions & 0 deletions test/consistent_test_data/rdfs.ttl
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@prefix owl: <http://www.w3.org/2002/07/owl#> .
@prefix dc: <http://purl.org/dc/elements/1.1/> .

<http://www.w3.org/2000/01/rdf-schema#> a owl:Ontology ;
dc:title "The RDF Schema vocabulary (RDFS)" .

rdfs:Resource a rdfs:Class ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "Resource" ;
rdfs:comment "The class resource, everything." .

rdfs:Class a rdfs:Class ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "Class" ;
rdfs:comment "The class of classes." ;
rdfs:subClassOf rdfs:Resource .

rdfs:subClassOf a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "subClassOf" ;
rdfs:comment "The subject is a subclass of a class." ;
rdfs:range rdfs:Class ;
rdfs:domain rdfs:Class .

rdfs:subPropertyOf a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "subPropertyOf" ;
rdfs:comment "The subject is a subproperty of a property." ;
rdfs:range rdf:Property ;
rdfs:domain rdf:Property .

rdfs:comment a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "comment" ;
rdfs:comment "A description of the subject resource." ;
rdfs:domain rdfs:Resource ;
rdfs:range rdfs:Literal .

rdfs:label a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "label" ;
rdfs:comment "A human-readable name for the subject." ;
rdfs:domain rdfs:Resource ;
rdfs:range rdfs:Literal .

rdfs:domain a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "domain" ;
rdfs:comment "A domain of the subject property." ;
rdfs:range rdfs:Class ;
rdfs:domain rdf:Property .

rdfs:range a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "range" ;
rdfs:comment "A range of the subject property." ;
rdfs:range rdfs:Class ;
rdfs:domain rdf:Property .

rdfs:seeAlso a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "seeAlso" ;
rdfs:comment "Further information about the subject resource." ;
rdfs:range rdfs:Resource ;
rdfs:domain rdfs:Resource .

rdfs:isDefinedBy a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:subPropertyOf rdfs:seeAlso ;
rdfs:label "isDefinedBy" ;
rdfs:comment "The defininition of the subject resource." ;
rdfs:range rdfs:Resource ;
rdfs:domain rdfs:Resource .

rdfs:Literal a rdfs:Class ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "Literal" ;
rdfs:comment "The class of literal values, eg. textual strings and integers." ;
rdfs:subClassOf rdfs:Resource .

rdfs:Container a rdfs:Class ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "Container" ;
rdfs:subClassOf rdfs:Resource ;
rdfs:comment "The class of RDF containers." .

rdfs:ContainerMembershipProperty a rdfs:Class ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "ContainerMembershipProperty" ;
rdfs:comment """The class of container membership properties, rdf:_1, rdf:_2, ...,
all of which are sub-properties of 'member'.""" ;
rdfs:subClassOf rdf:Property .

rdfs:member a rdf:Property ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "member" ;
rdfs:comment "A member of the subject resource." ;
rdfs:domain rdfs:Resource ;
rdfs:range rdfs:Resource .

rdfs:Datatype a rdfs:Class ;
rdfs:isDefinedBy <http://www.w3.org/2000/01/rdf-schema#> ;
rdfs:label "Datatype" ;
rdfs:comment "The class of RDF datatypes." ;
rdfs:subClassOf rdfs:Class .

<http://www.w3.org/2000/01/rdf-schema#> rdfs:seeAlso <http://www.w3.org/2000/01/rdf-schema-more> .
21 changes: 21 additions & 0 deletions test/test_resource.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import pytest
from rdflib import Graph
from rdflib.resource import Resource
from pathlib import Path
from rdflib.namespace import RDFS
import pytest

TEST_DIR = Path(__file__).parent


@pytest.fixture
def rdfs_graph() -> Graph:
return Graph().parse(
TEST_DIR / "consistent_test_data" / "rdfs.ttl", format="turtle"
)


def test_properties(rdfs_graph: Graph) -> None:
cres = Resource(rdfs_graph, RDFS.Container)
assert cres.graph is rdfs_graph
assert cres.identifier == RDFS.Container

0 comments on commit 0d2c762

Please sign in to comment.