@prefix dash: <http://datashapes.org/dash#> .
@prefix ns1: <http://purl.org/pav/> .
@prefix owl: <http://www.w3.org/2002/07/owl#> .
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .
@prefix sh: <http://www.w3.org/ns/shacl#> .
@prefix tosh: <http://topbraid.org/tosh#> .
@prefix xsd: <http://www.w3.org/2001/XMLSchema#> .

dash:Editor a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Editor" ;
    rdfs:comment "The class of widgets for editing value nodes." ;
    rdfs:subClassOf dash:Widget .

dash:ExecutionPlatform a rdfs:Class ;
    rdfs:label "Execution platform" ;
    rdfs:comment "An platform (such as TopBraid) that may have features needed to execute, for example, SPARQL queries." ;
    rdfs:subClassOf rdfs:Resource .

dash:FailureResult a rdfs:Class ;
    rdfs:label "Failure result" ;
    rdfs:comment "A result representing a validation failure such as an unsupported recursion." ;
    rdfs:subClassOf sh:AbstractResult .

dash:FailureTestCaseResult a rdfs:Class ;
    rdfs:label "Failure test case result" ;
    rdfs:comment "Represents a failure of a test case." ;
    rdfs:subClassOf dash:TestCaseResult .

dash:FunctionTestCase a rdfs:Class ;
    rdfs:label "Function test case" ;
    rdfs:comment "A test case that verifies that a given SPARQL expression produces a given, expected result." ;
    rdfs:subClassOf dash:TestCase ;
    sh:property [ a sh:PropertyShape ;
            sh:description "The expected result of a function call." ;
            sh:maxCount 1 ;
            sh:name "expected result" ;
            sh:path dash:expectedResult ],
        [ a sh:PropertyShape ;
            sh:description "A valid SPARQL expression calling the function to test." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:name "expression" ;
            sh:path dash:expression ] .

dash:GraphStoreTestCase a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Graph store test case" ;
    rdfs:comment "A test case that can be used to verify that an RDF file could be loaded (from a file) and that the resulting RDF graph is equivalent to a given TTL file." ;
    rdfs:subClassOf dash:TestCase ;
    sh:property [ a sh:PropertyShape ;
            sh:datatype xsd:string ;
            sh:description "The expected RDF graph, as a Turtle string." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:path dash:expectedResult ],
        [ a sh:PropertyShape ;
            sh:datatype xsd:anyURI ;
            sh:description "The URI of the graph to load." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:name "uri" ;
            sh:path dash:uri ] .

dash:GraphUpdate a rdfs:Class ;
    rdfs:label "Graph update" ;
    rdfs:comment "A suggestion consisting of added and/or deleted triples, represented as rdf:Statements via dash:addedTriple and dash:deletedTriple." ;
    rdfs:subClassOf dash:Suggestion .

dash:GraphValidationTestCase a rdfs:Class ;
    rdfs:label "Graph validation test case" ;
    rdfs:comment "A test case that performs SHACL constraint validation on the whole graph and compares the results with the expected validation results stored with the test case. By default this excludes meta-validation (i.e. the validation of the shape definitions themselves). If that's desired, set dash:validateShapes to true." ;
    rdfs:subClassOf dash:ValidationTestCase .

dash:InferencingTestCase a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Inferencing test case" ;
    rdfs:comment "A test case to verify whether an inferencing engine is producing identical results to those stored as expected results." ;
    rdfs:subClassOf dash:TestCase ;
    sh:property [ a sh:PropertyShape ;
            sh:description "The expected inferred triples, represented by instances of rdfs:Statement." ;
            sh:name "expected result" ;
            sh:path dash:expectedResult ] .

dash:JSTestCase a rdfs:Class ;
    rdfs:label "JavaScript test case" ;
    rdfs:comment "A test case that calls a given JavaScript function like a sh:JSFunction and compares its result with the dash:expectedResult." ;
    rdfs:subClassOf dash:TestCase,
        sh:JSFunction ;
    sh:property [ a sh:PropertyShape ;
            sh:description "The expected result of the JavaScript function call, as an RDF node." ;
            sh:maxCount 1 ;
            sh:name "expected result" ;
            sh:path dash:expectedResult ] .

dash:QueryTestCase a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Query test case" ;
    rdfs:comment "A test case running a given SPARQL SELECT query and comparing its results with those stored as JSON Result Set in the expected result property." ;
    rdfs:subClassOf dash:TestCase,
        sh:SPARQLSelectExecutable ;
    sh:property [ a sh:PropertyShape ;
            sh:datatype xsd:string ;
            sh:description "The expected result set, as a JSON string." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:name "expected result" ;
            sh:path dash:expectedResult ],
        [ a sh:PropertyShape ;
            sh:datatype xsd:string ;
            sh:description "The SPARQL SELECT query to execute." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:name "SPARQL query" ;
            sh:path sh:select ] .

dash:SPARQLConstructTemplate a rdfs:Class ;
    rdfs:label "SPARQL CONSTRUCT template" ;
    rdfs:comment "Encapsulates one or more SPARQL CONSTRUCT queries that can be parameterized. Parameters will become pre-bound variables in the queries." ;
    rdfs:subClassOf sh:Parameterizable,
        sh:SPARQLConstructExecutable .

dash:SPARQLSelectTemplate a rdfs:Class ;
    rdfs:label "SPARQL SELECT template" ;
    rdfs:comment "Encapsulates a SPARQL SELECT query that can be parameterized. Parameters will become pre-bound variables in the query." ;
    rdfs:subClassOf sh:Parameterizable,
        sh:SPARQLSelectExecutable .

dash:SPARQLUpdateSuggestionGenerator a rdfs:Class ;
    rdfs:label "SPARQL UPDATE suggestion generator" ;
    rdfs:comment """A SuggestionGenerator based on a SPARQL UPDATE query (sh:update), producing an instance of dash:GraphUpdate. The INSERTs become dash:addedTriple and the DELETEs become dash:deletedTriple. The WHERE clause operates on the data graph with the pre-bound variables $subject, $predicate and $object, as well as the other pre-bound variables for the parameters of the constraint.

In many cases, there may be multiple possible suggestions to fix a problem. For example, with sh:maxLength there are many ways to slice a string. In those cases, the system will first iterate through the result variables from a SELECT query (sh:select) and apply these results as pre-bound variables into the UPDATE query.""" ;
    rdfs:subClassOf dash:SuggestionGenerator,
        sh:SPARQLSelectExecutable,
        sh:SPARQLUpdateExecutable .

dash:SuccessResult a rdfs:Class ;
    rdfs:label "Success result" ;
    rdfs:comment "A result representing a successfully validated constraint." ;
    rdfs:subClassOf sh:AbstractResult .

dash:SuccessTestCaseResult a rdfs:Class ;
    rdfs:label "Success test case result" ;
    rdfs:comment "Represents a successful run of a test case." ;
    rdfs:subClassOf dash:TestCaseResult .

dash:Suggestion a rdfs:Class ;
    rdfs:label "Suggestion" ;
    dash:abstract true ;
    rdfs:comment "Base class of suggestions that modify a graph to \"fix\" the source of a validation result." ;
    rdfs:subClassOf rdfs:Resource .

dash:SuggestionGenerator a rdfs:Class ;
    rdfs:label "Suggestion generator" ;
    dash:abstract true ;
    rdfs:comment "Base class of objects that can generate suggestions (added or deleted triples) for a validation result of a given constraint component." ;
    rdfs:subClassOf rdfs:Resource .

dash:SuggestionResult a rdfs:Class ;
    rdfs:label "Suggestion result" ;
    rdfs:comment "Class of results that have been produced as suggestions, not through SHACL validation. How the actual results are produced is up to implementers. Each instance of this class should have values for sh:focusNode, sh:resultMessage, sh:resultSeverity (suggested default: sh:Info), and dash:suggestion to point at one or more suggestions." ;
    rdfs:subClassOf sh:AbstractResult .

dash:TestCase a rdfs:Class ;
    rdfs:label "Test case" ;
    dash:abstract true ;
    rdfs:comment "A test case to verify that a (SHACL-based) feature works as expected." ;
    rdfs:subClassOf rdfs:Resource ;
    sh:property [ sh:datatype xsd:boolean ;
            sh:description "If set to true, this test case will be skipped." ;
            sh:maxCount 1 ;
            sh:name "deactivated" ;
            sh:path sh:deactivated ] .

