diff --git a/ontology/uco/core/core.ttl b/ontology/uco/core/core.ttl index d2689b66..5ab836a7 100644 --- a/ontology/uco/core/core.ttl +++ b/ontology/uco/core/core.ttl @@ -1,8 +1,11 @@ +# imports: http://www.w3.org/TR/skos-reference/skos-owl1-dl.rdf + @prefix core: . @prefix owl: . @prefix rdf: . @prefix rdfs: . @prefix sh: . +@prefix skos: . @prefix types: . @prefix xsd: . @@ -10,6 +13,7 @@ a owl:Ontology ; rdfs:label "uco-core"@en ; rdfs:comment "This ontology defines classes and properties that are shared across the various UCO ontologies. At a high-level, the UCO core ontology provides base classes, relationship-oriented classes, content-aggregation classes, and shared classes."@en ; + owl:imports ; . core:Annotation @@ -317,6 +321,13 @@ core:Relationship sh:targetClass core:Relationship ; . +core:TaxonomicConcept + a owl:Class ; + rdfs:subClassOf skos:Concept ; + rdfs:label "TaxonomicConcept"@en ; + rdfs:comment "Taxonomic Concept is a mix-in class that enables UCO as an OWL ontology to use SKOS taxonomic individuals. [based on https://www.w3.org/2006/07/SWD/SKOS/skos-and-owl/master.html#Hybrids]"@en ; + . + core:UcoObject a owl:Class , diff --git a/ontology/uco/master/uco.ttl b/ontology/uco/master/uco.ttl index c9d4397f..4a2cc753 100644 --- a/ontology/uco/master/uco.ttl +++ b/ontology/uco/master/uco.ttl @@ -1,3 +1,4 @@ +# imports: http://www.w3.org/TR/skos-reference/skos-owl1-dl.rdf # imports: https://ontology.unifiedcyberontology.org/co # imports: https://ontology.unifiedcyberontology.org/owl # imports: https://ontology.unifiedcyberontology.org/uco/action @@ -26,6 +27,7 @@ a owl:Ontology ; rdfs:label "uco-master"@en ; owl:imports + , , , , diff --git a/ontology/uco/observable/observable.ttl b/ontology/uco/observable/observable.ttl index 0c747c3e..ba344497 100644 --- a/ontology/uco/observable/observable.ttl +++ b/ontology/uco/observable/observable.ttl @@ -8,6 +8,7 @@ @prefix action: . @prefix co: . @prefix core: . +@prefix dcterms: . @prefix identity: . @prefix location: . @prefix observable: . @@ -15,6 +16,7 @@ @prefix rdf: . @prefix rdfs: . @prefix sh: . +@prefix skos: . @prefix types: . @prefix vocabulary: . @prefix xsd: . @@ -1749,6 +1751,11 @@ observable:ContentDataFacet rdfs:label "ContentDataFacet"@en ; rdfs:comment "A content data facet is a grouping of characteristics unique to a block of digital data."@en ; sh:property + [ + sh:class dcterms:FileFormat ; + sh:nodeKind sh:IRI ; + sh:path observable:mimeType ; + ] , [ sh:class observable:ObservableObject ; sh:maxCount "1"^^xsd:integer ; @@ -1796,11 +1803,6 @@ observable:ContentDataFacet sh:nodeKind sh:Literal ; sh:path observable:mimeClass ; ] , - [ - sh:datatype xsd:string ; - sh:nodeKind sh:Literal ; - sh:path observable:mimeType ; - ] , [ sh:datatype vocabulary:EndiannessTypeVocab ; sh:message "Value is outside the default vocabulary EndiannessTypeVocab." ; @@ -10964,10 +10966,37 @@ observable:mimeClass . observable:mimeType - a owl:DatatypeProperty ; + a owl:ObjectProperty ; rdfs:label "mimeType"@en ; - rdfs:comment "MIME type of the data. For example 'text/html' or 'audio/mp3'."@en ; - rdfs:range xsd:string ; + rdfs:comment "MIME type of the data. The text form of '${type}/${subtype}' (for example, 'text/html' or 'audio/mp3') can be used to find a UCO-provisioned set of types from the UCO Media Types Taxonomy. For interoperability with non-UCO resources, dcterms:FileFormat is this property's required range. The more-specific UCO classes types:IANAMediaType or types:NonIANAMediaType should be used when available."@en ; + rdfs:range dcterms:FileFormat ; + rdfs:seeAlso + types:IANAMediaType , + types:NonIANAMediaType , + + ; + . + +observable:mimeType-class-types-MIMEFormat + a sh:PropertyShape ; + rdfs:comment "This shape is given an IRI in order to facilitate deactivation on request."@en ; + rdfs:seeAlso sh:deactivated ; + sh:class types:MIMEFormat ; + sh:message "Value is not an instance of types:MIMEFormat or one of its subclasses. Please consider using a value having type types:IANAMediaType or types:NonIANAMediaType."@en ; + sh:path observable:mimeType ; + sh:severity sh:Info ; + sh:targetSubjectsOf observable:mimeType ; + . + +observable:mimeType-notation + a sh:PropertyShape ; + rdfs:comment "This shape is intended to be deactivated by using overriding shapes in the UCO Mime Taxonomy."@en ; + rdfs:seeAlso ; + sh:message "The used mimeType value is not a concept with a skos:notation. Some consumers of this data expect a string with the MIME 'type/subtype' format to be supplied with skos:notation. Please either add the skos:notation to your input graph or incorporate the UCO MIME Taxonomy."@en ; + sh:minCount "1"^^xsd:integer ; + sh:path skos:notation ; + sh:severity sh:Warning ; + sh:targetObjectsOf observable:mimeType ; . observable:minorImageVersion diff --git a/ontology/uco/types/types.ttl b/ontology/uco/types/types.ttl index 8bcc917c..83991e9c 100644 --- a/ontology/uco/types/types.ttl +++ b/ontology/uco/types/types.ttl @@ -4,6 +4,8 @@ @prefix co: . @prefix core: . +@prefix dcterms: . +@prefix observable: . @prefix owl: . @prefix rdf: . @prefix rdfs: . @@ -22,6 +24,11 @@ ; . +dcterms:FileFormat + a owl:Class ; + rdfs:comment "UCO extends dcterms:FileFormat to be an OWL Class in addition to its native definition of an RDF Class."@en ; + . + types:ControlledDictionary a owl:Class , @@ -167,16 +174,41 @@ types:Hash sh:targetClass types:Hash ; . +types:IANAMediaType + a owl:Class ; + rdfs:subClassOf types:MIMEFormat ; + rdfs:label "IANAMediaType"@en ; + owl:disjointWith types:NonIANAMediaType ; + . + types:Identifier a rdfs:Datatype ; rdfs:comment "An identifier is a string conformant to the specified UUID-based format for UCO object identifiers."@en ; . +types:MIMEFormat + a owl:Class ; + rdfs:subClassOf + dcterms:FileFormat , + core:TaxonomicConcept + ; + rdfs:label "MIMEFormat"@en ; + rdfs:comment "This class should be considered an intermediary, 'abstract' class, and should not have individuals defined that are not a member of one of its subclasses. This class has two purposes. First, to encode for interoperability with existing frameworks, without relying on RDFS inference, that a UCO MIMEFormat individual is both a SKOS Concept (via core:TaxonomicConcept) and Dublin Core Terms FileFormat. Second, to guarantee a concept to be used as a UCO MIME type has exactly one skos:notation. Note that strict SHACL enforcement of the skos:notation presence is not within the UCO Types ontology, but is instead a part of the shapes provided by the UCO MIME Taxonomy. The warning about skos:notation in the Observable namespace is deactivated on importing the taxonomy's shapes."@en ; + rdfs:seeAlso observable:mimeType-notation ; + . + types:NativeFormatString a rdfs:Datatype ; rdfs:comment "Specifies data in its native format of some external language. The data may be encoded in Base64 per [RFC4648]. Data encoded in Base64 must be denoted as such using the encoded property."@en ; . +types:NonIANAMediaType + a owl:Class ; + rdfs:subClassOf types:MIMEFormat ; + rdfs:label "NonIANAMediaType"@en ; + owl:disjointWith types:IANAMediaType ; + . + types:StructuredText a rdfs:Datatype ; rdfs:comment "Expresses string-based data in some information structuring format (e.g., HTML5)."@en ; diff --git a/tests/examples/Makefile b/tests/examples/Makefile index 2af81c99..9f052c82 100644 --- a/tests/examples/Makefile +++ b/tests/examples/Makefile @@ -29,6 +29,9 @@ all: \ location_XFAIL_validation.ttl \ message_thread_PASS_validation.ttl \ message_thread_XFAIL_validation.ttl \ + mime_PASS_validation.ttl \ + mime_XFAIL_validation.ttl \ + mime_prefix_PASS_validation.ttl \ owl_axiom_PASS_validation.ttl \ owl_axiom_XFAIL_validation.ttl \ owl_properties_PASS_validation.ttl \ @@ -90,6 +93,9 @@ check: \ location_XFAIL_validation.ttl \ message_thread_PASS_validation.ttl \ message_thread_XFAIL_validation.ttl \ + mime_PASS_validation.ttl \ + mime_XFAIL_validation.ttl \ + mime_prefix_PASS_validation.ttl \ owl_axiom_PASS_validation.ttl \ owl_axiom_XFAIL_validation.ttl \ owl_properties_PASS_validation.ttl \ diff --git a/tests/examples/mime_PASS.json b/tests/examples/mime_PASS.json new file mode 100644 index 00000000..ad0fbcea --- /dev/null +++ b/tests/examples/mime_PASS.json @@ -0,0 +1,152 @@ +{ + "@context": { + "core": "https://ontology.unifiedcyberontology.org/uco/core/", + "dcterms": "http://purl.org/dc/terms/", + "kb": "http://example.org/kb/", + "observable": "https://ontology.unifiedcyberontology.org/uco/observable/", + "rdfs": "http://www.w3.org/2000/01/rdf-schema#", + "skos": "http://www.w3.org/2004/02/skos/core#", + "types": "https://ontology.unifiedcyberontology.org/uco/types/" + }, + "@graph": [ + { + "@id": "urn:example:mime:dcterms:application/gzip", + "@type": "dcterms:FileFormat", + "rdfs:comment": "This is a custom media type individual, designed for just this unit test. A larger taxonomy of individuals should be used outside of testing contexts.", + "skos:notation": "application/gzip" + }, + { + "@id": "urn:example:mime:uco:application/gzip", + "@type": "types:IANAMediaType", + "rdfs:comment": "This is a custom media type individual, designed for just this unit test. A larger taxonomy of individuals should be used outside of testing contexts.", + "skos:exactMatch": { + "@id": "urn:example:mime:dcterms:application/gzip" + }, + "skos:notation": "application/gzip" + }, + { + "@id": "urn:example:mime:uco:application/tar", + "@type": "types:NonIANAMediaType", + "rdfs:comment": "This is a custom media type individual, designed for just this unit test. A larger taxonomy of individuals should be used outside of testing contexts.", + "skos:notation": "application/tar" + }, + { + "@id": "urn:example:mime:uco:application/tar+gzip", + "@type": "types:NonIANAMediaType", + "rdfs:comment": "This is a custom media type individual, designed for just this unit test. A larger taxonomy of individuals should be used outside of testing contexts.", + "skos:broader": [ + { + "@id": "urn:example:mime:uco:application/gzip" + }, + { + "@id": "urn:example:mime:uco:application/tar" + } + ], + "skos:notation": "application/tar+gzip" + }, + { + "@id": "urn:example:mime:uco:image/example.image.type.without.notation", + "@type": "types:NonIANAMediaType", + "rdfs:comment": "This is a custom media type individual, designed for just this unit test. A larger taxonomy of individuals should be used outside of testing contexts." + }, + { + "@id": "kb:file-1", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": { + "@id": "urn:example:mime:dcterms:application/gzip" + } + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "1.gz" + } + ], + "rdfs:comment": "This file node should trigger an sh:Info-severity result." + }, + { + "@id": "kb:file-2", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": { + "@id": "urn:example:mime:uco:application/gzip" + } + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "2.gz" + } + ] + }, + { + "@id": "kb:file-3", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": { + "@id": "urn:example:mime:uco:application/tar" + } + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "3.tar" + } + ] + }, + { + "@id": "kb:file-4", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": { + "@id": "urn:example:mime:uco:application/tar+gzip" + } + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "4.tar.gz" + } + ] + }, + { + "@id": "kb:file-5", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": { + "@id": "urn:example:mime:uco:image/example.image.type.without.notation" + } + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "5.dat" + } + ], + "rdfs:comment": "This file node should trigger an sh:Warning-severity result." + }, + { + "@id": "kb:file-6", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": { + "@id": "urn:example:mime:uco:image/example.image.type.without.notation" + } + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "6.dat" + } + ], + "rdfs:comment": "This file node should trigger an sh:Warning-severity result." + } + ] +} diff --git a/tests/examples/mime_PASS_validation.ttl b/tests/examples/mime_PASS_validation.ttl new file mode 100644 index 00000000..98fae107 --- /dev/null +++ b/tests/examples/mime_PASS_validation.ttl @@ -0,0 +1,37 @@ +@prefix observable: . +@prefix owl: . +@prefix rdf: . +@prefix rdfs: . +@prefix sh: . +@prefix skos: . +@prefix xsd: . + +[] + a sh:ValidationReport ; + sh:conforms "true"^^xsd:boolean ; + sh:result + [ + a sh:ValidationResult ; + sh:focusNode ; + sh:resultMessage "The used mimeType value is not a concept with a skos:notation. Some consumers of this data expect a string with the MIME 'type/subtype' format to be supplied with skos:notation. Please either add the skos:notation to your input graph or incorporate the UCO MIME Taxonomy."@en ; + sh:resultPath skos:notation ; + sh:resultSeverity sh:Warning ; + sh:sourceConstraintComponent sh:MinCountConstraintComponent ; + sh:sourceShape observable:mimeType-notation ; + ] , + [ + a sh:ValidationResult ; + sh:focusNode [ + a observable:ContentDataFacet ; + observable:mimeType ; + ] ; + sh:resultMessage "Value is not an instance of types:MIMEFormat or one of its subclasses. Please consider using a value having type types:IANAMediaType or types:NonIANAMediaType."@en ; + sh:resultPath observable:mimeType ; + sh:resultSeverity sh:Info ; + sh:sourceConstraintComponent sh:ClassConstraintComponent ; + sh:sourceShape observable:mimeType-class-types-MIMEFormat ; + sh:value ; + ] + ; + . + diff --git a/tests/examples/mime_XFAIL.json b/tests/examples/mime_XFAIL.json new file mode 100644 index 00000000..6f86ea64 --- /dev/null +++ b/tests/examples/mime_XFAIL.json @@ -0,0 +1,28 @@ +{ + "@context": { + "core": "https://ontology.unifiedcyberontology.org/uco/core/", + "dcterms": "http://purl.org/dc/terms/", + "kb": "http://example.org/kb/", + "observable": "https://ontology.unifiedcyberontology.org/uco/observable/", + "rdfs": "http://www.w3.org/2000/01/rdf-schema#", + "skos": "http://www.w3.org/2004/02/skos/core#", + "types": "https://ontology.unifiedcyberontology.org/uco/types/" + }, + "@graph": [ + { + "@id": "kb:file-7", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": "application/gzip" + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "7.gz" + } + ], + "rdfs:comment": "This file node errantly uses a literal instead of object reference." + } + ] +} diff --git a/tests/examples/mime_XFAIL_validation.ttl b/tests/examples/mime_XFAIL_validation.ttl new file mode 100644 index 00000000..d4d56dcb --- /dev/null +++ b/tests/examples/mime_XFAIL_validation.ttl @@ -0,0 +1,72 @@ +@prefix dcterms: . +@prefix observable: . +@prefix owl: . +@prefix rdf: . +@prefix rdfs: . +@prefix sh: . +@prefix skos: . +@prefix xsd: . + +[] + a sh:ValidationReport ; + sh:conforms "false"^^xsd:boolean ; + sh:result + [ + a sh:ValidationResult ; + sh:focusNode "application/gzip" ; + sh:resultMessage "The used mimeType value is not a concept with a skos:notation. Some consumers of this data expect a string with the MIME 'type/subtype' format to be supplied with skos:notation. Please either add the skos:notation to your input graph or incorporate the UCO MIME Taxonomy."@en ; + sh:resultPath skos:notation ; + sh:resultSeverity sh:Warning ; + sh:sourceConstraintComponent sh:MinCountConstraintComponent ; + sh:sourceShape observable:mimeType-notation ; + ] , + [ + a sh:ValidationResult ; + sh:focusNode [ + a observable:ContentDataFacet ; + observable:mimeType "application/gzip" ; + ] ; + sh:resultMessage "Value does not have class dcterms:FileFormat" ; + sh:resultPath observable:mimeType ; + sh:resultSeverity sh:Violation ; + sh:sourceConstraintComponent sh:ClassConstraintComponent ; + sh:sourceShape [ + sh:class dcterms:FileFormat ; + sh:nodeKind sh:IRI ; + sh:path observable:mimeType ; + ] ; + sh:value "application/gzip" ; + ] , + [ + a sh:ValidationResult ; + sh:focusNode [ + a observable:ContentDataFacet ; + observable:mimeType "application/gzip" ; + ] ; + sh:resultMessage "Value is not an instance of types:MIMEFormat or one of its subclasses. Please consider using a value having type types:IANAMediaType or types:NonIANAMediaType."@en ; + sh:resultPath observable:mimeType ; + sh:resultSeverity sh:Info ; + sh:sourceConstraintComponent sh:ClassConstraintComponent ; + sh:sourceShape observable:mimeType-class-types-MIMEFormat ; + sh:value "application/gzip" ; + ] , + [ + a sh:ValidationResult ; + sh:focusNode [ + a observable:ContentDataFacet ; + observable:mimeType "application/gzip" ; + ] ; + sh:resultMessage "Value is not of Node Kind sh:IRI" ; + sh:resultPath observable:mimeType ; + sh:resultSeverity sh:Violation ; + sh:sourceConstraintComponent sh:NodeKindConstraintComponent ; + sh:sourceShape [ + sh:class dcterms:FileFormat ; + sh:nodeKind sh:IRI ; + sh:path observable:mimeType ; + ] ; + sh:value "application/gzip" ; + ] + ; + . + diff --git a/tests/examples/mime_prefix_PASS.json b/tests/examples/mime_prefix_PASS.json new file mode 100644 index 00000000..047ba475 --- /dev/null +++ b/tests/examples/mime_prefix_PASS.json @@ -0,0 +1,36 @@ +{ + "@context": { + "core": "https://ontology.unifiedcyberontology.org/uco/core/", + "ex-mime": "urn:example:mime:custom:", + "kb": "http://example.org/kb/", + "observable": "https://ontology.unifiedcyberontology.org/uco/observable/", + "observable:mimeType": { + "@type": "@id" + }, + "rdfs": "http://www.w3.org/2000/01/rdf-schema#", + "skos": "http://www.w3.org/2004/02/skos/core#", + "types": "https://ontology.unifiedcyberontology.org/uco/types/" + }, + "@graph": [ + { + "@id": "ex-mime:application/gzip", + "@type": "types:IANAMediaType", + "rdfs:comment": "This is a custom media type individual, designed for just this unit test. A larger taxonomy of individuals should be used outside of testing contexts.", + "skos:notation": "application/gzip" + }, + { + "@id": "kb:file-8", + "@type": "observable:File", + "core:hasFacet": [ + { + "@type": "observable:ContentDataFacet", + "observable:mimeType": "ex-mime:application/gzip" + }, + { + "@type": "observable:FileFacet", + "observable:fileName": "8.gz" + } + ] + } + ] +} diff --git a/tests/examples/mime_prefix_PASS_validation.ttl b/tests/examples/mime_prefix_PASS_validation.ttl new file mode 100644 index 00000000..33496ff0 --- /dev/null +++ b/tests/examples/mime_prefix_PASS_validation.ttl @@ -0,0 +1,11 @@ +@prefix owl: . +@prefix rdf: . +@prefix rdfs: . +@prefix sh: . +@prefix xsd: . + +[] + a sh:ValidationReport ; + sh:conforms "true"^^xsd:boolean ; + . + diff --git a/tests/examples/test_mime.py b/tests/examples/test_mime.py new file mode 100644 index 00000000..822f5648 --- /dev/null +++ b/tests/examples/test_mime.py @@ -0,0 +1,98 @@ +#!/usr/bin/env python3 + +# This software was developed at the National Institute of Standards +# and Technology by employees of the Federal Government in the course +# of their official duties. Pursuant to title 17 Section 105 of the +# United States Code this software is not subject to copyright +# protection and is in the public domain. NIST assumes no +# responsibility whatsoever for its use by other parties, and makes +# no guarantees, expressed or implied, about its quality, +# reliability, or any other characteristic. +# +# We would appreciate acknowledgement if the software is used. + +import typing + +import pytest +import rdflib + +NS_UCO_CORE = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/core/") +NS_UCO_OBSERVABLE = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/observable/") + +NSDICT = { + "core": NS_UCO_CORE, + "observable": NS_UCO_OBSERVABLE, + "skos": rdflib.SKOS +} + +@pytest.fixture +def mime_pass_graph() -> rdflib.Graph: + graph = rdflib.Graph() + graph.parse("mime_PASS.json", format="json-ld") + return graph + + +def test_mime_file_names(mime_pass_graph: rdflib.Graph) -> None: + expected: typing.Set[str] = { + "1.gz", + "2.gz", + "3.tar", + "4.tar.gz", + "5.dat", + "6.dat", + } + computed: typing.Set[str] = set() + + query = rdflib.plugins.sparql.prepareQuery("""\ +SELECT ?lFileName +WHERE { + ?nFile core:hasFacet/observable:fileName ?lFileName . +} +""", initNs=NSDICT) + for result in mime_pass_graph.query(query): + computed.add(str(result[0])) + assert expected == computed + + +def test_mime_gzip_files(mime_pass_graph: rdflib.Graph) -> None: + expected: typing.Set[str] = { + "1.gz", + "2.gz", + "4.tar.gz", + } + computed: typing.Set[str] = set() + + query = rdflib.plugins.sparql.prepareQuery("""\ +SELECT ?lFileName +WHERE { + ?nFile core:hasFacet/observable:fileName ?lFileName . + ?nFile core:hasFacet/observable:mimeType ?nMimeType . + + ?nMimeType skos:exactMatch*/skos:broader*/skos:notation "application/gzip" . +} +""", initNs=NSDICT) + for result in mime_pass_graph.query(query): + computed.add(str(result[0])) + assert expected == computed + + + +def test_mime_tar_files(mime_pass_graph: rdflib.Graph) -> None: + expected: typing.Set[str] = { + "3.tar", + "4.tar.gz", + } + computed: typing.Set[str] = set() + + query = rdflib.plugins.sparql.prepareQuery("""\ +SELECT ?lFileName +WHERE { + ?nFile core:hasFacet/observable:fileName ?lFileName . + ?nFile core:hasFacet/observable:mimeType ?nMimeType . + + ?nMimeType skos:exactMatch*/skos:broader*/skos:notation "application/tar" . +} +""", initNs=NSDICT) + for result in mime_pass_graph.query(query): + computed.add(str(result[0])) + assert expected == computed diff --git a/tests/examples/test_validation.py b/tests/examples/test_validation.py index 30addef8..b8e48922 100644 --- a/tests/examples/test_validation.py +++ b/tests/examples/test_validation.py @@ -30,10 +30,12 @@ NS_CO = rdflib.Namespace("http://purl.org/co/") NS_SH = rdflib.SH +NS_SKOS = rdflib.SKOS NS_UCO_ACTION = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/action/") NS_UCO_CO = rdflib.Namespace("https://ontology.unifiedcyberontology.org/co/") NS_UCO_CORE = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/core/") NS_UCO_LOCATION = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/location/") +NS_UCO_OBSERVABLE = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/observable/") NS_UCO_TYPES = rdflib.Namespace("https://ontology.unifiedcyberontology.org/uco/types/") NSDICT = {"sh": NS_SH} @@ -320,6 +322,33 @@ def test_message_thread_PASS_validation(): def test_message_thread_XFAIL_validation(): confirm_validation_results("message_thread_XFAIL_validation.ttl", False) +def test_mime_PASS_validation() -> None: + confirm_validation_results( + "mime_PASS_validation.ttl", + True, + expected_result_paths={ + str(NS_SKOS.notation), + str(NS_UCO_OBSERVABLE.mimeType) + } + ) + +def test_mime_XFAIL_validation() -> None: + confirm_validation_results( + "mime_XFAIL_validation.ttl", + False, + expected_result_paths={ + str(NS_SKOS.notation), + str(NS_UCO_OBSERVABLE.mimeType) + } + ) + +def test_mime_prefix_PASS_validation() -> None: + confirm_validation_results( + "mime_prefix_PASS_validation.ttl", + True, + expected_focus_node_severities=set() + ) + def test_owl_axiom_PASS() -> None: confirm_validation_results( "owl_axiom_PASS_validation.ttl",