oldaplib 0.3.4__py3-none-any.whl → 0.3.5__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- oldaplib/src/enums/attributeclass.py +31 -6
- oldaplib/src/enums/owlpropertytype.py +2 -2
- oldaplib/src/enums/propertyclassattr.py +23 -20
- oldaplib/src/propertyclass.py +50 -28
- oldaplib/src/version.py +1 -1
- oldaplib/src/xsd/xsd_qname.py +1 -1
- oldaplib/test/test_propertyclass.py +75 -0
- {oldaplib-0.3.4.dist-info → oldaplib-0.3.5.dist-info}/METADATA +3 -2
- {oldaplib-0.3.4.dist-info → oldaplib-0.3.5.dist-info}/RECORD +10 -10
- {oldaplib-0.3.4.dist-info → oldaplib-0.3.5.dist-info}/WHEEL +1 -1
|
@@ -1,8 +1,13 @@
|
|
|
1
|
-
from enum import Enum
|
|
2
|
-
from typing import Type, Self
|
|
1
|
+
from enum import Enum, Flag, auto
|
|
2
|
+
from typing import Type, Self, Any
|
|
3
3
|
|
|
4
4
|
from oldaplib.src.xsd.xsd_qname import Xsd_QName
|
|
5
5
|
|
|
6
|
+
class Target(Flag):
|
|
7
|
+
SHACL = auto()
|
|
8
|
+
OWL = auto()
|
|
9
|
+
BOTH = SHACL | OWL # convenience alias
|
|
10
|
+
|
|
6
11
|
|
|
7
12
|
class AttributeClass(Enum):
|
|
8
13
|
"""
|
|
@@ -10,7 +15,12 @@ class AttributeClass(Enum):
|
|
|
10
15
|
Project, PropertyClass, ResourceClass, User etc.,
|
|
11
16
|
"""
|
|
12
17
|
|
|
13
|
-
def __new__(cls,
|
|
18
|
+
def __new__(cls,
|
|
19
|
+
value: Xsd_QName | str,
|
|
20
|
+
mandatory: bool,
|
|
21
|
+
immutable: bool,
|
|
22
|
+
datatype: Type,
|
|
23
|
+
target: Target = Target.BOTH):
|
|
14
24
|
"""
|
|
15
25
|
:param value: The value of the attribute-enum item. Must have the form of a QName!
|
|
16
26
|
:param mandatory: True, if this attribute is mandatory, False otherwise.
|
|
@@ -23,6 +33,7 @@ class AttributeClass(Enum):
|
|
|
23
33
|
member._mandatory = mandatory
|
|
24
34
|
member._immutable = immutable
|
|
25
35
|
member._datatype = datatype
|
|
36
|
+
member._target = target
|
|
26
37
|
return member
|
|
27
38
|
|
|
28
39
|
def __str__(self) -> str:
|
|
@@ -48,6 +59,23 @@ class AttributeClass(Enum):
|
|
|
48
59
|
def immutable(self) -> bool:
|
|
49
60
|
return self._immutable
|
|
50
61
|
|
|
62
|
+
@property
|
|
63
|
+
def target(self) -> Target:
|
|
64
|
+
"""Where this attribute should be emitted/used (SHACL, OWL, BOTH)."""
|
|
65
|
+
return self._target
|
|
66
|
+
|
|
67
|
+
@property
|
|
68
|
+
def in_shacl(self) -> bool:
|
|
69
|
+
return bool(self._target & Target.SHACL)
|
|
70
|
+
|
|
71
|
+
@property
|
|
72
|
+
def in_owl(self) -> bool:
|
|
73
|
+
return bool(self._target & Target.OWL)
|
|
74
|
+
|
|
75
|
+
@property
|
|
76
|
+
def to_rdf(self) -> str:
|
|
77
|
+
return self._value.toRdf
|
|
78
|
+
|
|
51
79
|
@classmethod
|
|
52
80
|
def from_value(cls, value: Xsd_QName | str) -> Self:
|
|
53
81
|
"""
|
|
@@ -73,6 +101,3 @@ class AttributeClass(Enum):
|
|
|
73
101
|
return member
|
|
74
102
|
raise ValueError(f"No member with name {name} found")
|
|
75
103
|
|
|
76
|
-
@property
|
|
77
|
-
def to_rdf(self) -> str:
|
|
78
|
-
return self._value.toRdf
|
|
@@ -19,8 +19,8 @@ class OwlPropertyType(Enum):
|
|
|
19
19
|
IrreflexiveProperty = 'owl:IrreflexiveProperty'
|
|
20
20
|
FunctionalProperty = 'owl:FunctionalProperty'
|
|
21
21
|
InverseFunctionalProperty = 'owl:InverseFunctionalProperty'
|
|
22
|
-
# InverseOfProperty = 'owl:
|
|
23
|
-
# EquivalentProperty = 'owl:
|
|
22
|
+
# InverseOfProperty = 'owl:inverseOf'
|
|
23
|
+
# EquivalentProperty = 'owl:equivalentProperty'
|
|
24
24
|
# _owl_inverseOf: Xsd_QName # :hasParent owl:inverseOf :hasChild .
|
|
25
25
|
# _owl_equivalent: Xsd_QName # :hasSpouse owl:equivalentProperty :marriedTo .
|
|
26
26
|
|
|
@@ -3,7 +3,7 @@ from typing import Self
|
|
|
3
3
|
|
|
4
4
|
from oldaplib.src.dtypes.languagein import LanguageIn
|
|
5
5
|
from oldaplib.src.dtypes.xsdset import XsdSet
|
|
6
|
-
from oldaplib.src.enums.attributeclass import AttributeClass
|
|
6
|
+
from oldaplib.src.enums.attributeclass import AttributeClass, Target
|
|
7
7
|
from oldaplib.src.enums.xsd_datatypes import XsdDatatypes
|
|
8
8
|
from oldaplib.src.helpers.langstring import LangString
|
|
9
9
|
from oldaplib.src.helpers.numeric import Numeric
|
|
@@ -12,6 +12,7 @@ from oldaplib.src.helpers.observable_set import ObservableSet
|
|
|
12
12
|
from oldaplib.src.xsd.iri import Iri
|
|
13
13
|
from oldaplib.src.xsd.xsd_boolean import Xsd_boolean
|
|
14
14
|
from oldaplib.src.xsd.xsd_integer import Xsd_integer
|
|
15
|
+
from oldaplib.src.xsd.xsd_qname import Xsd_QName
|
|
15
16
|
from oldaplib.src.xsd.xsd_string import Xsd_string
|
|
16
17
|
|
|
17
18
|
|
|
@@ -35,26 +36,28 @@ class PropClassAttr(AttributeClass):
|
|
|
35
36
|
- `PropertyClassAttribute.DESCRIPTION`: Description of the property. The literal is a string that may
|
|
36
37
|
have attached a language id.
|
|
37
38
|
"""
|
|
38
|
-
# order: (QName, mandatory, immutable, datatype)
|
|
39
|
+
# order: (QName, mandatory, immutable, datatype, target)
|
|
39
40
|
SUBPROPERTY_OF = ('rdfs:subPropertyOf', False, False, Iri)
|
|
40
|
-
TYPE = ('rdf:type', False, False, ObservableSet)
|
|
41
|
-
CLASS = ('sh:class', False, False, Iri)
|
|
42
|
-
NODEKIND = ('sh:nodeKind', False, False, Iri)
|
|
43
|
-
DATATYPE = ('sh:datatype', False, False, XsdDatatypes)
|
|
44
|
-
NAME = ('sh:name', False, False, LangString) # needs notifier
|
|
45
|
-
DESCRIPTION = ('sh:description', False, False, LangString) # needs notifier
|
|
46
|
-
LANGUAGE_IN = ('sh:languageIn', False, False, LanguageIn) # needs notifier
|
|
47
|
-
UNIQUE_LANG = ('sh:uniqueLang', False, False, Xsd_boolean)
|
|
48
|
-
IN = ('sh:in', False, False, XsdSet) # needs notifier
|
|
49
|
-
MIN_LENGTH = ('sh:minLength', False, False, Xsd_integer)
|
|
50
|
-
MAX_LENGTH = ('sh:maxLength', False, False, Xsd_integer)
|
|
51
|
-
PATTERN = ('sh:pattern', False, False, Xsd_string)
|
|
52
|
-
MIN_EXCLUSIVE = ('sh:minExclusive', False, False, Numeric)
|
|
53
|
-
MIN_INCLUSIVE = ('sh:minInclusive', False, False, Numeric)
|
|
54
|
-
MAX_EXCLUSIVE = ('sh:maxExclusive', False, False, Numeric)
|
|
55
|
-
MAX_INCLUSIVE = ('sh:maxInclusive', False, False, Numeric)
|
|
56
|
-
LESS_THAN = ('sh:lessThan', False, False, Iri)
|
|
57
|
-
LESS_THAN_OR_EQUALS = ('sh:lessThanOrEquals', False, False, Iri)
|
|
41
|
+
TYPE = ('rdf:type', False, False, ObservableSet, Target.OWL)
|
|
42
|
+
CLASS = ('sh:class', False, False, Iri, Target.SHACL)
|
|
43
|
+
NODEKIND = ('sh:nodeKind', False, False, Iri, Target.SHACL)
|
|
44
|
+
DATATYPE = ('sh:datatype', False, False, XsdDatatypes, Target.SHACL)
|
|
45
|
+
NAME = ('sh:name', False, False, LangString, Target.SHACL) # needs notifier
|
|
46
|
+
DESCRIPTION = ('sh:description', False, False, LangString, Target.SHACL) # needs notifier
|
|
47
|
+
LANGUAGE_IN = ('sh:languageIn', False, False, LanguageIn, Target.SHACL) # needs notifier
|
|
48
|
+
UNIQUE_LANG = ('sh:uniqueLang', False, False, Xsd_boolean, Target.SHACL)
|
|
49
|
+
IN = ('sh:in', False, False, XsdSet, Target.SHACL) # needs notifier
|
|
50
|
+
MIN_LENGTH = ('sh:minLength', False, False, Xsd_integer, Target.SHACL)
|
|
51
|
+
MAX_LENGTH = ('sh:maxLength', False, False, Xsd_integer, Target.SHACL)
|
|
52
|
+
PATTERN = ('sh:pattern', False, False, Xsd_string, Target.SHACL)
|
|
53
|
+
MIN_EXCLUSIVE = ('sh:minExclusive', False, False, Numeric, Target.SHACL)
|
|
54
|
+
MIN_INCLUSIVE = ('sh:minInclusive', False, False, Numeric, Target.SHACL)
|
|
55
|
+
MAX_EXCLUSIVE = ('sh:maxExclusive', False, False, Numeric, Target.SHACL)
|
|
56
|
+
MAX_INCLUSIVE = ('sh:maxInclusive', False, False, Numeric, Target.SHACL)
|
|
57
|
+
LESS_THAN = ('sh:lessThan', False, False, Iri, Target.SHACL)
|
|
58
|
+
LESS_THAN_OR_EQUALS = ('sh:lessThanOrEquals', False, False, Iri, Target.SHACL)
|
|
59
|
+
INVERSE_OF = ('owl:inverseOf', False, False, Xsd_QName, Target.OWL)
|
|
60
|
+
EQUIVALEND_PROPERTY = ('owl:equivalentProperty', False, False, Xsd_QName, Target.OWL)
|
|
58
61
|
|
|
59
62
|
|
|
60
63
|
@classmethod
|
oldaplib/src/propertyclass.py
CHANGED
|
@@ -823,6 +823,8 @@ class PropertyClass(Model, Notify):
|
|
|
823
823
|
group = val
|
|
824
824
|
elif key in propkeys:
|
|
825
825
|
attr = PropClassAttr.from_value(key)
|
|
826
|
+
if not attr.in_shacl:
|
|
827
|
+
continue
|
|
826
828
|
if attr.datatype == Numeric:
|
|
827
829
|
if not isinstance(val, (Xsd_integer, Xsd_float)):
|
|
828
830
|
raise OldapErrorInconsistency(f'SHACL inconsistency: "{attr.value}" expects a "Xsd:integer" or "Xsd:float", but got "{type(val).__name__}".')
|
|
@@ -858,6 +860,7 @@ class PropertyClass(Model, Notify):
|
|
|
858
860
|
def read_owl(self) -> None:
|
|
859
861
|
if self._externalOntology:
|
|
860
862
|
return
|
|
863
|
+
propkeys = {Xsd_QName(x.value) for x in PropClassAttr}
|
|
861
864
|
context = Context(name=self._con.context_name)
|
|
862
865
|
query1 = context.sparql_context
|
|
863
866
|
query1 += f"""
|
|
@@ -878,24 +881,12 @@ class PropertyClass(Model, Notify):
|
|
|
878
881
|
obj = r['o']
|
|
879
882
|
match attr:
|
|
880
883
|
case 'rdf:type':
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
elif obj == 'owl:TransitiveProperty':
|
|
888
|
-
self._attributes[PropClassAttr.TYPE].add(OwlPropertyType.TransitiveProperty)
|
|
889
|
-
elif obj == 'owl:SymmetricProperty':
|
|
890
|
-
self._attributes[PropClassAttr.TYPE].add(OwlPropertyType.SymmetricProperty)
|
|
891
|
-
elif obj == 'owl:ReflexiveProperty':
|
|
892
|
-
self._attributes[PropClassAttr.TYPE].add(OwlPropertyType.ReflexiveProperty)
|
|
893
|
-
elif obj == 'owl:IrreflexiveProperty':
|
|
894
|
-
self._attributes[PropClassAttr.TYPE].add(OwlPropertyType.IrreflexiveProperty)
|
|
895
|
-
elif obj == 'owl:InverseFunctionalProperty':
|
|
896
|
-
self._attributes[PropClassAttr.TYPE].add(OwlPropertyType.InverseFunctionalProperty)
|
|
897
|
-
else:
|
|
898
|
-
raise OldapErrorNotFound(f'Unknown owl:Property type "{obj}"')
|
|
884
|
+
try:
|
|
885
|
+
# If obj is already a member, keep it; otherwise look it up by value
|
|
886
|
+
prop_type = obj if isinstance(obj, OwlPropertyType) else OwlPropertyType(obj)
|
|
887
|
+
except ValueError as e:
|
|
888
|
+
raise OldapErrorNotFound(f'Unknown owl:Property type "{obj}"') from e
|
|
889
|
+
self._attributes[PropClassAttr.TYPE].add(prop_type)
|
|
899
890
|
case 'owl:subPropertyOf':
|
|
900
891
|
self._attributes[PropClassAttr.SUBPROPERTY_OF] = obj
|
|
901
892
|
case 'rdfs:range':
|
|
@@ -919,6 +910,11 @@ class PropertyClass(Model, Notify):
|
|
|
919
910
|
dt = obj
|
|
920
911
|
if self._modified != dt:
|
|
921
912
|
raise OldapError(f'Inconsistency between SHACL and OWL: created "{self._modified}" vs "{dt}" for property "{self._property_class_iri}".')
|
|
913
|
+
case _:
|
|
914
|
+
if attr in propkeys:
|
|
915
|
+
pcattr = PropClassAttr.from_value(attr)
|
|
916
|
+
if pcattr.in_owl:
|
|
917
|
+
self._attributes[pcattr] = pcattr.datatype(obj)
|
|
922
918
|
#
|
|
923
919
|
# Consistency checks
|
|
924
920
|
#
|
|
@@ -1052,7 +1048,7 @@ class PropertyClass(Model, Notify):
|
|
|
1052
1048
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}oldap:statementProperty {self._statementProperty.toRdf}'
|
|
1053
1049
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}oldap:externalOntology {self._externalOntology.toRdf}'
|
|
1054
1050
|
for prop, value in self._attributes.items():
|
|
1055
|
-
if prop
|
|
1051
|
+
if not prop.in_shacl:
|
|
1056
1052
|
continue
|
|
1057
1053
|
if not value and not isinstance(value, bool):
|
|
1058
1054
|
#if value is None:
|
|
@@ -1085,24 +1081,47 @@ class PropertyClass(Model, Notify):
|
|
|
1085
1081
|
|
|
1086
1082
|
def create_owl_part1(self, timestamp: Xsd_dateTime, indent: int = 0, indent_inc: int = 4) -> str:
|
|
1087
1083
|
blank = ''
|
|
1088
|
-
sparql = f'{blank:{indent * indent_inc}}{self._property_class_iri.toRdf}
|
|
1089
|
-
if self._attributes.get(PropClassAttr.SUBPROPERTY_OF):
|
|
1090
|
-
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:subPropertyOf {self._attributes[PropClassAttr.SUBPROPERTY_OF].toRdf}'
|
|
1084
|
+
sparql = f'{blank:{indent * indent_inc}}{self._property_class_iri.toRdf} {PropClassAttr.TYPE.toRdf} {self._attributes[PropClassAttr.TYPE].toRdf}'
|
|
1091
1085
|
if self._internal:
|
|
1092
1086
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:domain {self._internal.toRdf}'
|
|
1093
1087
|
if self._attributes.get(PropClassAttr.TYPE) and OwlPropertyType.OwlDataProperty in self._attributes[PropClassAttr.TYPE]:
|
|
1094
1088
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:range {self._attributes[PropClassAttr.DATATYPE].value}'
|
|
1095
1089
|
elif self._attributes.get(PropClassAttr.TYPE) and OwlPropertyType.OwlObjectProperty in self._attributes[PropClassAttr.TYPE]:
|
|
1096
1090
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:range {self._attributes[PropClassAttr.CLASS].toRdf}'
|
|
1091
|
+
for attr, val in self._attributes.items():
|
|
1092
|
+
#attr = PropClassAttr.from_value(key)
|
|
1093
|
+
if not attr.in_owl or attr == PropClassAttr.TYPE or val is None:
|
|
1094
|
+
continue
|
|
1095
|
+
if attr == PropClassAttr.NAME:
|
|
1096
|
+
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:label {val.toRdf}'
|
|
1097
|
+
elif attr == PropClassAttr.DESCRIPTION:
|
|
1098
|
+
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:comment {val.toRdf}'
|
|
1099
|
+
else:
|
|
1100
|
+
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}{attr.toRdf} {val.toRdf}'
|
|
1097
1101
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:creator {self._con.userIri.toRdf}'
|
|
1098
1102
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:created {timestamp.toRdf}'
|
|
1099
1103
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:contributor {self._con.userIri.toRdf}'
|
|
1100
1104
|
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:modified {timestamp.toRdf}'
|
|
1101
|
-
if self.name:
|
|
1102
|
-
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:label {self.name.toRdf}'
|
|
1103
|
-
if self.description:
|
|
1104
|
-
sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:comment {self.description.toRdf}'
|
|
1105
1105
|
sparql += ' .\n'
|
|
1106
|
+
|
|
1107
|
+
# sparql = f'{blank:{indent * indent_inc}}{self._property_class_iri.toRdf} rdf:type {self._attributes[PropClassAttr.TYPE].toRdf}'
|
|
1108
|
+
# if self._attributes.get(PropClassAttr.SUBPROPERTY_OF):
|
|
1109
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:subPropertyOf {self._attributes[PropClassAttr.SUBPROPERTY_OF].toRdf}'
|
|
1110
|
+
# if self._internal:
|
|
1111
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:domain {self._internal.toRdf}'
|
|
1112
|
+
# if self._attributes.get(PropClassAttr.TYPE) and OwlPropertyType.OwlDataProperty in self._attributes[PropClassAttr.TYPE]:
|
|
1113
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:range {self._attributes[PropClassAttr.DATATYPE].value}'
|
|
1114
|
+
# elif self._attributes.get(PropClassAttr.TYPE) and OwlPropertyType.OwlObjectProperty in self._attributes[PropClassAttr.TYPE]:
|
|
1115
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:range {self._attributes[PropClassAttr.CLASS].toRdf}'
|
|
1116
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:creator {self._con.userIri.toRdf}'
|
|
1117
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:created {timestamp.toRdf}'
|
|
1118
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:contributor {self._con.userIri.toRdf}'
|
|
1119
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}dcterms:modified {timestamp.toRdf}'
|
|
1120
|
+
# if self.name:
|
|
1121
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:label {self.name.toRdf}'
|
|
1122
|
+
# if self.description:
|
|
1123
|
+
# sparql += f' ;\n{blank:{(indent + 1) * indent_inc}}rdfs:comment {self.description.toRdf}'
|
|
1124
|
+
# sparql += ' .\n'
|
|
1106
1125
|
return sparql
|
|
1107
1126
|
|
|
1108
1127
|
def create_owl_part2(self, *,
|
|
@@ -1218,6 +1237,7 @@ class PropertyClass(Model, Notify):
|
|
|
1218
1237
|
try:
|
|
1219
1238
|
self._con.transaction_update(sparql)
|
|
1220
1239
|
except OldapError as err:
|
|
1240
|
+
print(sparql)
|
|
1221
1241
|
self._con.transaction_abort()
|
|
1222
1242
|
raise
|
|
1223
1243
|
if not self._externalOntology: # it's a project specific property -> OWL has been written -> check consistency!
|
|
@@ -1362,12 +1382,14 @@ class PropertyClass(Model, Notify):
|
|
|
1362
1382
|
owlclass_iri: Xsd_QName | None = None,
|
|
1363
1383
|
timestamp: Xsd_dateTime,
|
|
1364
1384
|
indent: int = 0, indent_inc: int = 4) -> str:
|
|
1385
|
+
tmp = {x for x in PropClassAttr if x.in_owl and x != PropClassAttr.TYPE}
|
|
1365
1386
|
owl_propclass_attributes = {PropClassAttr.SUBPROPERTY_OF, # should be in OWL ontology
|
|
1366
1387
|
PropClassAttr.DATATYPE, # used for rdfs:range in OWL ontology
|
|
1367
|
-
PropClassAttr.CLASS}
|
|
1388
|
+
PropClassAttr.CLASS} | tmp # used for rdfs:range in OWL ontology
|
|
1389
|
+
tmp = {x: x.value.toRdf for x in PropClassAttr if x.in_owl and x != PropClassAttr.TYPE}
|
|
1368
1390
|
owl_prop = {PropClassAttr.SUBPROPERTY_OF: PropClassAttr.SUBPROPERTY_OF.value,
|
|
1369
1391
|
PropClassAttr.DATATYPE: "rdfs:range",
|
|
1370
|
-
PropClassAttr.CLASS: "rdfs:range"}
|
|
1392
|
+
PropClassAttr.CLASS: "rdfs:range"} | tmp
|
|
1371
1393
|
blank = ''
|
|
1372
1394
|
sparql_list = []
|
|
1373
1395
|
for prop, change in self._changeset.items():
|
oldaplib/src/version.py
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
__version__ = "0.3.
|
|
1
|
+
__version__ = "0.3.5"
|
oldaplib/src/xsd/xsd_qname.py
CHANGED
|
@@ -55,7 +55,7 @@ class Xsd_QName(Xsd):
|
|
|
55
55
|
raise OldapErrorValue(f'Invalid string "{value}" for QName. Error: {err}')
|
|
56
56
|
self._value = f'{prefix}:{fragment}'
|
|
57
57
|
else:
|
|
58
|
-
raise OldapErrorValue(f'Invalid value for QName "{value}"')
|
|
58
|
+
raise OldapErrorValue(f'Invalid value for QName "{value}" (type: {type(value).__name__})')
|
|
59
59
|
else:
|
|
60
60
|
prefix = Xsd_NCName(value, validate=validate)
|
|
61
61
|
if fragment:
|
|
@@ -110,6 +110,22 @@ class TestPropertyClass(unittest.TestCase):
|
|
|
110
110
|
self.assertEqual(p.get(PropClassAttr.DESCRIPTION), LangString("A property for testing...@en", "Property für Tests@de"))
|
|
111
111
|
self.assertEqual(p[PropClassAttr.TYPE], {OwlPropertyType.StatementProperty, OwlPropertyType.OwlDataProperty})
|
|
112
112
|
|
|
113
|
+
def test_propertyclass_constructor_owlprop(self):
|
|
114
|
+
p = PropertyClass(con=self._connection,
|
|
115
|
+
project=self._project,
|
|
116
|
+
property_class_iri=Xsd_QName('test:isParent'),
|
|
117
|
+
toClass=Iri('test:Human'),
|
|
118
|
+
name=LangString(["Parent"]),
|
|
119
|
+
description={"Parent of the human"})
|
|
120
|
+
i = PropertyClass(con=self._connection,
|
|
121
|
+
project=self._project,
|
|
122
|
+
property_class_iri=Xsd_QName('test:isChild'),
|
|
123
|
+
toClass=Iri('test:Human'),
|
|
124
|
+
inverseOf=Xsd_QName('test:isParent'),
|
|
125
|
+
name=LangString(["Child"]),
|
|
126
|
+
description={"Child of the human"})
|
|
127
|
+
self.assertEqual(i.inverseOf, Xsd_QName('test:isParent'))
|
|
128
|
+
|
|
113
129
|
def test_propertyclass_inset_datatypes(self):
|
|
114
130
|
p = PropertyClass(con=self._connection,
|
|
115
131
|
project=self._project,
|
|
@@ -416,6 +432,30 @@ class TestPropertyClass(unittest.TestCase):
|
|
|
416
432
|
ignore_cache=True)
|
|
417
433
|
self.assertEqual(p4.get(PropClassAttr.TYPE), {OwlPropertyType.SymmetricProperty, OwlPropertyType.OwlDataProperty})
|
|
418
434
|
|
|
435
|
+
def test_propertyclass_create_G(self):
|
|
436
|
+
p = PropertyClass(con=self._connection,
|
|
437
|
+
project=self._project,
|
|
438
|
+
property_class_iri=Xsd_QName('test:isParentG'),
|
|
439
|
+
toClass=Iri('test:Human'),
|
|
440
|
+
name=LangString(["Parent"]),
|
|
441
|
+
description={"Parent of the human"})
|
|
442
|
+
p.create()
|
|
443
|
+
i = PropertyClass(con=self._connection,
|
|
444
|
+
project=self._project,
|
|
445
|
+
property_class_iri=Xsd_QName('test:isChildG'),
|
|
446
|
+
toClass=Iri('test:Human'),
|
|
447
|
+
inverseOf=Xsd_QName('test:isParentG'),
|
|
448
|
+
name=LangString(["Child"]),
|
|
449
|
+
description={"Child of the human"})
|
|
450
|
+
self.assertEqual(i.inverseOf, Xsd_QName('test:isParentG'))
|
|
451
|
+
i.create()
|
|
452
|
+
i2 = PropertyClass.read(con=self._connection,
|
|
453
|
+
project=self._project,
|
|
454
|
+
property_class_iri=Xsd_QName('test:isChildG'),
|
|
455
|
+
ignore_cache=True)
|
|
456
|
+
self.assertEqual(i2.get(PropClassAttr.INVERSE_OF), Xsd_QName('test:isParentG'))
|
|
457
|
+
|
|
458
|
+
|
|
419
459
|
def test_propertyclass_create_nopermission(self):
|
|
420
460
|
p1 = PropertyClass(
|
|
421
461
|
con=self._unpriv,
|
|
@@ -850,6 +890,24 @@ class TestPropertyClass(unittest.TestCase):
|
|
|
850
890
|
ignore_cache=True)
|
|
851
891
|
self.assertEqual(p8.get(PropClassAttr.TYPE), {OwlPropertyType.SymmetricProperty, OwlPropertyType.OwlDataProperty})
|
|
852
892
|
|
|
893
|
+
def test_propertyclass_update9(self):
|
|
894
|
+
i = PropertyClass(con=self._connection,
|
|
895
|
+
project=self._project,
|
|
896
|
+
property_class_iri=Xsd_QName('test:isChild9'),
|
|
897
|
+
toClass=Iri('test:Human'),
|
|
898
|
+
inverseOf=Xsd_QName('test:isParent9'),
|
|
899
|
+
name=LangString(["Child"]),
|
|
900
|
+
description={"Child of the human"})
|
|
901
|
+
self.assertEqual(i.inverseOf, Xsd_QName('test:isParent9'))
|
|
902
|
+
i.create()
|
|
903
|
+
i.inverseOf = Xsd_QName('test:anotherParent')
|
|
904
|
+
i.update()
|
|
905
|
+
i2 = PropertyClass.read(con=self._connection,
|
|
906
|
+
project=self._project,
|
|
907
|
+
property_class_iri=Xsd_QName('test:isChild9'),
|
|
908
|
+
ignore_cache=True)
|
|
909
|
+
self.assertEqual(i2.get(PropClassAttr.INVERSE_OF), Xsd_QName('test:anotherParent'))
|
|
910
|
+
|
|
853
911
|
# @unittest.skip('Work in progress')
|
|
854
912
|
def test_propertyclass_delete_attrs(self):
|
|
855
913
|
p1 = PropertyClass(
|
|
@@ -894,6 +952,23 @@ class TestPropertyClass(unittest.TestCase):
|
|
|
894
952
|
res = QueryProcessor(self._context, jsonres)
|
|
895
953
|
self.assertEqual(len(res), 0)
|
|
896
954
|
|
|
955
|
+
def test_propertyclass_delete_owlattr(self):
|
|
956
|
+
i = PropertyClass(con=self._connection,
|
|
957
|
+
project=self._project,
|
|
958
|
+
property_class_iri=Xsd_QName('test:isChildDel'),
|
|
959
|
+
toClass=Iri('test:Human'),
|
|
960
|
+
inverseOf=Xsd_QName('test:isParentDel'),
|
|
961
|
+
name=LangString(["Child"]),
|
|
962
|
+
description={"Child of the human"})
|
|
963
|
+
i.create()
|
|
964
|
+
i.inverseOf = None
|
|
965
|
+
i.update()
|
|
966
|
+
i2 = PropertyClass.read(con=self._connection,
|
|
967
|
+
project=self._project,
|
|
968
|
+
property_class_iri=Xsd_QName('test:isChildDel'),
|
|
969
|
+
ignore_cache=True)
|
|
970
|
+
self.assertIsNone(i2.get(PropClassAttr.INVERSE_OF))
|
|
971
|
+
|
|
897
972
|
# @unittest.skip('Work in progress')
|
|
898
973
|
def test_propertyclass_delete(self):
|
|
899
974
|
p1 = PropertyClass(
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.3
|
|
2
2
|
Name: oldaplib
|
|
3
|
-
Version: 0.3.
|
|
3
|
+
Version: 0.3.5
|
|
4
4
|
Summary: Open Media Access Server Library (Linked Open Data middleware/RESTApi)
|
|
5
5
|
License: GNU Affero General Public License version 3
|
|
6
6
|
Author: Lukas Rosenthaler
|
|
@@ -9,6 +9,7 @@ Requires-Python: >=3.12,<4.0
|
|
|
9
9
|
Classifier: License :: Other/Proprietary License
|
|
10
10
|
Classifier: Programming Language :: Python :: 3
|
|
11
11
|
Classifier: Programming Language :: Python :: 3.12
|
|
12
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
12
13
|
Requires-Dist: bcrypt (==5.0.0)
|
|
13
14
|
Requires-Dist: bump2version (>=1.0.1,<2.0.0)
|
|
14
15
|
Requires-Dist: cloudpickle (>=3.1.1,<4.0.0)
|
|
@@ -20,17 +20,17 @@ oldaplib/src/dtypes/xsdset.py,sha256=oMFSY7JGBf0CYneoHL3OtnFIeEPaULN3FdUW7u15_I4
|
|
|
20
20
|
oldaplib/src/enums/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
21
21
|
oldaplib/src/enums/action.py,sha256=aL7XXmoZ63_L2TTR37vqHpPPf5H_kYiPunNyiSDN28U,828
|
|
22
22
|
oldaplib/src/enums/adminpermissions.py,sha256=v8Rc83NPSG_s7830-I7CbmKIhOioN2YkSH1xhWMKXdU,1998
|
|
23
|
-
oldaplib/src/enums/attributeclass.py,sha256=
|
|
23
|
+
oldaplib/src/enums/attributeclass.py,sha256=Lc7OnMMl9vjXj0SuL0l30iEjwC3oWDv_C8PFeTavDGc,3006
|
|
24
24
|
oldaplib/src/enums/datapermissions.py,sha256=0KiDjrPeSpGDAui8Z74sFBdDm64stzcMJx_dVEa2-bo,3437
|
|
25
25
|
oldaplib/src/enums/externalontologyattr.py,sha256=U5vlEQwOkf80mHbztBXicpsWSOCNcHzhoRFJlPnwj-E,808
|
|
26
26
|
oldaplib/src/enums/haspropertyattr.py,sha256=ZncedtYDNAP0kaPE_nsbzb7EdAt32wMXTPxWBBwwvy4,748
|
|
27
27
|
oldaplib/src/enums/language.py,sha256=OfQsFpIBj8lGBbZEqVCR_1F-bimPM48vqBl4EKBgggY,4623
|
|
28
28
|
oldaplib/src/enums/oldaplistattr.py,sha256=xuOU3oP35-PFFmlI-jlN28yqdk5lp_OzScKCC1O4IDI,620
|
|
29
29
|
oldaplib/src/enums/oldaplistnodeattr.py,sha256=qokSxE-0FLyWNipjjY3gZJC2bBEt1qS1Z2SFg-gb0kc,722
|
|
30
|
-
oldaplib/src/enums/owlpropertytype.py,sha256=
|
|
30
|
+
oldaplib/src/enums/owlpropertytype.py,sha256=R7DaCV4vtkGeuDhslN3q7719J1sLKUL-x0o91Te7Qk8,989
|
|
31
31
|
oldaplib/src/enums/permissionsetattr.py,sha256=og4jPvbY86ABr_I9qIvhvg4iIiQCFMcv9-_0D2gfzz8,839
|
|
32
32
|
oldaplib/src/enums/projectattr.py,sha256=A_iayrT3Sd1L_guhHtCKSlUaVf9JqikRXqML-GHkJ3o,1173
|
|
33
|
-
oldaplib/src/enums/propertyclassattr.py,sha256=
|
|
33
|
+
oldaplib/src/enums/propertyclassattr.py,sha256=92R_rVdG-xAWLsRqFknuyKIwLXI-g8gTszL_x9cGNVk,4263
|
|
34
34
|
oldaplib/src/enums/resourceclassattr.py,sha256=g8tc5JDr4wLCteBNnhHMVE4cRZOhlSQqs-qFnRB3_N0,709
|
|
35
35
|
oldaplib/src/enums/sparql_result_format.py,sha256=MLBHKY25o96mswSWioR-rS__zP6kPzYGNIWLZCr9784,636
|
|
36
36
|
oldaplib/src/enums/userattr.py,sha256=ZRBGGLP5NMvyAER893TzRjfkhZk4jOtS9RsSkYsQM-c,1628
|
|
@@ -66,11 +66,11 @@ oldaplib/src/oldaplistnode.py,sha256=NnC2juEGTtEkDO6OlB9PjSw_zTF-wSsRUgEk-6VV9DA
|
|
|
66
66
|
oldaplib/src/oldaplogging.py,sha256=IDSOylms9OSTInYPC4Y2QrTTEzRL0T5I2QssCevOhTU,1242
|
|
67
67
|
oldaplib/src/permissionset.py,sha256=bzzVuZ7O_yVMujziwo32GEJIZYGG3g5gTds4HjLmGtU,31874
|
|
68
68
|
oldaplib/src/project.py,sha256=DNwViRg19zkE1F0zuWqQFK008uTVehVAu7xNbyessig,34207
|
|
69
|
-
oldaplib/src/propertyclass.py,sha256=
|
|
69
|
+
oldaplib/src/propertyclass.py,sha256=pnaDsmyGKQnJaaOHXA0XyLcp4zn1b1vC9sLbjXls4lM,93462
|
|
70
70
|
oldaplib/src/resourceclass.py,sha256=EIxyd7Z_w59wDxWLXCaLvhhvh5SjLEUWb8gqmZz8LLM,102046
|
|
71
71
|
oldaplib/src/user.py,sha256=Z4GXPRkaHXx3glUpPXQdFqYMxQPOuqayDwkTAE5RGjU,48820
|
|
72
72
|
oldaplib/src/userdataclass.py,sha256=FbZkcRt0pKbOeqsZ7HbpwoKE-XPWH2AqpHG1GcsrBPo,12364
|
|
73
|
-
oldaplib/src/version.py,sha256=
|
|
73
|
+
oldaplib/src/version.py,sha256=7Mpk_ZUorFUStSKEAk4F5dnB7uCLNFviloAVMVv5V-8,21
|
|
74
74
|
oldaplib/src/xsd/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
75
75
|
oldaplib/src/xsd/floatingpoint.py,sha256=rDReKqh0mXyc4F5wslgTUxbeGf3-PGERyughj5_62YI,8852
|
|
76
76
|
oldaplib/src/xsd/iri.py,sha256=w1Dr0z-REi7yPe3GPGnyzGrLVMvLY03kEeK-AmZ9sxw,8383
|
|
@@ -106,7 +106,7 @@ oldaplib/src/xsd/xsd_nonnegativeinteger.py,sha256=pj9xa5YslZV6gSlnyIk4aXESQVgtsE
|
|
|
106
106
|
oldaplib/src/xsd/xsd_nonpositiveinteger.py,sha256=7cAFDIcewzeDZscQi3cbDZdqcbUMAvYR7DHrPvFw_fM,965
|
|
107
107
|
oldaplib/src/xsd/xsd_normalizedstring.py,sha256=NLLzH2Memdlrp4Ogvu94YOOOQzEMjvQeEZ8J-tOV40M,3965
|
|
108
108
|
oldaplib/src/xsd/xsd_positiveinteger.py,sha256=gAuqOpcOo0RHXtONXc2l-NSfcvSLDiSboUl963OAh1I,946
|
|
109
|
-
oldaplib/src/xsd/xsd_qname.py,sha256=
|
|
109
|
+
oldaplib/src/xsd/xsd_qname.py,sha256=A5W5Xoth8PYG_zVgLaOonhP0Zplb2vXOgmDakY_5c1o,7389
|
|
110
110
|
oldaplib/src/xsd/xsd_short.py,sha256=Yg1ltCIay2y-NObW4ZN-UvYfAF2sOOi_ZFLdyiUP6hQ,990
|
|
111
111
|
oldaplib/src/xsd/xsd_string.py,sha256=y_tw17IrI1xr1lLDSGlPPp1U22N8Oea787kTJz7QO1I,9780
|
|
112
112
|
oldaplib/src/xsd/xsd_time.py,sha256=aZLXu2a-nyA1_FuloW-foL6UWnXwO7pMqhiPmAexL2Y,3671
|
|
@@ -134,7 +134,7 @@ oldaplib/test/test_oldaplist_helpers.py,sha256=vJkA_Txhdk4oIwo2YK566yOte2Z6MQksh
|
|
|
134
134
|
oldaplib/test/test_oldaplistnode.py,sha256=bWoCmDmHvOnNNviSCvhWo7LA2CskA_5IRDxNUufTKj4,149434
|
|
135
135
|
oldaplib/test/test_permissionset.py,sha256=YOCirqm_oFE1Emz9fYsnDeawwI6zHN9xBv9vOZnKst0,23368
|
|
136
136
|
oldaplib/test/test_project.py,sha256=fwkfaCxEskd27xinxDDr74dMWs7S0YcGr84mUOw20x4,25290
|
|
137
|
-
oldaplib/test/test_propertyclass.py,sha256=
|
|
137
|
+
oldaplib/test/test_propertyclass.py,sha256=67Kw5cDlPzRNm20bqz1QB-8PXFpV5iQy8Jza1epLXxk,53293
|
|
138
138
|
oldaplib/test/test_resourceclass.py,sha256=WQGyns2S8O6vDH8oXBQjcww_VcjIONovuNdKm0coO-c,96621
|
|
139
139
|
oldaplib/test/test_semantic_version.py,sha256=OSJYHWDpKBqk-HsxJ2nFpSr14a4OEZTFCogzEni8mcE,3392
|
|
140
140
|
oldaplib/test/test_user.py,sha256=gLTcQ0ymi9pYPPpq9BOY_3YS07EJXtnJKFCHe4Rj0mQ,72133
|
|
@@ -157,6 +157,6 @@ oldaplib/testdata/source_type.yaml,sha256=dSihKikw3O-IlGf6anj5KWMoBYLaweLVF1Zojm
|
|
|
157
157
|
oldaplib/testdata/test_move_left_of_toL.yaml,sha256=2m1OSQrQFlsCQxeJrjzBAO74LMprNDo_HuyrYGsOeXI,787
|
|
158
158
|
oldaplib/testdata/testlist.yaml,sha256=AT11nXEG81Sfyb-tr1gQV0H_dZBrOCcFuHf7YtL8P2g,1994
|
|
159
159
|
oldaplib/testit.http,sha256=qW7mnr6aNLXFG6lQdLgyhXILOPN6qc5iFVZclLyVvkY,303
|
|
160
|
-
oldaplib-0.3.
|
|
161
|
-
oldaplib-0.3.
|
|
162
|
-
oldaplib-0.3.
|
|
160
|
+
oldaplib-0.3.5.dist-info/METADATA,sha256=YpXOxS-1xvQQpvMl_REtdkSbsizXGNcE3zhylyTrj2s,2854
|
|
161
|
+
oldaplib-0.3.5.dist-info/WHEEL,sha256=b4K_helf-jlQoXBBETfwnf4B04YC67LOev0jo4fX5m8,88
|
|
162
|
+
oldaplib-0.3.5.dist-info/RECORD,,
|