dash:TestCaseResult a rdfs:Class ;
    rdfs:label "Test case result" ;
    dash:abstract true ;
    rdfs:comment "Base class for results produced by running test cases." ;
    rdfs:subClassOf sh:AbstractResult ;
    sh:property [ a sh:PropertyShape ;
            sh:class dash:TestCase ;
            sh:description "The dash:TestCase that was executed." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:name "test case" ;
            sh:path dash:testCase ],
        [ a sh:PropertyShape ;
            sh:class rdfs:Resource ;
            sh:description "The graph containing the test case." ;
            sh:maxCount 1 ;
            sh:minCount 1 ;
            sh:name "test graph" ;
            sh:nodeKind sh:IRI ;
            sh:path dash:testGraph ] .

dash:TestEnvironment a rdfs:Class ;
    rdfs:label "Test environment" ;
    dash:abstract true ;
    rdfs:comment "Abstract base class for test environments, holding information on how to set up a test case." ;
    rdfs:subClassOf rdfs:Resource .

dash:ValidationTestCase a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Validation test case" ;
    dash:abstract true ;
    rdfs:comment "Abstract superclass for test cases concerning SHACL constraint validation. Future versions may add new kinds of validatin test cases, e.g. to validate a single resource only." ;
    rdfs:subClassOf dash:TestCase ;
    sh:property [ a sh:PropertyShape ;
            sh:class sh:ValidationReport ;
            sh:description "The expected validation report." ;
            sh:name "expected result" ;
            sh:path dash:expectedResult ] .

dash:Viewer a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Viewer" ;
    rdfs:comment "The class of widgets for viewing value nodes." ;
    rdfs:subClassOf dash:Widget .

dash:Widget a rdfs:Class,
        sh:NodeShape ;
    rdfs:label "Widget" ;
    dash:abstract true ;
    rdfs:comment "Base class of user interface components that can be used to display or edit value nodes." ;
    rdfs:subClassOf rdfs:Resource .

owl:Class a rdfs:Class ;
    rdfs:subClassOf rdfs:Class .

dash:AllObjects a dash:AllObjectsTarget ;
    rdfs:label "All objects" ;
    rdfs:comment "A reusable instance of dash:AllObjectsTarget." .

dash:AllSubjects a dash:AllSubjectsTarget ;
    rdfs:label "All subjects" ;
    rdfs:comment "A reusable instance of dash:AllSubjectsTarget." .

dash:AutoCompleteEditor a dash:Editor ;
    rdfs:label "Auto-complete editor" ;
    rdfs:comment "An auto-complete field to enter the label of instances of a class. This is the fallback editor for any URI resource if no other editors are more suitable." .

dash:BlankNodeViewer a dash:Viewer ;
    rdfs:label "Blank Node Viewer" ;
    rdfs:comment "A Viewer for blank nodes, rendering as the label of the blank node." .

dash:BooleanSelectEditor a dash:Editor ;
    rdfs:label "Boolean select editor" ;
    rdfs:comment """An editor for boolean literals, rendering as a select box with values true and false.

Also displays the current value (such as "1"^^xsd:boolean), but only allows to switch to true or false.""" .

dash:ClosedByTypesConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Closed by types constraint component" ;
    rdfs:comment "A constraint component that can be used to declare that focus nodes are \"closed\" based on their rdf:types, meaning that focus nodes may only have values for the properties that are explicitly enumerated via sh:property/sh:path in property constraints at their rdf:types and the superclasses of those. This assumes that the type classes are also shapes." ;
    sh:nodeValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateClosedByTypesNode" ;
            sh:jsLibrary dash:DASHJSLibrary ;
            sh:message "Property is not among those permitted for any of the types" ],
        [ a sh:SPARQLSelectValidator ;
            sh:message "Property {?path} is not among those permitted for any of the types" ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT $this (?predicate AS ?path) ?value
WHERE {
	FILTER ($closedByTypes) .
    $this ?predicate ?value .
	FILTER (?predicate != rdf:type) .
	FILTER NOT EXISTS {
		$this rdf:type ?type .
		?type rdfs:subClassOf* ?class .
		GRAPH $shapesGraph {
			?class sh:property/sh:path ?predicate .
		}
	}
}""" ] ;
    sh:parameter dash:ClosedByTypesConstraintComponent-closedByTypes ;
    sh:targetClass sh:NodeShape .

dash:CoExistsWithConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Co-exists-with constraint component" ;
    dash:localConstraint true ;
    rdfs:comment "A constraint component that can be used to express a constraint on property shapes so that if the property path has any value then the given property must also have a value, and vice versa." ;
    sh:message "Values must co-exist with values of {$coExistsWith}" ;
    sh:parameter dash:CoExistsWithConstraintComponent-coExistsWith ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateCoExistsWith" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT $this
WHERE {
	{
    	FILTER (EXISTS { $this $PATH ?any } && NOT EXISTS { $this $coExistsWith ?any })
	}
	UNION
	{
    	FILTER (NOT EXISTS { $this $PATH ?any } && EXISTS { $this $coExistsWith ?any })
	}
}""" ] ;
    sh:targetClass sh:PropertyShape .

dash:DateOrDateTime a rdf:List ;
    rdfs:label "Date or date time" ;
    rdf:first [ sh:datatype xsd:date ] ;
    rdf:rest ( [ sh:datatype xsd:dateTime ] ) ;
    rdfs:comment "An rdf:List that can be used in property constraints as value for sh:or to indicate that all values of a property must be either xsd:date or xsd:dateTime." .

dash:DatePickerEditor a dash:Editor ;
    rdfs:label "Date picker editor" ;
    rdfs:comment "An editor for xsd:date literals, offering a calendar-like date picker." .

dash:DefaultValueTypeRule a sh:SPARQLConstructExecutable ;
    rdfs:label "default value type inference rule" ;
    rdfs:comment """
		A resource encapsulating a query that can be used to construct rdf:type triples for certain untyped nodes
		that are an object in a triple where the predicate has a sh:defaultValueType.
		This can be used as a pre-processor for shape graphs before they are validated.
		"""^^rdf:HTML ;
    sh:construct """
		CONSTRUCT {
			?node a ?defaultValueType .
		}
		WHERE {
			?predicate sh:defaultValueType ?defaultValueType .
			?anySubject ?predicate ?node .
			FILTER (NOT EXISTS { ?node a ?anyType }) .
		}
		""" .

dash:DetailsViewer a dash:Viewer ;
    rdfs:label "Details Viewer" ;
    rdfs:comment "A Viewer for resources that shows the details of the value using its default view shape as a nested form-like display." .

dash:EnumSelectEditor a dash:Editor ;
    rdfs:label "Enum select editor" ;
    rdfs:comment "A drop-down editor for enumerated values (typically based on sh:in lists)." .

dash:HTMLOrStringOrLangString a rdf:List ;
    rdfs:label "HTML or string or langString" ;
    rdf:first [ sh:datatype rdf:HTML ] ;
    rdf:rest ( [ sh:datatype xsd:string ] [ sh:datatype rdf:langString ] ) ;
    rdfs:comment "An rdf:List that can be used in property constraints as value for sh:or to indicate that all values of a property must be either rdf:HTML, xsd:string or rdf:langString." .

dash:HTMLViewer a dash:Viewer ;
    rdfs:label "HTML Viewer" ;
    rdfs:comment "A Viewer for HTML encoded text from rdf:HTML literals, rendering as parsed HTML DOM elements. Also displays the language if the HTML has a lang attribute on its root DOM element." .

dash:HasValueWithClassConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Has value with class constraint component" ;
    rdfs:comment "A constraint component that can be used to express a constraint on property shapes so that one of the values of the property path must be an instance of a given class." ;
    sh:message "At least one of the values must be an instance of class {$hasValueWithClass}" ;
    sh:parameter dash:HasValueWithClassConstraintComponent-hasValueWithClass ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateHasValueWithClass" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT $this
WHERE {
	FILTER NOT EXISTS {
    	$this $PATH ?value .
		?value a ?type .
		?type rdfs:subClassOf* ?hasValueWithClass .
	}
}""" ] ;
    sh:targetClass sh:PropertyShape .

dash:HyperlinkViewer a dash:Viewer ;
    rdfs:label "Hyperlink Viewer" ;
    rdfs:comment """A Viewer for literals, rendering as a hyperlink to a URL.

For literals it assumes the lexical form is the URL.

This is often used as default viewer for xsd:anyURI literals. Unsupported for blank nodes.""" .

dash:ImageViewer a dash:Viewer ;
    rdfs:label "Image Viewer" ;
    rdfs:comment "A Viewer for URI values that are recognized as images by a browser, rendering as an image." .

dash:InstancesSelectEditor a dash:Editor ;
    rdfs:label "Instances select editor" ;
    rdfs:comment "A drop-down editor for all instances of the target class (based on sh:class of the property)." .

dash:LabelViewer a dash:Viewer ;
    rdfs:label "Label Viewer" ;
    rdfs:comment "A Viewer for URI resources, rendering as a hyperlink to that URI based on the display label of the resource. Also includes other ways of interacting with the URI such as opening a nested summary display." .

dash:LangStringViewer a dash:Viewer ;
    rdfs:label "LangString Viewer" ;
    rdfs:comment "A Viewer for literals with a language tag, rendering as the text plus a language indicator." .

dash:ListShape a sh:NodeShape ;
    rdfs:label "List shape" ;
    rdfs:comment """Defines constraints on what it means for a node to be a well-formed RDF list.

