class PropertyClass: _context: Context _id: str _name: str _ontology_id: str _superproperties: List[str] _object: str _subject: str _gui_element: str _gui_attributes: Dict[str, str] _label: LangString _comment: LangString _editable: bool _linkvalue: bool _changed: Set[str] def __init__(self, con: Connection, context: Context, id: Optional[str] = None, name: Optional[str] = None, ontology_id: Optional[str] = None, superproperties: Optional[List[Union['PropertyClass', str]]] = None, object: Optional[str] = None, subject: Optional[str] = None, gui_element: Optional[str] = None, gui_attributes: Optional[Dict[str, str]] = None, label: Optional[Union[LangString, str]] = None, comment: Optional[Union[LangString, str]] = None, editable: Optional[bool] = None, linkvalue: Optional[bool] = None): if not isinstance(con, Connection): raise BaseError( '"con"-parameter must be an instance of Connection') if not isinstance(context, Context): raise BaseError( '"context"-parameter must be an instance of Context') self.con = con self._context = context self._id = id self._name = name self._ontology_id = ontology_id if isinstance(superproperties, PropertyClass): self._superproperties = list(map(lambda a: a.id, superproperties)) else: self._superproperties = superproperties self._object = object self._subject = subject self._gui_element = gui_element self._gui_attributes = gui_attributes # # process label # if label is not None: if isinstance(label, str): self._label = LangString(label) elif isinstance(label, LangString): self._label = label else: raise BaseError('Invalid LangString for label!') else: self._label = None # # process comment # if comment is not None: if isinstance(comment, str): self._comment = LangString(comment) elif isinstance(comment, LangString): self._comment = comment else: raise BaseError('Invalid LangString for comment!') else: self._comment = None self._editable = editable self._linkvalue = linkvalue self._changed = set() # # Here follows a list of getters/setters # @property def name(self) -> Optional[str]: return self._name @name.setter def name(self, value: str) -> None: raise BaseError('"name" cannot be modified!') @property def id(self) -> Optional[str]: return self._id @id.setter def id(self, value: str) -> None: raise BaseError('"id" cannot be modified!') @property def ontology_id(self) -> Optional[str]: return self._ontology_id @ontology_id.setter def ontology_id(self, value: str) -> None: raise BaseError('"ontology_id" cannot be modified!') @property def superproperties(self) -> Optional[str]: return self._superproperties @superproperties.setter def superproperties(self, value: str) -> None: raise BaseError('"superproperties" cannot be modified!') @property def object(self) -> Optional[str]: return self._object @object.setter def object(self, value: Any): raise BaseError('"object" cannot be modified!') @property def subject(self) -> Optional[str]: return self._subject @subject.setter def subject(self, value: Any): raise BaseError('"subject" cannot be modified!') @property def gui_element(self) -> Optional[str]: return self._gui_element @gui_element.setter def gui_element(self, value: str) -> None: self._gui_element = value self._changed.append('gui_element') @property def gui_attributes(self) -> Optional[Dict[str, str]]: return self._gui_attributes @gui_attributes.setter def gui_attributes(self, value: List[Dict[str, str]]) -> None: self._gui_attributes = value self._changed.append('gui_attributes') def addGuiAttribute(self, key: str, value: str) -> None: self._gui_attributes[key] = value self._changed.append('gui_attributes') def rmGuiAttribute(self, key: str) -> None: if self._gui_attributes.get(key) is not None: del self._gui_attributes[key] self._changed.append('gui_attributes') @property def label(self) -> Optional[LangString]: return self._label @label.setter def label(self, value: Optional[Union[LangString, str]]) -> None: if value is None: self._label.empty() # clear all labels else: if isinstance(value, LangString): self._label = value elif isinstance(value, str): self._label = LangString(value) else: raise BaseError('Not a valid LangString') self._changed.add('label') def addLabel(self, lang: Union[Languages, str], value: str) -> None: self._label[lang] = value self._changed.add('label') def rmLabel(self, lang: Union[Languages, str]) -> None: del self._label[lang] self._changed.add('label') @property def comment(self) -> Optional[LangString]: return self._comment @comment.setter def comment(self, value: Optional[LangString]) -> None: if value is None: self._comment.empty() # clear all comments! else: if isinstance(value, LangString): self._comment = value elif isinstance(value, str): self._comment = LangString(value) else: raise BaseError('Not a valid LangString') self._changed.add('comment') def addComment(self, lang: Union[Languages, str], value: str) -> None: self._comment[lang] = value self._changed.add('comment') def rmComment(self, lang: Union[Languages, str]) -> None: del self._comment[lang] self._changed.add('comment') @property def editable(self) -> bool: return self._editable @editable.setter def editable(self, value: bool) -> None: raise BaseError('"editable" cannot be modified!') @property def linkvalue(self) -> bool: return self._linkvalue @linkvalue.setter def linkvalue(self) -> None: raise BaseError('"linkvalue" cannot be modified!') @classmethod def fromJsonObj(cls, con: Connection, context: Context, json_obj: Any) -> Any: if isinstance(json_obj, list): json_obj = json_obj[ 0] # TODO: Is it possible to have more than one element in the list?? if not isinstance(con, Connection): raise BaseError( '"con"-parameter must be an instance of Connection') if not isinstance(context, Context): raise BaseError( '"context"-parameter must be an instance of Context') rdf = context.prefixFromIri( "http://www.w3.org/1999/02/22-rdf-syntax-ns#") rdfs = context.prefixFromIri("http://www.w3.org/2000/01/rdf-schema#") owl = context.prefixFromIri("http://www.w3.org/2002/07/owl#") xsd = context.prefixFromIri("http://www.w3.org/2001/XMLSchema#") knora_api = context.prefixFromIri( "http://api.knora.org/ontology/knora-api/v2#") salsah_gui = context.prefixFromIri( "http://api.knora.org/ontology/salsah-gui/v2#") if not (json_obj.get(knora_api + ':isResourceProperty')): raise BaseError("This is not a property!") if json_obj.get('@id') is None: raise BaseError('Property class has no "@id"!') tmp_id = json_obj.get('@id').split(':') id = context.iriFromPrefix(tmp_id[0]) + '#' + tmp_id[1] ontology_id = tmp_id[0] name = tmp_id[1] superproperties_obj = json_obj.get(rdfs + ':subPropertyOf') superproperties: List[Union[None, str]] if not isinstance(superproperties_obj, list): superproperties_obj = [superproperties_obj ] # make a list out of it if superproperties_obj is not None: superprops: List[Any] = list( filter(lambda a: a.get('@id') is not None, superproperties_obj)) superproperties = list(map(lambda a: a['@id'], superprops)) else: superproperties = None object = WithId(json_obj.get(knora_api + ':objectType')).str() subject = WithId(json_obj.get(knora_api + ':subjectType')).str() label = LangString.fromJsonLdObj(json_obj.get(rdfs + ':label')) comment = LangString.fromJsonLdObj(json_obj.get(rdfs + ':comment')) gui_element = None if json_obj.get(salsah_gui + ':guiElement') is not None: gui_element = WithId(json_obj.get(salsah_gui + ':guiElement')).str() gui_attributes_list = json_obj.get(salsah_gui + ':guiAttribute') gui_attributes: Union[None, Dict[str, str]] = None if gui_attributes_list is not None: gui_attributes = {} if not isinstance(gui_attributes_list, list): gui_attributes_list = [gui_attributes_list] for ga in gui_attributes_list: tmp = ga.split('=') if len(tmp) == 1: gui_attributes[tmp[0]] = '' else: gui_attributes[tmp[0]] = tmp[1] editable = json_obj.get(knora_api + ':isEditable') linkvalue = json_obj.get(knora_api + ':isLinkProperty') return cls(con=con, context=context, id=id, name=name, ontology_id=ontology_id, superproperties=superproperties, object=object, subject=subject, gui_element=gui_element, gui_attributes=gui_attributes, label=label, comment=comment, editable=editable, linkvalue=linkvalue) def toJsonObj(self, lastModificationDate: LastModificationDate, action: Actions, what: Optional[str] = None) -> Any: def resolve_propref(resref: str): tmp = resref.split(':') if len(tmp) > 1: if tmp[0]: return { "@id": resref } # fully qualified name in the form "prefix:name" else: return { "@id": self._context.prefixFromIri(self._ontology_id) + ':' + tmp[1] } # ":name" in current ontology else: return { "@id": "knora-api:" + resref } # no ":", must be from knora-api! tmp = {} exp = re.compile('^http.*') # It is already a fully IRI if exp.match(self._ontology_id): propid = self._context.prefixFromIri( self._ontology_id) + ":" + self._name ontid = self._ontology_id else: propid = self._ontology_id + ":" + self._name ontid = self._context.iriFromPrefix(self._ontology_id) if action == Actions.Create: if self._name is None: raise BaseError("There must be a valid property class name!") if self._ontology_id is None: raise BaseError("There must be a valid ontology_id given!") if self._superproperties is None: superproperties = [{"@id": "knora-api:hasValue"}] else: superproperties = list( map(resolve_propref, self._superproperties)) tmp = { "@id": ontid, # self._ontology_id, "@type": "owl:Ontology", "knora-api:lastModificationDate": lastModificationDate.toJsonObj(), "@graph": [{ "@id": propid, "@type": "owl:ObjectProperty", "rdfs:label": self._label.toJsonLdObj(), "rdfs:subPropertyOf": superproperties }], "@context": self._context.toJsonObj() } if self._comment is not None: if not self._comment.isEmpty(): tmp['@graph'][0][ "rdfs:comment"] = self._comment.toJsonLdObj() if self._subject is not None: tmp['@graph'][0]["knora-api:subjectType"] = resolve_propref( self._subject) if self._object is not None: tmp['@graph'][0]["knora-api:objectType"] = resolve_propref( self._object) if self._gui_element is not None: tmp['@graph'][0]["salsah-gui:guiElement"] = { "@id": self._gui_element } if self._gui_attributes: ga = list( map(lambda x: x[0] + '=' + str(x[1]), self._gui_attributes.items())) tmp['@graph'][0]["salsah-gui:guiAttribute"] = ga elif action == Actions.Update: tmp = { "@id": ontid, # self._ontology_id, "@type": "owl:Ontology", "knora-api:lastModificationDate": lastModificationDate.toJsonObj(), "@graph": [{ "@id": propid, "@type": "owl:ObjectProperty", }], "@context": self._context.toJsonObj(), } if what == 'label': if not self._label.isEmpty() and 'label' in self._changed: tmp['@graph'][0]['rdfs:label'] = self._label.toJsonLdObj() if what == 'comment': if not self._comment.isEmpty() and 'comment' in self._changed: tmp['@graph'][0][ 'rdfs:comment'] = self._comment.toJsonLdObj() return tmp def create( self, last_modification_date: LastModificationDate ) -> Tuple[LastModificationDate, 'PropertyClass']: jsonobj = self.toJsonObj(last_modification_date, Actions.Create) jsondata = json.dumps(jsonobj, cls=SetEncoder, indent=2) result = self.con.post('/v2/ontologies/properties', jsondata) last_modification_date = LastModificationDate( result['knora-api:lastModificationDate']) return last_modification_date, PropertyClass.fromJsonObj( self.con, self._context, result['@graph']) def update( self, last_modification_date: LastModificationDate ) -> Tuple[LastModificationDate, 'ResourceClass']: # # Note: Knora is able to change only one thing per call, either label or comment! # result = None something_changed = False if 'label' in self._changed: jsonobj = self.toJsonObj(last_modification_date, Actions.Update, 'label') jsondata = json.dumps(jsonobj, cls=SetEncoder, indent=4) result = self.con.put('/v2/ontologies/properties', jsondata) last_modification_date = LastModificationDate( result['knora-api:lastModificationDate']) something_changed = True if 'comment' in self._changed: jsonobj = self.toJsonObj(last_modification_date, Actions.Update, 'comment') jsondata = json.dumps(jsonobj, cls=SetEncoder, indent=4) result = self.con.put('/v2/ontologies/properties', jsondata) last_modification_date = LastModificationDate( result['knora-api:lastModificationDate']) something_changed = True if something_changed: return last_modification_date, PropertyClass.fromJsonObj( self.con, self._context, result['@graph']) else: return last_modification_date, self def delete( self, last_modification_date: LastModificationDate ) -> LastModificationDate: result = self.con.delete('/v2/ontologies/properties/' + quote_plus(self._id) + '?lastModificationDate=' + str(last_modification_date)) return LastModificationDate(result['knora-api:lastModificationDate']) def print(self, offset: int = 0): blank = ' ' print(f'{blank:>{offset}}Property Class Info') print(f'{blank:>{offset+2}}Name: {self._name}') print(f'{blank:>{offset+2}}Ontology prefix: {self._ontology_id}') print(f'{blank:>{offset+2}}Superproperties:') if self._superproperties is not None: for sc in self._superproperties: print(f'{blank:>{offset + 4}}{sc}') if self._label is not None: print(f'{blank:>{offset + 2}}Labels:') self._label.print(offset + 4) if self._subject is not None: print(f'{blank:>{offset + 4}}Subject: {self._subject}') if self._object is not None: print(f'{blank:>{offset + 4}}Object: {self._object}') if self._gui_element is not None: print(f'{blank:>{offset + 4}}Guielement: {self._gui_element}') if self._gui_attributes is not None: print(f'{blank:>{offset + 4}}Gui Attributes:') if self._gui_attributes is not None: pprint(self._gui_attributes) for (attname, attvalue) in self._gui_attributes.items(): print( f'{blank:>{offset + 6}}Attribute: {attname} Value: {attvalue}' ) if self._comment is not None: print(f'{blank:>{offset + 2}}Comments:') self._comment.print(offset + 4) if self._editable is not None: print(f'{blank:>{offset + 4}}Editable: {self._editable}') if self._linkvalue is not None: print(f'{blank:>{offset + 4}}Editable: {self._linkvalue}')
class ResourceClass: con: Connection _context: Context _id: str _name: str _ontology_id: str _superclasses: List[str] _label: LangString _comment: LangString _permissions: str _has_properties: Dict[str, HasProperty] _changed: Set[str] def __init__(self, con: Connection, context: Context, id: Optional[str] = None, name: Optional[str] = None, ontology_id: Optional[str] = None, superclasses: Optional[List[Union['ResourceClass', str]]] = None, label: Optional[Union[LangString, str]] = None, comment: Optional[Union[LangString, str]] = None, permissions: Optional[str] = None, has_properties: Optional[Dict[str, HasProperty]] = None): if not isinstance(con, Connection): raise BaseError( '"con"-parameter must be an instance of Connection') if not isinstance(context, Context): raise BaseError( '"context"-parameter must be an instance of Context') self.con = con self._context = context self._id = id self._name = name self._ontology_id = ontology_id if isinstance(superclasses, ResourceClass): self._superclasses = list(map(lambda a: a.id, superclasses)) else: self._superclasses = superclasses # # process label # if label is not None: if isinstance(label, str): self._label = LangString(label) elif isinstance(label, LangString): self._label = label else: raise BaseError('Invalid LangString for label!') else: self._label = None # # process comment # if comment is not None: if isinstance(comment, str): self._comment = LangString(comment) elif isinstance(comment, LangString): self._comment = comment else: raise BaseError('Invalid LangString for comment!') else: self._comment = None self._permissions = permissions self._has_properties = has_properties self._changed = set() # # Here follows a list of getters/setters # @property def name(self) -> Optional[str]: return self._name @name.setter def name(self, value: str) -> None: raise BaseError('"name" cannot be modified!') @property def id(self) -> Optional[str]: return self._id @id.setter def id(self, value: str) -> None: raise BaseError('"id" cannot be modified!') @property def ontology_id(self) -> Optional[str]: return self._ontology_id @ontology_id.setter def ontology_id(self, value: str) -> None: raise BaseError('"ontology_id" cannot be modified!') @property def superclasses(self) -> Optional[List[str]]: return self._superclasses @superclasses.setter def superclasses(self, value: List[str]) -> None: raise BaseError('"superclasses" cannot be modified!') @property def label(self) -> Optional[LangString]: return self._label @label.setter def label(self, value: Optional[Union[LangString, str]]) -> None: if value is None: self._label.empty() # clear all labels else: if isinstance(value, LangString): self._label = value elif isinstance(value, str): self._label = LangString(value) else: raise BaseError('Not a valid LangString') self._changed.add('label') def addLabel(self, lang: Union[Languages, str], value: str) -> None: self._label[lang] = value self._changed.add('label') def rmLabel(self, lang: Union[Languages, str]) -> None: del self._label[lang] self._changed.add('label') @property def comment(self) -> Optional[LangString]: return self._comment @comment.setter def comment(self, value: Optional[LangString]) -> None: if value is None: self._comment.empty() # clear all comments! else: if isinstance(value, LangString): self._comment = value elif isinstance(value, str): self._comment = LangString(value) else: raise BaseError('Not a valid LangString') self._changed.add('comment') def addComment(self, lang: Union[Languages, str], value: str) -> None: self._comment[lang] = value self._changed.add('comment') def rmComment(self, lang: Union[Languages, str]) -> None: del self._comment[lang] self._changed.add('comment') @property def permissions(self) -> Optional[str]: return self._permissions @permissions.setter def permissions(self, value: str) -> None: raise BaseError('"permissions" cannot be modified!') @property def has_property(self) -> Dict[str, HasProperty]: return self._has_properties @has_property.setter def has_property(self, value: str) -> None: raise BaseError('"has_property" cannot be modified!') def getProperty(self, property_id) -> Optional[HasProperty]: if self._has_properties is None: return None else: return self._has_properties.get( self._context.getPrefixIri(property_id)) def addProperty( self, property_id: str, cardinality: Cardinality, last_modification_date: LastModificationDate ) -> Optional[LastModificationDate]: if self._has_properties.get(property_id) is None: latest_modification_date, resclass = HasProperty( con=self.con, context=self._context, ontology_id=self._ontology_id, property_id=property_id, resclass_id=self.id, cardinality=cardinality).create(last_modification_date) hp = resclass.getProperty(property_id) hp.ontology_id = self._context.iriFromPrefix(self._ontology_id) hp.resclass_id = self.id self._has_properties[hp.property_id] = hp return latest_modification_date else: raise BaseError("Property already has cardinality in this class!") def updateProperty( self, property_id: str, cardinality: Cardinality, last_modification_date: LastModificationDate ) -> Optional[LastModificationDate]: property_id = self._context.getPrefixIri(property_id) if self._has_properties.get(property_id) is not None: has_properties = self._has_properties[property_id] onto_id = has_properties.ontology_id # save for later user rescl_id = has_properties.resclass_id # save for later user has_properties.cardinality = cardinality latest_modification_date, resclass = has_properties.update( last_modification_date) hp = resclass.getProperty(property_id) hp.ontology_id = self._context.iriFromPrefix( onto_id) # restore value hp.resclass_id = rescl_id # restore value self._has_properties[hp.property_id] = hp return latest_modification_date else: return last_modification_date @classmethod def fromJsonObj(cls, con: Connection, context: Context, json_obj: Any) -> Any: if isinstance(json_obj, list): json_obj = json_obj[ 0] # TODO: Is it possible to have more than one element in the list?? if not isinstance(con, Connection): raise BaseError( '"con"-parameter must be an instance of Connection') if not isinstance(context, Context): raise BaseError( '"context"-parameter must be an instance of Context') rdf = context.prefixFromIri( "http://www.w3.org/1999/02/22-rdf-syntax-ns#") rdfs = context.prefixFromIri("http://www.w3.org/2000/01/rdf-schema#") owl = context.prefixFromIri("http://www.w3.org/2002/07/owl#") xsd = context.prefixFromIri("http://www.w3.org/2001/XMLSchema#") knora_api = context.prefixFromIri( "http://api.knora.org/ontology/knora-api/v2#") salsah_gui = context.prefixFromIri( "http://api.knora.org/ontology/salsah-gui/v2#") if not (json_obj.get(knora_api + ':isResourceClass') or json_obj.get(knora_api + ':isStandoffClass')): raise BaseError("This is not a resource!") if json_obj.get('@id') is None: raise BaseError('Resource class has no "@id"!') tmp_id = json_obj.get('@id').split(':') id = context.iriFromPrefix(tmp_id[0]) + '#' + tmp_id[1] ontology_id = tmp_id[0] name = tmp_id[1] superclasses_obj = json_obj.get(rdfs + ':subClassOf') if superclasses_obj is not None: supercls: List[Any] = list( filter(lambda a: a.get('@id') is not None, superclasses_obj)) superclasses: List[str] = list(map(lambda a: a['@id'], supercls)) has_props: List[Any] = list( filter(lambda a: a.get('@type') == (owl + ':Restriction'), superclasses_obj)) has_properties: Dict[HasProperty] = dict( map(lambda a: HasProperty.fromJsonObj(con, context, a), has_props)) else: superclasses = None has_properties = None label = LangString.fromJsonLdObj(json_obj.get(rdfs + ':label')) comment = LangString.fromJsonLdObj(json_obj.get(rdfs + ':comment')) return cls(con=con, context=context, name=name, id=id, ontology_id=ontology_id, superclasses=superclasses, label=label, comment=comment, has_properties=has_properties) def toJsonObj(self, lastModificationDate: LastModificationDate, action: Actions, what: Optional[str] = None) -> Any: def resolve_resref(resref: str): tmp = resref.split(':') if len(tmp) > 1: if tmp[0]: return { "@id": resref } # fully qualified name in the form "prefix:name" else: return { "@id": self._context.prefixFromIri(self._ontology_id) + ':' + tmp[1] } # ":name" in current ontology else: return { "@id": "knora-api:" + resref } # no ":", must be from knora-api! tmp = {} exp = re.compile('^http.*') # It is already a fully IRI if exp.match(self._ontology_id): resid = self._context.prefixFromIri( self._ontology_id) + ":" + self._name ontid = self._ontology_id else: resid = self._ontology_id + ":" + self._name ontid = self._context.iriFromPrefix(self._ontology_id) if action == Actions.Create: if self._name is None: raise BaseError("There must be a valid resource class name!") if self._ontology_id is None: raise BaseError("There must be a valid ontology_id given!") if self._superclasses is None: superclasses = [{"@id": "knora-api:Resource"}] else: superclasses = list(map(resolve_resref, self._superclasses)) if self._comment is None or self._comment.isEmpty(): self._comment = LangString("no comment vailable") tmp = { "@id": ontid, # self._ontology_id, "@type": "owl:Ontology", "knora-api:lastModificationDate": lastModificationDate.toJsonObj(), "@graph": [{ "@id": resid, "@type": "owl:Class", "rdfs:label": self._label.toJsonLdObj(), "rdfs:comment": self._comment.toJsonLdObj(), "rdfs:subClassOf": superclasses }], "@context": self._context.toJsonObj(), } elif action == Actions.Update: tmp = { "@id": ontid, # self._ontology_id, "@type": "owl:Ontology", "knora-api:lastModificationDate": lastModificationDate.toJsonObj(), "@graph": [{ "@id": resid, "@type": "owl:Class", }], "@context": self._context.toJsonObj(), } if what == 'label': if not self._label.isEmpty() and 'label' in self._changed: tmp['@graph'][0]['rdfs:label'] = self._label.toJsonLdObj() if what == 'comment': if not self._comment.isEmpty() and 'comment' in self._changed: tmp['@graph'][0][ 'rdfs:comment'] = self._comment.toJsonLdObj() return tmp def create( self, last_modification_date: LastModificationDate ) -> Tuple[LastModificationDate, 'ResourceClass']: jsonobj = self.toJsonObj(last_modification_date, Actions.Create) jsondata = json.dumps(jsonobj) result = self.con.post('/v2/ontologies/classes', jsondata) last_modification_date = LastModificationDate( result['knora-api:lastModificationDate']) return last_modification_date, ResourceClass.fromJsonObj( self.con, self._context, result['@graph']) def update( self, last_modification_date: LastModificationDate ) -> Tuple[LastModificationDate, 'ResourceClass']: # # Note: Knora is able to change only one thing per call, either label or comment! # result = None something_changed = False if 'label' in self._changed: jsonobj = self.toJsonObj(last_modification_date, Actions.Update, 'label') jsondata = json.dumps(jsonobj, cls=SetEncoder, indent=4) result = self.con.put('v2/ontologies/classes', jsondata) last_modification_date = LastModificationDate( result['knora-api:lastModificationDate']) something_changed = True if 'comment' in self._changed: jsonobj = self.toJsonObj(last_modification_date, Actions.Update, 'comment') jsondata = json.dumps(jsonobj, cls=SetEncoder, indent=4) result = self.con.put('v2/ontologies/classes', jsondata) last_modification_date = LastModificationDate( result['knora-api:lastModificationDate']) something_changed = True if something_changed: return last_modification_date, ResourceClass.fromJsonObj( self.con, self._context, result['@graph']) else: return last_modification_date, self def delete( self, last_modification_date: LastModificationDate ) -> LastModificationDate: result = self.con.delete('v2/ontologies/classes/' + quote_plus(self._id) + '?lastModificationDate=' + str(last_modification_date)) return LastModificationDate(result['knora-api:lastModificationDate']) def print(self, offset: int = 0): blank = ' ' print(f'{blank:>{offset}}Resource Class Info') print(f'{blank:>{offset+2}}Name: {self._name}') print(f'{blank:>{offset+2}}Ontology prefix: {self._ontology_id}') print(f'{blank:>{offset+2}}Superclasses:') if self._superclasses is not None: for sc in self._superclasses: print(f'{blank:>{offset + 4}}{sc}') if self._label is not None: print(f'{blank:>{offset + 2}}Labels:') self._label.print(offset + 4) if self._comment is not None: print(f'{blank:>{offset + 2}}Comments:') self._comment.print(offset + 4) if self._has_properties is not None: print(f'{blank:>{offset + 2}}Has properties:') if self._has_properties is not None: for pid, hp in self._has_properties.items(): hp.print(offset + 4)