The focus node must either be rdf:nil or not recursive. Furthermore, this shape uses dash:ListNodeShape as a "helper" to walk through all members of the whole list (including itself).""" ;
    sh:or ( [ sh:hasValue () ] [ sh:not [ sh:hasValue () ] ;
                sh:property [ dash:nonRecursive true ;
                        sh:path [ sh:oneOrMorePath rdf:rest ] ] ] ) ;
    sh:property [ rdfs:comment "Each list member (including this node) must be have the shape dash:ListNodeShape." ;
            sh:node dash:ListNodeShape ;
            sh:path [ sh:zeroOrMorePath rdf:rest ] ] .

dash:LiteralViewer a dash:Viewer ;
    rdfs:label "Literal Viewer" ;
    rdfs:comment "A simple viewer for literals, rendering the lexical form of the value." .

dash:NonRecursiveConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Non-recursive constraint component" ;
    rdfs:comment """Used to state that a property or path must not point back to itself.

For example, "a person cannot have itself as parent" can be expressed by setting dash:nonRecursive=true for a given sh:path.

To express that a person cannot have itself among any of its (recursive) parents, use a sh:path with the + operator such as ex:parent+.""" ;
    sh:message "Points back at itself (recursively)" ;
    sh:parameter dash:NonRecursiveConstraintComponent-nonRecursive ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateNonRecursiveProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT DISTINCT $this ($this AS ?value)
WHERE {
	{
		FILTER (?nonRecursive)
	}
    $this $PATH $this .
}""" ] ;
    sh:targetClass sh:PropertyShape .

dash:None a sh:NodeShape ;
    rdfs:label "None" ;
    rdfs:comment "A Shape that is no node can conform to." ;
    sh:in () .

dash:ParameterConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Parameter constraint component"@en ;
    rdfs:comment "A constraint component that can be used to verify that all value nodes conform to the given Parameter."@en ;
    sh:parameter dash:ParameterConstraintComponent-parameter .

dash:PrimaryKeyConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Primary key constraint component" ;
    dash:localConstraint true ;
    rdfs:comment "Enforces a constraint that the given property (sh:path) serves as primary key for all resources in the target of the shape. If a property has been declared to be the primary key then each resource must have exactly one value for that property. Furthermore, the URIs of those resources must start with a given string (dash:uriStart), followed by the URL-encoded primary key value. For example if dash:uriStart is \"http://example.org/country-\" and the primary key for an instance is \"de\" then the URI must be \"http://example.org/country-de\". Finally, as a result of the URI policy, there can not be any other resource with the same value under the same primary key policy." ;
    sh:labelTemplate "The property {?predicate} is the primary key and URIs start with {?uriStart}" ;
    sh:message "Violation of primary key constraint" ;
    sh:parameter dash:PrimaryKeyConstraintComponent-uriStart ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validatePrimaryKeyProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT DISTINCT $this
WHERE {
        FILTER (
			# Must have a value for the primary key
			NOT EXISTS { ?this $PATH ?any }
			||
			# Must have no more than one value for the primary key
			EXISTS {
				?this $PATH ?value1 .
				?this $PATH ?value2 .
				FILTER (?value1 != ?value2) .
			}
			||
			# The value of the primary key must align with the derived URI
			EXISTS {
				{
        			?this $PATH ?value .
					FILTER NOT EXISTS { ?this $PATH ?value2 . FILTER (?value != ?value2) }
				}
        		BIND (CONCAT($uriStart, ENCODE_FOR_URI(str(?value))) AS ?uri) .
        		FILTER (str(?this) != ?uri) .
    		}
		)
}""" ] ;
    sh:targetClass sh:PropertyShape .

dash:ReifiableByConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Reifiable-by constraint component" ;
    sh:labelTemplate "Reifiable by {$reifiableBy}" ;
    sh:parameter dash:ReifiableByConstraintComponent-reifiableBy .

dash:RichTextEditor a dash:Editor ;
    rdfs:label "Rich text editor" ;
    rdfs:comment "A rich text editor to enter the lexical value of a literal and a drop down to select language. The selected language is stored in the HTML lang attribute of the root node in the HTML DOM tree." .

dash:RootClassConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Root class constraint component" ;
    rdfs:comment "A constraint component defining the parameter dash:rootClass, which restricts the values to be either the root class itself or one of its subclasses. This is typically used in conjunction with properties that have rdfs:Class as their type." ;
    sh:labelTemplate "Root class {$rootClass}" ;
    sh:message "Value must be subclass of {$rootClass}" ;
    sh:parameter dash:RootClassConstraintComponent-rootClass ;
    sh:targetClass sh:PropertyShape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateRootClass" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasRootClass .

dash:SingleLineConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Single line constraint component" ;
    rdfs:comment """A constraint component that can be used to declare that all values that are literals must have a lexical form that contains no line breaks ('\\n' or '\\r').

User interfaces may use the dash:singleLine flag to prefer a text field over a (multi-line) text area.""" ;
    sh:message "Must not contain line breaks." ;
    sh:parameter [ a sh:Parameter ;
            sh:datatype xsd:boolean ;
            sh:description "True to state that the lexical form of literal value nodes must not contain any line breaks. False to state that line breaks are explicitly permitted." ;
            sh:group tosh:StringBasedConstraintPropertyGroup ;
            sh:name "single line" ;
            sh:path dash:singleLine ] ;
    sh:targetClass sh:PropertyShape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateSingleLine" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLAskValidator ;
            sh:ask """ASK {
    FILTER (!$singleLine || !isLiteral($value) || (!contains(str($value), '\\n') && !contains(str($value), '\\r')))
}""" ;
            sh:prefixes <http://datashapes.org/dash> ] .

dash:StemConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Stem constraint component"@en ;
    dash:staticConstraint true ;
    rdfs:comment "A constraint component that can be used to verify that every value node is an IRI and the IRI starts with a given string value."@en ;
    sh:labelTemplate "Value needs to have stem {$stem}" ;
    sh:message "Value does not have stem {$stem}" ;
    sh:parameter dash:StemConstraintComponent-stem ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateStem" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasStem .

dash:StringOrLangString a rdf:List ;
    rdfs:label "String or langString" ;
    rdf:first [ sh:datatype xsd:string ] ;
    rdf:rest ( [ sh:datatype rdf:langString ] ) ;
    rdfs:comment "An rdf:List that can be used in property constraints as value for sh:or to indicate that all values of a property must be either xsd:string or rdf:langString." .

dash:SubSetOfConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Sub set of constraint component" ;
    dash:localConstraint true ;
    rdfs:comment "A constraint component that can be used to state that the set of value nodes must be a subset of the value of a given property." ;
    sh:message "Must be one of the values of {$subSetOf}" ;
    sh:parameter dash:SubSetOfConstraintComponent-subSetOf ;
    sh:propertyValidator [ a sh:SPARQLAskValidator ;
            sh:ask """ASK {
    $this $subSetOf $value .
}""" ;
            sh:prefixes <http://datashapes.org/dash> ] ;
    sh:targetClass sh:PropertyShape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateSubSetOf" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

dash:SymmetricConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Symmetric constraint component" ;
    rdfs:comment "A contraint component for property shapes to validate that a property is symmetric. For symmetric properties, if A relates to B then B must relate to A." ;
    sh:message "Symmetric value expected" ;
    sh:parameter dash:SymmetricConstraintComponent-symmetric ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateSymmetric" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT $this ?value {
	FILTER ($symmetric) .
	$this $PATH ?value .
	FILTER NOT EXISTS {
    	?value $PATH $this .
	}
}""" ] ;
    sh:targetClass sh:PropertyShape .

dash:TextAreaEditor a dash:Editor ;
    rdfs:label "Text area editor" ;
    rdfs:comment "A multi-line text area to enter the value of a literal." .

dash:TextAreaWithLangEditor a dash:Editor ;
    rdfs:label "Text area with lang editor" ;
    rdfs:comment "A multi-line text area to enter the value of a literal and a drop down to select a language." .

dash:TextFieldEditor a dash:Editor ;
    rdfs:label "Text field editor" ;
    rdfs:comment """A simple input field to enter the value of a literal, without the ability to change language or datatype.

This is the fallback editor for any literal if no other editors are more suitable.""" .

dash:TextFieldWithLangEditor a dash:Editor ;
    rdfs:label "Text field with lang editor" ;
    rdfs:comment "A single-line input field to enter the value of a literal and a drop down to select language, which is mandatory unless xsd:string is among the permissible datatypes." .

dash:URIEditor a dash:Editor ;
    rdfs:label "URI editor" ;
    rdfs:comment "An input field to enter the URI of a resource, e.g. rdfs:seeAlso links or images." .

dash:URIViewer a dash:Viewer ;
    rdfs:label "URI Viewer" ;
    rdfs:comment "A Viewer for URI resources, rendering as a hyperlink to that URI. Also includes other ways of interacting with the URI such as opening a nested summary display." .

dash:UniqueValueForClassConstraintComponent a sh:ConstraintComponent ;
    rdfs:label "Unique value for class constraint component" ;
    dash:propertySuggestionGenerator tosh:DeleteTripleSuggestionGenerator ;
    rdfs:comment "A constraint component that can be used to state that the values of a property must be unique for all instances of a given class (and its subclasses)." ;
    sh:labelTemplate "Values must be unique among all instances of {?uniqueValueForClass}" ;
    sh:parameter dash:UniqueValueForClassConstraintComponent-uniqueValueForClass ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateUniqueValueForClass" ;
            sh:jsLibrary dash:DASHJSLibrary ;
            sh:message "Value {?value} must be unique but is also used by {?other}" ],
        [ a sh:SPARQLSelectValidator ;
            sh:message "Value {?value} must be unique but is also used by {?other}" ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """SELECT DISTINCT $this ?value ?other
WHERE {
	{
    	$this $PATH ?value .
		?other $PATH ?value .
		FILTER (?other != $this) .
	}
	?other a ?type .
	?type rdfs:subClassOf* $uniqueValueForClass .
}""" ] ;
    sh:targetClass sh:PropertyShape .

dash:ValueTableViewer a dash:Viewer ;
    rdfs:label "Value table viewer" ;
    rdfs:comment "A viewer that renders all values of a given property as a table, with one value per row, and the columns defined by the shape that is the sh:node or sh:class of the property." .

dash:abstract a rdf:Property ;
    rdfs:label "abstract" ;
    rdfs:comment "Indicates that a class is \"abstract\" and cannot be used in asserted rdf:type triples. Only non-abstract subclasses of abstract classes should be instantiated directly." ;
    rdfs:domain rdfs:Class ;
    rdfs:range xsd:boolean .

dash:addedTriple a rdf:Property ;
    rdfs:label "added triple" ;
    rdfs:comment "May link a dash:GraphUpdate with one or more triples (represented as instances of rdf:Statement) that should be added to fix the source of the result." ;
    rdfs:domain dash:GraphUpdate ;
    rdfs:range rdf:Statement .

dash:all a rdfs:Resource ;
    rdfs:label "all" ;
    rdfs:comment "Represents all users/roles, for example as a possible value of the default view for role property." .

dash:applicableToClass a rdf:Property ;
    rdfs:label "applicable to class" ;
    rdfs:comment "Can be used to state that a shape is applicable to instances of a given class. This is a softer statement than \"target class\": a target means that all instances of the class must conform to the shape. Being applicable to simply means that the shape may apply to (some) instances of the class. This information can be used by algorithms or humans." ;
    rdfs:domain sh:Shape ;
    rdfs:range rdfs:Class .

dash:composite a rdf:Property ;
    rdfs:label "composite" ;
    rdfs:comment "Can be used to indicate that a property/path represented by a property constraint represents a composite relationship. In a composite relationship, the life cycle of a \"child\" object (value of the property/path) depends on the \"parent\" object (focus node). If the parent gets deleted, then the child objects should be deleted, too. Tools may use dash:composite (if set to true) to implement cascading delete operations." ;
    rdfs:domain sh:PropertyShape ;
    rdfs:range xsd:boolean .

dash:defaultValueType a rdf:Property ;
    rdfs:label "default value type" ;
    rdfs:comment """
		Links a property with a default value type.
		The default value type is assumed to be the <code>rdf:type</code> of values of the property
		that declare no type on their own.
		An example use of <code>sh:defaultValueType</code> is <code>sh:property</code>,
		the values of which are assumed to be instances of <code>sh:PropertyShape</code>
		even if they are untyped (blank) nodes.
		"""^^rdf:HTML ;
    rdfs:range rdfs:Class ;
    owl:versionInfo "Note this property may get removed in future versions. It is a left-over from a previous design in SHACL." .

dash:defaultViewForRole a rdf:Property ;
    rdfs:label "default view for role" ;
    rdfs:comment "Links a node shape with the roles for which it shall be used as default view. User interfaces can use these values to select how to present a given RDF resource. The values of this property are URIs representing a group of users or agents. There is a dedicated URI dash:all representing all users." ;
    rdfs:domain sh:NodeShape .

dash:deletedTriple a rdf:Property ;
    rdfs:label "deleted triple" ;
    rdfs:comment "May link a dash:GraphUpdate result with one or more triples (represented as instances of rdf:Statement) that should be deleted to fix the source of the result." ;
    rdfs:domain dash:GraphUpdate ;
    rdfs:range rdf:Statement .

dash:detailsEndpoint a rdf:Property ;
    rdfs:label "details endpoint" ;
    rdfs:comment """Can be used to link a SHACL property shape with the URL of a SPARQL endpoint that may contain further RDF triples for the value nodes delivered by the property. This can be used to inform a processor that it should switch to values from an external graph when the user wants to retrieve more information about a value.

This property should be regarded as an "annotation", i.e. it does not have any impact on validation or other built-in SHACL features. However, selected tools may want to use this information. One implementation strategy would be to periodically fetch the values specified by the sh:node or sh:class shape associated with the property, using the property shapes in that shape, and add the resulting triples into the main query graph.

An example value is "https://query.wikidata.org/sparql".""" .

dash:detailsGraph a rdf:Property ;
    rdfs:label "details graph" ;
    rdfs:comment """Can be used to link a SHACL property shape with a SHACL node expression that produces the URIs of one or more graphs that contain further RDF triples for the value nodes delivered by the property. This can be used to inform a processor that it should switch to another data graph when the user wants to retrieve more information about a value.

The node expressions are evaluated with the focus node as input. (It is unclear whether there are also cases where the result may be different for each specific value, in which case the node expression would need a second input argument).

This property should be regarded as an "annotation", i.e. it does not have any impact on validation or other built-in SHACL features. However, selected tools may want to use this information.""" .

dash:editor a rdf:Property ;
    rdfs:label "editor" ;
    rdfs:comment "Can be used to link a property shape with an editor, to state a preferred editing widget in user interfaces." ;
    rdfs:domain sh:PropertyShape ;
    rdfs:range dash:Editor .

dash:expectedResultIsJSON a rdf:Property ;
    rdfs:label "expected result is JSON" ;
    rdfs:comment "A flag to indicate that the expected result represents a JSON string. If set to true, then tests would compare JSON structures (regardless of whitespaces) instead of actual syntax." ;
    rdfs:range xsd:boolean .

dash:expectedResultIsTTL a rdf:Property ;
    rdfs:label "expected result is Turtle" ;
    rdfs:comment "A flag to indicate that the expected result represents an RDF graph encoded as a Turtle file. If set to true, then tests would compare graphs instead of actual syntax." ;
    rdfs:domain dash:TestCase ;
    rdfs:range xsd:boolean .

dash:fixed a rdf:Property ;
    rdfs:label "fixed" ;
    rdfs:comment "Can be used to mark that certain validation results have already been fixed." ;
    rdfs:domain sh:ValidationResult ;
    rdfs:range xsd:boolean .

dash:height a rdf:Property ;
    rdfs:label "height" ;
    rdfs:comment "The height." ;
    rdfs:range xsd:integer .

dash:hidden a rdf:Property ;
    rdfs:label "hidden" ;
    rdfs:comment "Properties marked as readOnly do not appear in user interfaces, yet remain part of the shape for other purposes such as validation and GraphQL schemas." ;
    rdfs:domain sh:PropertyShape ;
    rdfs:range xsd:boolean .

dash:includedExecutionPlatform a rdf:Property ;
    rdfs:label "included execution platform" ;
    rdfs:comment "Can be used to state that one (subject) execution platform includes all features of another platform (object)." ;
    rdfs:domain dash:ExecutionPlatform ;
    rdfs:range dash:ExecutionPlatform .

dash:isDeactivated a sh:SPARQLFunction ;
    rdfs:label "is deactivated" ;
    rdfs:comment "Checks whether a given shape or constraint has been marked as \"deactivated\" using sh:deactivated." ;
    sh:ask """ASK {
    ?constraintOrShape sh:deactivated true .
}""" ;
    sh:parameter [ sh:description "The sh:Constraint or sh:Shape to test." ;
            sh:name "constraint or shape" ;
            sh:path dash:constraintOrShape ] ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:returnType xsd:boolean .

dash:isNodeKindBlankNode a sh:SPARQLFunction ;
    rdfs:label "is NodeKind BlankNode" ;
    dash:cachable true ;
    rdfs:comment "Checks if a given sh:NodeKind is one that includes BlankNodes." ;
    sh:ask """ASK {
	FILTER ($nodeKind IN ( sh:BlankNode, sh:BlankNodeOrIRI, sh:BlankNodeOrLiteral ))
}""" ;
    sh:parameter [ sh:class sh:NodeKind ;
            sh:description "The sh:NodeKind to check." ;
            sh:name "node kind" ;
            sh:nodeKind sh:IRI ;
            sh:path dash:nodeKind ] ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:returnType xsd:boolean .

dash:isNodeKindIRI a sh:SPARQLFunction ;
    rdfs:label "is NodeKind IRI" ;
    dash:cachable true ;
    rdfs:comment "Checks if a given sh:NodeKind is one that includes IRIs." ;
    sh:ask """ASK {
	FILTER ($nodeKind IN ( sh:IRI, sh:BlankNodeOrIRI, sh:IRIOrLiteral ))
}""" ;
    sh:parameter [ sh:class sh:NodeKind ;
            sh:description "The sh:NodeKind to check." ;
            sh:name "node kind" ;
            sh:nodeKind sh:IRI ;
            sh:path dash:nodeKind ] ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:returnType xsd:boolean .

dash:isNodeKindLiteral a sh:SPARQLFunction ;
    rdfs:label "is NodeKind Literal" ;
    dash:cachable true ;
    rdfs:comment "Checks if a given sh:NodeKind is one that includes Literals." ;
    sh:ask """ASK {
	FILTER ($nodeKind IN ( sh:Literal, sh:BlankNodeOrLiteral, sh:IRIOrLiteral ))
}""" ;
    sh:parameter [ sh:class sh:NodeKind ;
            sh:description "The sh:NodeKind to check." ;
            sh:name "node kind" ;
            sh:nodeKind sh:IRI ;
            sh:path dash:nodeKind ] ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:returnType xsd:boolean .

dash:localConstraint a rdf:Property ;
    rdfs:label "local constraint" ;
    rdfs:comment """Can be set to true for those constraint components where the validation does not require to visit any other triples than the shape definitions and the direct property values of the focus node mentioned in the property constraints. Examples of this include sh:minCount and sh:hasValue.

Constraint components that are marked as such can be optimized by engines, e.g. they can be evaluated client-side at form submission time, without having to make a round-trip to a server, assuming the client has downloaded a complete snapshot of the resource.

Any component marked with dash:staticConstraint is also a dash:localConstraint.""" ;
    rdfs:domain sh:ConstraintComponent ;
    rdfs:range xsd:boolean .

dash:propertySuggestionGenerator a rdf:Property ;
    rdfs:label "property suggestion generator" ;
    rdfs:comment "Links the constraint component with instances of dash:SuggestionGenerator that may be used to produce suggestions for a given validation result that was produced by a property constraint." ;
    rdfs:domain sh:ConstraintComponent ;
    rdfs:range dash:SuggestionGenerator .

dash:readOnly a rdf:Property ;
    rdfs:label "read only" ;
    rdfs:comment "Used as a hint for user interfaces that values of the associated property should not be editable. The values of this may be the boolean literals true or false or, more generally, a SHACL node expression that must evaluate to true or false." ;
    rdfs:domain sh:PropertyShape .

dash:requiredExecutionPlatform a rdf:Property ;
    rdfs:label "required execution platform" ;
    rdfs:comment "Links a SPARQL executable with the platforms that it can be executed on. This can be used by a SHACL implementation to determine whether a constraint validator or rule shall be ignored based on the current platform. For example, if a SPARQL query uses a function or magic property that is only available in TopBraid then a non-TopBraid platform can ignore the constraint (or simply always return no validation results). If this property has no value then the assumption is that the execution will succeed. As soon as one value exists, the assumption is that the engine supports at least one of the given platforms." ;
    rdfs:domain sh:SPARQLExecutable ;
    rdfs:range dash:ExecutionPlatform .

dash:shape a rdf:Property ;
    rdfs:label "shape" ;
    rdfs:comment "States that a subject resource has a given shape. This property can, for example, be used to capture results of SHACL validation on static data." ;
    rdfs:range sh:Shape .

dash:staticConstraint a rdf:Property ;
    rdfs:label "static constraint" ;
    rdfs:comment """Can be set to true for those constraint components where the validation does not require to visit any other triples than the parameters. Examples of this include sh:datatype or sh:nodeKind, where no further triples need to be queried to determine the result.

Constraint components that are marked as such can be optimized by engines, e.g. they can be evaluated client-side at form submission time, without having to make a round-trip to a server.""" ;
    rdfs:domain sh:ConstraintComponent ;
    rdfs:range xsd:boolean .

dash:suggestion a rdf:Property ;
    rdfs:label "suggestion" ;
    rdfs:comment "Can be used to link a result with one or more suggestions on how to address or improve the underlying issue." ;
    rdfs:domain sh:AbstractResult ;
    rdfs:range dash:Suggestion .

dash:suggestionConfidence a rdf:Property ;
    rdfs:label "suggestion confidence" ;
    rdfs:comment "An optional confidence between 0% and 100%. Suggestions with 100% confidence are strongly recommended. Can be used to sort recommended updates." ;
    rdfs:domain dash:Suggestion ;
    rdfs:range xsd:decimal .

dash:suggestionGenerator a rdf:Property ;
    rdfs:label "suggestion generator" ;
    rdfs:comment "Links a sh:SPARQLConstraint or sh:JSConstraint with instances of dash:SuggestionGenerator that may be used to produce suggestions for a given validation result that was produced by the constraint." ;
    rdfs:range dash:SuggestionGenerator .

dash:suggestionGroup a rdf:Property ;
    rdfs:label "suggestion" ;
    rdfs:comment "Can be used to link a suggestion with the group identifier to which it belongs. By default this is a link to the dash:SuggestionGenerator, but in principle this could be any value." ;
    rdfs:domain dash:Suggestion .

dash:testEnvironment a rdf:Property ;
    rdfs:label "test environment" ;
    rdfs:comment "Can be used by TestCases to point at a resource with information on how to set up the execution environment prior to execution." ;
    rdfs:domain dash:TestCase ;
    rdfs:range dash:TestEnvironment .

dash:testModifiesEnvironment a rdf:Property ;
    rdfs:label "test modifies environment" ;
    rdfs:comment "Indicates whether this test modifies the specified dash:testEnvironment. If set to true then a test runner can make sure to wipe out the previous environment, while leaving it false (or undefined) means that the test runner can reuse the environment from the previous test case. As setting up and tearing down tests is sometimes slow, this flag can significantly accelerate test execution." ;
    rdfs:domain dash:TestCase ;
    rdfs:range xsd:boolean .

dash:toString a sh:JSFunction,
        sh:SPARQLFunction ;
    rdfs:label "to string" ;
    dash:cachable true ;
    rdfs:comment "Returns a literal with datatype xsd:string that has the input value as its string. If the input value is an (URI) resource then its URI will be used." ;
    sh:jsFunctionName "dash_toString" ;
    sh:jsLibrary dash:DASHJSLibrary ;
    sh:labelTemplate "Convert {$arg} to xsd:string" ;
    sh:parameter [ sh:description "The input value." ;
            sh:name "arg" ;
            sh:nodeKind sh:IRIOrLiteral ;
            sh:path dash:arg ] ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:returnType xsd:string ;
    sh:select """SELECT (xsd:string($arg) AS ?result)
WHERE {
}""" .

dash:validateShapes a rdf:Property ;
    rdfs:label "validate shapes" ;
    rdfs:comment "True to also validate the shapes itself (i.e. parameter declarations)." ;
    rdfs:domain dash:GraphValidationTestCase ;
    rdfs:range xsd:boolean .

dash:valueCount a sh:SPARQLFunction ;
    rdfs:label "value count" ;
    rdfs:comment "Computes the number of objects for a given subject/predicate combination." ;
    sh:parameter [ sh:class rdfs:Resource ;
            sh:description "The predicate to get the number of objects of." ;
            sh:name "predicate" ;
            sh:order 1 ;
            sh:path dash:predicate ],
        [ sh:class rdfs:Resource ;
            sh:description "The subject to get the number of objects of." ;
            sh:name "subject" ;
            sh:order 0 ;
            sh:path dash:subject ] ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:returnType xsd:integer ;
    sh:select """
		SELECT (COUNT(?object) AS ?result)
		WHERE {
    		$subject $predicate ?object .
		}
""" .

dash:viewer a rdf:Property ;
    rdfs:label "viewer" ;
    rdfs:comment "Can be used to link a property shape with a viewer, to state a preferred viewing widget in user interfaces." ;
    rdfs:domain sh:PropertyShape ;
    rdfs:range dash:Viewer .

dash:width a rdf:Property ;
    rdfs:label "width" ;
    rdfs:comment "The width." ;
    rdfs:range xsd:integer .

dash:x a rdf:Property ;
    rdfs:label "x" ;
    rdfs:comment "The x position." ;
    rdfs:range xsd:integer .

dash:y a rdf:Property ;
    rdfs:label "y" ;
    rdfs:comment "The y position." ;
    rdfs:range xsd:integer .

sh:AndConstraintComponent sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateAnd" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

sh:ClassConstraintComponent sh:labelTemplate "Value needs to have class {$class}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateClass" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasClass .

sh:ClosedConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "Closed shape: only the enumerated properties can be used" ;
    sh:nodeValidator [ a sh:SPARQLSelectValidator ;
            sh:message "Predicate {?path} is not allowed (closed shape)" ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT $this (?predicate AS ?path) ?value
		WHERE {
			{
				FILTER ($closed) .
			}
			$this ?predicate ?value .
			FILTER (NOT EXISTS {
				GRAPH $shapesGraph {
					$currentShape sh:property/sh:path ?predicate .
				}
			} && (!bound($ignoredProperties) || NOT EXISTS {
				GRAPH $shapesGraph {
					$ignoredProperties rdf:rest*/rdf:first ?predicate .
				}
			}))
		}
""" ] ;
    sh:targetClass sh:NodeShape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateClosed" ;
            sh:jsLibrary dash:DASHJSLibrary ;
            sh:message "Predicate is not allowed (closed shape)" ] .

sh:DatatypeConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Values must have datatype {$datatype}" ;
    sh:message "Value does not have datatype {$datatype}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateDatatype" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

sh:DisjointConstraintComponent dash:localConstraint true ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateDisjoint" ;
            sh:jsLibrary dash:DASHJSLibrary ;
            sh:message "Value node must not also be one of the values of {$disjoint}" ],
        [ a sh:SPARQLAskValidator ;
            sh:ask """
		ASK {
			FILTER NOT EXISTS {
				$this $disjoint $value .
			}
		}
		""" ;
            sh:message "Property must not share any values with {$disjoint}" ;
            sh:prefixes <http://datashapes.org/dash> ] .

sh:EqualsConstraintComponent dash:localConstraint true ;
    sh:message "Must have same values as {$equals}" ;
    sh:nodeValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateEqualsNode" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT DISTINCT $this ?value
		WHERE {
			{
				FILTER NOT EXISTS { $this $equals $this }
				BIND ($this AS ?value) .
			}
			UNION
			{
				$this $equals ?value .
				FILTER (?value != $this) .
			}
		}
		""" ] ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateEqualsProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT DISTINCT $this ?value
		WHERE {
			{
				$this $PATH ?value .
				MINUS {
					$this $equals ?value .
				}
			}
			UNION
			{
				$this $equals ?value .
				MINUS {
					$this $PATH ?value .
				}
			}
		}
		""" ] ;
    sh:targetClass sh:Shape .

sh:HasValueConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "Must have value {$hasValue}" ;
    sh:nodeValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateHasValueNode" ;
            sh:jsLibrary dash:DASHJSLibrary ;
            sh:message "Value must be {$hasValue}" ],
        [ a sh:SPARQLAskValidator ;
            sh:ask """ASK {
    FILTER ($value = $hasValue)
}""" ;
            sh:message "Value must be {$hasValue}" ;
            sh:prefixes <http://datashapes.org/dash> ] ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateHasValueProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ;
            sh:message "Missing expected value {$hasValue}" ],
        [ a sh:SPARQLSelectValidator ;
            sh:message "Missing expected value {$hasValue}" ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT $this
		WHERE {
			FILTER NOT EXISTS { $this $PATH $hasValue }
		}
		""" ] ;
    sh:targetClass sh:Shape .

sh:InConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "Value must be in {$in}" ;
    sh:message "Value is not in {$in}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateIn" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:isIn .

sh:JSExecutable dash:abstract true .

sh:LanguageInConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "Language must match any of {$languageIn}" ;
    sh:message "Language does not match any of {$languageIn}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateLanguageIn" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:isLanguageIn .

sh:LessThanConstraintComponent dash:localConstraint true ;
    sh:message "Value is not < value of {$lessThan}" ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateLessThanProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT $this ?value
		WHERE {
			$this $PATH ?value .
			$this $lessThan ?otherValue .
			BIND (?value < ?otherValue AS ?result) .
			FILTER (!bound(?result) || !(?result)) .
		}
		""" ] ;
    sh:targetClass sh:PropertyShape .

sh:LessThanOrEqualsConstraintComponent dash:localConstraint true ;
    sh:message "Value is not <= value of {$lessThanOrEquals}" ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateLessThanOrEqualsProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT DISTINCT $this ?value
		WHERE {
			$this $PATH ?value .
			$this $lessThanOrEquals ?otherValue .
			BIND (?value <= ?otherValue AS ?result) .
			FILTER (!bound(?result) || !(?result)) .
		}
""" ] ;
    sh:targetClass sh:PropertyShape .

sh:MaxCountConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "Must not have more than {$maxCount} values" ;
    sh:message "More than {$maxCount} values" ;
    sh:propertyValidator [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT $this
		WHERE {
			$this $PATH ?value .
		}
		GROUP BY $this
		HAVING (COUNT(DISTINCT ?value) > $maxCount)
		""" ],
        [ a sh:JSValidator ;
            sh:jsFunctionName "validateMaxCountProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ] ;
    sh:targetClass sh:PropertyShape .

sh:MaxExclusiveConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must be < {$maxExclusive}" ;
    sh:message "Value is not < {$maxExclusive}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMaxExclusive" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasMaxExclusive .

sh:MaxInclusiveConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must be <= {$maxInclusive}" ;
    sh:message "Value is not <= {$maxInclusive}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMaxInclusive" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasMaxInclusive .

sh:MaxLengthConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must not have more than {$maxLength} characters" ;
    sh:message "Value has more than {$maxLength} characters" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMaxLength" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasMaxLength .

sh:MinCountConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "Must have at least {$minCount} values" ;
    sh:message "Fewer than {$minCount} values" ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMinCountProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT $this
		WHERE {
			OPTIONAL {
				$this $PATH ?value .
			}
		}
		GROUP BY $this
		HAVING (COUNT(DISTINCT ?value) < $minCount)
		""" ] ;
    sh:targetClass sh:PropertyShape .

sh:MinExclusiveConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must be > {$minExclusive}" ;
    sh:message "Value is not > {$minExclusive}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMinExclusive" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasMinExclusive .

sh:MinInclusiveConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must be >= {$minInclusive}" ;
    sh:message "Value is not >= {$minInclusive}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMinInclusive" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasMinInclusive .

sh:MinLengthConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must have less than {$minLength} characters" ;
    sh:message "Value has less than {$minLength} characters" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateMinLength" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasMinLength .

sh:NodeConstraintComponent sh:message "Value does not have shape {$node}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateNode" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

sh:NodeKindConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must have node kind {$nodeKind}" ;
    sh:message "Value does not have node kind {$nodeKind}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateNodeKind" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasNodeKind .

sh:NotConstraintComponent sh:labelTemplate "Value must not have shape {$not}" ;
    sh:message "Value does have shape {$not}" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateNot" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

sh:OrConstraintComponent sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateOr" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

sh:PatternConstraintComponent dash:staticConstraint true ;
    sh:labelTemplate "Value must match pattern \"{$pattern}\"" ;
    sh:message "Value does not match pattern \"{$pattern}\"" ;
    sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validatePattern" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        dash:hasPattern .

sh:QualifiedMaxCountConstraintComponent sh:labelTemplate "No more than {$qualifiedMaxCount} values can have shape {$qualifiedValueShape}" ;
    sh:message "More than {$qualifiedMaxCount} values have shape {$qualifiedValueShape}" ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateQualifiedMaxCountProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ] ;
    sh:targetClass sh:PropertyShape .

sh:QualifiedMinCountConstraintComponent sh:labelTemplate "No fewer than {$qualifiedMinCount} values can have shape {$qualifiedValueShape}" ;
    sh:message "Fewer than {$qualifiedMinCount} values have shape {$qualifiedValueShape}" ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateQualifiedMinCountProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ] ;
    sh:targetClass sh:PropertyShape .

sh:Rule dash:abstract true .

sh:Rules a rdfs:Resource ;
    rdfs:label "SHACL Rules" ;
    rdfs:comment "The SHACL rules entailment regime." ;
    rdfs:seeAlso <https://www.w3.org/TR/shacl-af/#Rules> .

sh:TargetType dash:abstract true .

sh:UniqueLangConstraintComponent dash:localConstraint true ;
    sh:labelTemplate "No language can be used more than once" ;
    sh:message "Language \"{?lang}\" used more than once" ;
    sh:propertyValidator [ a sh:JSValidator ;
            sh:jsFunctionName "validateUniqueLangProperty" ;
            sh:jsLibrary dash:DASHJSLibrary ],
        [ a sh:SPARQLSelectValidator ;
            sh:prefixes <http://datashapes.org/dash> ;
            sh:select """
		SELECT DISTINCT $this ?lang
		WHERE {
			{
				FILTER sameTerm($uniqueLang, true) .
			}
			$this $PATH ?value .
			BIND (lang(?value) AS ?lang) .
			FILTER (bound(?lang) && ?lang != "") .
			FILTER EXISTS {
				$this $PATH ?otherValue .
				FILTER (?otherValue != ?value && ?lang = lang(?otherValue)) .
			}
		}
		""" ] ;
    sh:targetClass sh:PropertyShape .

sh:Validator dash:abstract true .

sh:XoneConstraintComponent sh:targetClass sh:Shape ;
    sh:validator [ a sh:JSValidator ;
            sh:jsFunctionName "validateXone" ;
            sh:jsLibrary dash:DASHJSLibrary ] .

sh:node dash:defaultValueType sh:NodeShape .

sh:not dash:defaultValueType sh:Shape .

sh:order rdfs:range xsd:decimal .

sh:property dash:defaultValueType sh:PropertyShape .

sh:qualifiedValueShape dash:defaultValueType sh:Shape .

sh:sparql dash:defaultValueType sh:SPARQLConstraint .

dash:AllObjectsTarget a sh:JSTargetType,
        sh:SPARQLTargetType ;
    rdfs:label "All objects target" ;
    rdfs:comment "A target containing all objects in the data graph as focus nodes." ;
    rdfs:subClassOf sh:Target ;
    sh:jsFunctionName "dash_allObjects" ;
    sh:jsLibrary dash:DASHJSLibrary ;
    sh:labelTemplate "All objects" ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:select """SELECT DISTINCT ?this
WHERE {
    ?anyS ?anyP ?this .
}""" .

dash:AllSubjectsTarget a sh:JSTargetType,
        sh:SPARQLTargetType ;
    rdfs:label "All subjects target" ;
    rdfs:comment "A target containing all subjects in the data graph as focus nodes." ;
    rdfs:subClassOf sh:Target ;
    sh:jsFunctionName "dash_allSubjects" ;
    sh:jsLibrary dash:DASHJSLibrary ;
    sh:labelTemplate "All subjects" ;
    sh:prefixes <http://datashapes.org/dash> ;
    sh:select """SELECT DISTINCT ?this
WHERE {
    ?this ?anyP ?anyO .
}""" .

dash:ClosedByTypesConstraintComponent-closedByTypes a sh:Parameter ;
    sh:datatype xsd:boolean ;
    sh:description "True to indicate that the focus nodes are closed by their types. A constraint violation is reported for each property value of the focus node where the property is not among those that are explicitly declared via sh:property/sh:path in any of the rdf:types of the focus node (and their superclasses). The property rdf:type is always permitted." ;
    sh:path dash:closedByTypes .

dash:CoExistsWithConstraintComponent-coExistsWith a sh:Parameter ;
    sh:class rdf:Property ;
    sh:nodeKind sh:IRI ;
    sh:path dash:coExistsWith .

dash:HasValueWithClassConstraintComponent-hasValueWithClass a sh:Parameter ;
    sh:class rdfs:Class ;
    sh:nodeKind sh:IRI ;
    sh:path dash:hasValueWithClass .

dash:ListNodeShape a sh:NodeShape ;
    rdfs:label "List node shape" ;
    rdfs:comment "Defines constraints on what it means for a node to be a node within a well-formed RDF list. Note that this does not check whether the rdf:rest items are also well-formed lists as this would lead to unsupported recursion." ;
    sh:or ( [ sh:hasValue () ;
                sh:property [ sh:maxCount 0 ;
                        sh:path rdf:first ],
                    [ sh:maxCount 0 ;
                        sh:path rdf:rest ] ] [ sh:not [ sh:hasValue () ] ;
                sh:property [ sh:maxCount 1 ;
                        sh:minCount 1 ;
                        sh:path rdf:first ],
                    [ sh:maxCount 1 ;
                        sh:minCount 1 ;
                        sh:path rdf:rest ] ] ) .

dash:NonRecursiveConstraintComponent-nonRecursive a sh:Parameter ;
    sh:datatype xsd:boolean ;
    sh:maxCount 1 ;
    sh:name "non-recursive" ;
    sh:path dash:nonRecursive .

dash:ParameterConstraintComponent-parameter a sh:Parameter ;
    sh:path sh:parameter .

dash:PrimaryKeyConstraintComponent-uriStart a sh:Parameter ;
    sh:datatype xsd:string ;
    sh:description "The start of the URIs of well-formed resources. If specified then the associated property/path serves as \"primary key\" for all target nodes (instances). All such target nodes need to have a URI that starts with the given string, followed by the URI-encoded value of the primary key property." ;
    sh:name "URI start" ;
    sh:path dash:uriStart .

dash:RDFQueryJSLibrary a sh:JSLibrary ;
    rdfs:label "rdfQuery JavaScript Library" ;
    sh:jsLibraryURL "http://datashapes.org/js/rdfquery.js"^^xsd:anyURI .

dash:ReifiableByConstraintComponent-reifiableBy a sh:Parameter ;
    sh:class sh:NodeShape ;
    sh:description "Can be used to specify the node shape that may be applied to reified statements produced by a property shape. The property shape must have a URI resource as its sh:path. The values of this property must be node shapes. User interfaces can use this information to determine which properties to present to users when reified statements are explored or edited. Also, SHACL validators can use it to determine how to validate reified triples. Use dash:None to indicate that no reification should be permitted." ;
    sh:nodeKind sh:IRI ;
    sh:path dash:reifiableBy .

dash:RootClassConstraintComponent-rootClass a sh:Parameter ;
    sh:class rdfs:Class ;
    sh:description "The root class." ;
    sh:name "root class" ;
    sh:nodeKind sh:IRI ;
    sh:path dash:rootClass .

dash:StemConstraintComponent-stem a sh:Parameter ;
    sh:datatype xsd:string ;
    sh:path dash:stem .

dash:SubSetOfConstraintComponent-subSetOf a sh:Parameter ;
    sh:class rdf:Property ;
    sh:description "A property (of the focus node) that must (at least) have all values from the set of value nodes." ;
    sh:path dash:subSetOf .

dash:SymmetricConstraintComponent-symmetric a sh:Parameter ;
    sh:datatype xsd:boolean ;
    sh:path dash:symmetric .

dash:UniqueValueForClassConstraintComponent-uniqueValueForClass a sh:Parameter ;
    sh:class rdfs:Class ;
    sh:nodeKind sh:IRI ;
    sh:path dash:uniqueValueForClass .

dash:cachable a rdf:Property ;
    rdfs:label "cachable" ;
    rdfs:comment "If set to true then the results of the SHACL function can be cached in between invocations with the same arguments. In other words, they are stateless and do not depend on triples in any graph, or the current time stamp etc." ;
    rdfs:domain sh:Function ;
    rdfs:range xsd:boolean .

dash:closedByTypes a rdf:Property ;
    rdfs:label "closed by types" .

dash:coExistsWith a rdf:Property ;
    rdfs:label "co-exists with" ;
    rdfs:comment "Specifies a property that must have a value whenever the property path has a value, and must have no value whenever the property path has no value." ;
    rdfs:range rdf:Property .

dash:hasClass a sh:SPARQLAskValidator ;
    rdfs:label "has class" ;
    sh:ask """
		ASK {
			$value rdf:type/rdfs:subClassOf* $class .
		}
		""" ;
    sh:message "Value does not have class {$class}" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasMaxExclusive a sh:SPARQLAskValidator ;
    rdfs:label "has max exclusive" ;
    rdfs:comment "Checks whether a given node (?value) has a value less than (<) the provided ?maxExclusive. Returns false if this cannot be determined, e.g. because values do not have comparable types." ;
    sh:ask "ASK { FILTER ($value < $maxExclusive) }" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasMaxInclusive a sh:SPARQLAskValidator ;
    rdfs:label "has max inclusive" ;
    rdfs:comment "Checks whether a given node (?value) has a value less than or equal to (<=) the provided ?maxInclusive. Returns false if this cannot be determined, e.g. because values do not have comparable types." ;
    sh:ask "ASK { FILTER ($value <= $maxInclusive) }" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasMaxLength a sh:SPARQLAskValidator ;
    rdfs:label "has max length" ;
    rdfs:comment "Checks whether a given string (?value) has a length within a given maximum string length." ;
    sh:ask """
		ASK {
			FILTER (STRLEN(str($value)) <= $maxLength) .
		}
		""" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasMinExclusive a sh:SPARQLAskValidator ;
    rdfs:label "has min exclusive" ;
    rdfs:comment "Checks whether a given node (?value) has value greater than (>) the provided ?minExclusive. Returns false if this cannot be determined, e.g. because values do not have comparable types." ;
    sh:ask "ASK { FILTER ($value > $minExclusive) }" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasMinInclusive a sh:SPARQLAskValidator ;
    rdfs:label "has min inclusive" ;
    rdfs:comment "Checks whether a given node (?value) has value greater than or equal to (>=) the provided ?minInclusive. Returns false if this cannot be determined, e.g. because values do not have comparable types." ;
    sh:ask "ASK { FILTER ($value >= $minInclusive) }" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasMinLength a sh:SPARQLAskValidator ;
    rdfs:label "has min length" ;
    rdfs:comment "Checks whether a given string (?value) has a length within a given minimum string length." ;
    sh:ask """
		ASK {
			FILTER (STRLEN(str($value)) >= $minLength) .
		}
		""" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasNodeKind a sh:SPARQLAskValidator ;
    rdfs:label "has node kind" ;
    rdfs:comment "Checks whether a given node (?value) has a given sh:NodeKind (?nodeKind). For example, sh:hasNodeKind(42, sh:Literal) = true." ;
    sh:ask """
		ASK {
			FILTER ((isIRI($value) && $nodeKind IN ( sh:IRI, sh:BlankNodeOrIRI, sh:IRIOrLiteral ) ) ||
				(isLiteral($value) && $nodeKind IN ( sh:Literal, sh:BlankNodeOrLiteral, sh:IRIOrLiteral ) ) ||
				(isBlank($value)   && $nodeKind IN ( sh:BlankNode, sh:BlankNodeOrIRI, sh:BlankNodeOrLiteral ) )) .
		}
		""" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasPattern a sh:SPARQLAskValidator ;
    rdfs:label "has pattern" ;
    rdfs:comment "Checks whether the string representation of a given node (?value) matches a given regular expression (?pattern). Returns false if the value is a blank node." ;
    sh:ask "ASK { FILTER (!isBlank($value) && IF(bound($flags), regex(str($value), $pattern, $flags), regex(str($value), $pattern))) }" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasRootClass a sh:SPARQLAskValidator ;
    rdfs:label "has root class" ;
    sh:ask """ASK {
    $value rdfs:subClassOf* $rootClass .
}""" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasStem a sh:SPARQLAskValidator ;
    rdfs:label "has stem" ;
    rdfs:comment "Checks whether a given node is an IRI starting with a given stem." ;
    sh:ask "ASK { FILTER (isIRI($value) && STRSTARTS(str($value), $stem)) }" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:hasValueWithClass a rdf:Property ;
    rdfs:label "has value with class" ;
    rdfs:comment "Specifies a constraint that at least one of the value nodes must be an instance of a given class." ;
    rdfs:range rdfs:Class .

dash:isIn a sh:SPARQLAskValidator ;
    rdfs:label "is in" ;
    sh:ask """
		ASK {
			GRAPH $shapesGraph {
				$in (rdf:rest*)/rdf:first $value .
			}
		}
		""" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:isLanguageIn a sh:SPARQLAskValidator ;
    rdfs:label "is language in" ;
    sh:ask """
		ASK {
			BIND (lang($value) AS ?valueLang) .
			FILTER EXISTS {
				GRAPH $shapesGraph {
					$languageIn (rdf:rest*)/rdf:first ?lang .
				    FILTER (langMatches(?valueLang, ?lang))
				} }
		}
		""" ;
    sh:prefixes <http://datashapes.org/dash> .

dash:reifiableBy a rdf:Property ;
    rdfs:label "reifiable by" ;
    rdfs:comment "Can be used to specify the node shape that may be applied to reified statements produced by a property shape. The property shape must have a URI resource as its sh:path. The values of this property must be node shapes. User interfaces can use this information to determine which properties to present to users when reified statements are explored or edited. Use dash:None to indicate that no reification should be permitted." ;
    rdfs:domain sh:PropertyShape ;
    rdfs:range sh:NodeShape .

dash:rootClass a rdf:Property ;
    rdfs:label "root class" .

dash:singleLine a rdf:Property ;
    rdfs:label "single line" ;
    rdfs:range xsd:boolean .

dash:stem a rdf:Property ;
    rdfs:label "stem"@en ;
    rdfs:comment "Specifies a string value that the IRI of the value nodes must start with."@en ;
    rdfs:range xsd:string .

dash:subSetOf a rdf:Property ;
    rdfs:label "sub set of" .

dash:symmetric a rdf:Property ;
    rdfs:label "symmetric" ;
    rdfs:comment "True to declare that the associated property path is symmetric." .

dash:uniqueValueForClass a rdf:Property ;
    rdfs:label "unique value for class" .

<http://purl.allotrope.org/shapes/datashapes/REC/2019/12/dash> a owl:Ontology ;
    rdfs:label "DASH Data Shapes Library" ;
    ns1:lastRefreshedOn "2019-11-18T12:00:00+00:00"^^xsd:dateTime ;
    ns1:retrievedFrom <http://datashapes.org/dash> ;
    rdfs:comment """DASH defines SPARQL-based validators for many SHACL Core constraint components. These are (among others) utilized by TopBraid and its API. Note that constraint components that require validation of nested shapes (such as sh:node) are not implementable without a function such as tosh:hasShape.

DASH is also a SHACL library for frequently needed features and design patterns. All features in this library are 100% standards compliant and will work on any engine that fully supports SHACL.""" ;
    owl:imports <http://purl.allotrope.org/shapes/datashapes/REC/2019/12/tosh>,
        sh: ;
    owl:versionIRI <http://purl.allotrope.org/shapes/datashapes/REC/2019/12/dash> ;
    sh:declare [ sh:namespace "http://datashapes.org/dash#"^^xsd:anyURI ;
            sh:prefix "dash" ],
        [ sh:namespace "http://purl.org/dc/terms/"^^xsd:anyURI ;
            sh:prefix "dcterms" ],
        [ sh:namespace "http://www.w3.org/1999/02/22-rdf-syntax-ns#"^^xsd:anyURI ;
            sh:prefix "rdf" ],
        [ sh:namespace "http://www.w3.org/2000/01/rdf-schema#"^^xsd:anyURI ;
            sh:prefix "rdfs" ],
        [ sh:namespace "http://www.w3.org/2001/XMLSchema#"^^xsd:anyURI ;
            sh:prefix "xsd" ],
        [ sh:namespace "http://www.w3.org/2002/07/owl#"^^xsd:anyURI ;
            sh:prefix "owl" ],
        [ sh:namespace "http://www.w3.org/2004/02/skos/core#"^^xsd:anyURI ;
            sh:prefix "skos" ] .

sh:Function sh:property [ a sh:PropertyShape ;
            sh:datatype xsd:boolean ;
            sh:description "True to indicate that this function will always return the same values for the same combination of arguments, regardless of the query graphs. Engines can use this information to cache and reuse previous function calls." ;
            sh:maxCount 1 ;
            sh:name "cachable" ;
            sh:path dash:cachable ] .

sh:SPARQLExecutable dash:abstract true .

sh:parameter dash:defaultValueType sh:Parameter .

sh:Parameterizable dash:abstract true .

sh:Target dash:abstract true .

sh:AbstractResult dash:abstract true .

dash:expectedResult a rdf:Property ;
    rdfs:label "expected result" ;
    rdfs:comment "The expected result(s) of a test case. The value range of this property is different for each kind of test cases." ;
    rdfs:domain dash:TestCase .

sh:Shape dash:abstract true .

dash:DASHJSLibrary a sh:JSLibrary ;
    rdfs:label "DASH JavaScript library" ;
    sh:jsLibrary dash:RDFQueryJSLibrary ;
    sh:jsLibraryURL "http://datashapes.org/js/dash.js"^^xsd:anyURI .

