https://www.apachecon.com/acah2020/tracks/jena.html
Apache Jena track at ApacheCon@Home 2020
2020-09-28
SHACL in Apache Jena
Andy
Contributor to Apache Jena
Co-editor: SPARQL
Iotics : https://iotics.com/
Today
● About
● SHACL Core
○ Example walkthrough
● SHACL Compact syntax
● SHACL-SPARQL
● SHACL operations
SHACL
Describes what the data looks like
W3C standard: https://www.w3.org/TR/shacl/
Use for:
● Validation
● Schema
● HTML forms
● . . .
SHACL-AF
Also “SHACL Advanced features” : https://www.w3.org/TR/shacl-af/
● Custom Targets
● Rules
● Node expressions
● Functions
Active Community Group
https://www.w3.org/community/shacl/
Why validate?
● Unexpected data makes applications harder to write
● Unexpected data in a database is hard to clean up
● External data may be missing/incomplete/changed/. . .
● Unnoticed data changes
Unexpected or missing data is a signal
Доверяй, но проверяй
“Trust but verify”
-- Russian Proverb
SHACL
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:lessThan foaf:deathDate ;
sh:maxCount 1 ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
SHACL
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:lessThan foaf:deathDate ;
sh:maxCount 1 ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
Example data
:AlbertEinstein
a foaf:Person ;
foaf:givenName "Albert" ;
foaf:familyName "Einstein" ;
foaf:birthDate "1979-03-14"^^xsd:date ;
foaf:deathDate "1955-04-18"^^xsd:date ;
.
Validation
● Good: foaf:givenName
● No foaf:AddressShape (not required)
● foaf:familyName -- not matched
● Bad: foaf:birthDate
Validation Report
[ a sh:ValidationReport ;
sh:conforms false ;
sh:result [
a sh:ValidationResult ;
sh:focusNode :AlbertEinstein ;
sh:resultMessage "..." ;
sh:resultPath foaf:birthDate ;
sh:resultSeverity sh:Violation ;
sh:sourceConstraintComponent sh:LessThanConstraintComponent ;
sh:sourceShape [] ;
sh:value "1979-03-14"^^xsd:date
]
] .
SHACL Walkthrough
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:lessThan foaf:deathDate ;
sh:maxCount 1 ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
NodeShape URI: schema:PersonShape
… applies to resources of class foaf:Person
:AlbertEinstein rdf:type foaf:Person ;
foaf:givenName "Albert" ;
foaf:familyName "Einstein" ;
foaf:birthDate "1979-03-14"^^xsd:date ;
foaf:deathDate "1955-04-18"^^xsd:date ;
.
SHACL Walkthrough
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:lessThan foaf:deathDate ;
sh:maxCount 1 ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
Property Shape
… property foaf:givenName
:AlbertEinstein rdf:type foaf:Person ;
foaf:givenName "Albert" ;
foaf:familyName "Einstein" ;
foaf:birthDate "1979-03-14"^^xsd:date ;
foaf:deathDate "1955-04-18"^^xsd:date ;
.
SHACL Walkthrough
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:lessThan foaf:deathDate ;
sh:maxCount 1 ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
… property foaf:givenName
… … object must be an xsd:string
:AlbertEinstein rdf:type foaf:Person ;
foaf:givenName "Albert" ;
foaf:familyName "Einstein" ;
foaf:birthDate "1979-03-14"^^xsd:date ;
foaf:deathDate "1955-04-18"^^xsd:date ;
.
SHACL Walkthrough
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:maxCount 1 ;
sh:lessThan foaf:deathDate ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
… property foaf:birthDate
… … there must be at most one
:AlbertEinstein rdf:type foaf:Person ;
foaf:givenName "Albert" ;
foaf:familyName "Einstein" ;
foaf:birthDate "1979-03-14"^^xsd:date ;
foaf:deathDate "1955-04-18"^^xsd:date ;
.
SHACL Walkthrough
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:maxCount 1 ;
sh:lessThan foaf:deathDate ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
… property foaf:birthDate
… … value must be less than all values of foaf:deathDate
:AlbertEinstein rdf:type foaf:Person ;
foaf:givenName "Albert" ;
foaf:familyName "Einstein" ;
foaf:birthDate "1979-03-14"^^xsd:date ;
foaf:deathDate "1955-04-18"^^xsd:date ;
.
SHACL Walkthrough
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:maxCount 1 ;
sh:lessThan foaf:deathDate ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
… property schema:address
… … conforms to another node shape
SHACL Compact Syntax
schema:PersonShape
a sh:NodeShape ;
sh:targetClass foaf:Person ;
sh:property [
sh:path foaf:givenName ;
sh:datatype xsd:string ;
] ;
sh:property [
sh:path foaf:birthDate ;
sh:lessThan foaf:deathDate ;
sh:maxCount 1 ;
] ;
sh:property [
sh:path foaf:address ;
sh:node foaf:AddressShape ;
] .
shape schema:PersonShape -> foaf:Person {
foaf:givenName datatype=xsd:string .
foaf:birthDate [0..1] lessThan=foaf:deathDate .
foaf:address @foaf:AddressShape .
}
Targets
Classes
● sh:targetClass
● Implicit (with the class declaration)
sh:targetSubjectsOf property
● c.f. rdfs:domain
sh:targetObjectsOf property
● c.f. rdfs:range
sh:node
● Specific node
SPARQL targets (SHACL-af)
SHACL Core : Key concepts
Targets -- starting points
Node shapes
Property shapes and Paths
-- routes from starting points to nodes to validate
Constraints -- validations
Apache Jena
https://jena.apache.org/documentation/shacl/
● SHACL Core, SHACL SPARQL (the REC)
● SHACL Compact syntax - read and write
● Command line tools
○ Parse and print
○ Validate
● Fuseki service
○ Validate graph
○ Validate at node
SHACL SPARQL Constraints
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX sh: <http://www.w3.org/ns/shacl#>
PREFIX ex: <http://example/>
## SHAPES
ex:prefixes
sh:declare [ sh:prefix "rdfs"; sh:namespace "http://www.w3.org/2000/01/rdf-schema#"^^xsd:anyURI; ] .
:sparqlShape
sh:targetClass :CLASS ;
sh:sparql [
# Test language tag is in capitals
sh:prefixes ex:prefixes ;
# Query to return violations.
sh:select """
SELECT $this ?value
WHERE {
$this rdfs:label ?value .
BIND(lang(?value) AS ?X)
FILTER (!isLiteral(?value) || lcase(?X) != ?X)
}
""" ;
] .
One violation for each result of the query.
SHACL Idiom
PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX sh: <http://www.w3.org/ns/shacl#>
PREFIX ex: <http://example/>
## Test whether the data graph is empty.
ex:global
a sh:NodeShape ;
sh:targetNode ex:anything ;
sh:sparql [
sh:select "SELECT * { ?s ?p ?o } LIMIT 1" ;
] .
Online
https://shacl.org/playground/
Online
users@jena.apache.org
Subscribe: users-subscribe@jena.apache.org
https://jena.apache.org/documentation/shacl/

SHACL in Apache jena - ApacheCon2020

  • 1.
    https://www.apachecon.com/acah2020/tracks/jena.html Apache Jena trackat ApacheCon@Home 2020 2020-09-28 SHACL in Apache Jena
  • 2.
    Andy Contributor to ApacheJena Co-editor: SPARQL Iotics : https://iotics.com/
  • 3.
    Today ● About ● SHACLCore ○ Example walkthrough ● SHACL Compact syntax ● SHACL-SPARQL ● SHACL operations
  • 4.
    SHACL Describes what thedata looks like W3C standard: https://www.w3.org/TR/shacl/ Use for: ● Validation ● Schema ● HTML forms ● . . .
  • 5.
    SHACL-AF Also “SHACL Advancedfeatures” : https://www.w3.org/TR/shacl-af/ ● Custom Targets ● Rules ● Node expressions ● Functions Active Community Group https://www.w3.org/community/shacl/
  • 6.
    Why validate? ● Unexpecteddata makes applications harder to write ● Unexpected data in a database is hard to clean up ● External data may be missing/incomplete/changed/. . . ● Unnoticed data changes Unexpected or missing data is a signal Доверяй, но проверяй “Trust but verify” -- Russian Proverb
  • 7.
    SHACL schema:PersonShape a sh:NodeShape ; sh:targetClassfoaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:lessThan foaf:deathDate ; sh:maxCount 1 ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] .
  • 8.
    SHACL schema:PersonShape a sh:NodeShape ; sh:targetClassfoaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:lessThan foaf:deathDate ; sh:maxCount 1 ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . Example data :AlbertEinstein a foaf:Person ; foaf:givenName "Albert" ; foaf:familyName "Einstein" ; foaf:birthDate "1979-03-14"^^xsd:date ; foaf:deathDate "1955-04-18"^^xsd:date ; . Validation ● Good: foaf:givenName ● No foaf:AddressShape (not required) ● foaf:familyName -- not matched ● Bad: foaf:birthDate
  • 9.
    Validation Report [ ash:ValidationReport ; sh:conforms false ; sh:result [ a sh:ValidationResult ; sh:focusNode :AlbertEinstein ; sh:resultMessage "..." ; sh:resultPath foaf:birthDate ; sh:resultSeverity sh:Violation ; sh:sourceConstraintComponent sh:LessThanConstraintComponent ; sh:sourceShape [] ; sh:value "1979-03-14"^^xsd:date ] ] .
  • 10.
    SHACL Walkthrough schema:PersonShape a sh:NodeShape; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:lessThan foaf:deathDate ; sh:maxCount 1 ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . NodeShape URI: schema:PersonShape … applies to resources of class foaf:Person :AlbertEinstein rdf:type foaf:Person ; foaf:givenName "Albert" ; foaf:familyName "Einstein" ; foaf:birthDate "1979-03-14"^^xsd:date ; foaf:deathDate "1955-04-18"^^xsd:date ; .
  • 11.
    SHACL Walkthrough schema:PersonShape a sh:NodeShape; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:lessThan foaf:deathDate ; sh:maxCount 1 ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . Property Shape … property foaf:givenName :AlbertEinstein rdf:type foaf:Person ; foaf:givenName "Albert" ; foaf:familyName "Einstein" ; foaf:birthDate "1979-03-14"^^xsd:date ; foaf:deathDate "1955-04-18"^^xsd:date ; .
  • 12.
    SHACL Walkthrough schema:PersonShape a sh:NodeShape; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:lessThan foaf:deathDate ; sh:maxCount 1 ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . … property foaf:givenName … … object must be an xsd:string :AlbertEinstein rdf:type foaf:Person ; foaf:givenName "Albert" ; foaf:familyName "Einstein" ; foaf:birthDate "1979-03-14"^^xsd:date ; foaf:deathDate "1955-04-18"^^xsd:date ; .
  • 13.
    SHACL Walkthrough schema:PersonShape a sh:NodeShape; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:maxCount 1 ; sh:lessThan foaf:deathDate ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . … property foaf:birthDate … … there must be at most one :AlbertEinstein rdf:type foaf:Person ; foaf:givenName "Albert" ; foaf:familyName "Einstein" ; foaf:birthDate "1979-03-14"^^xsd:date ; foaf:deathDate "1955-04-18"^^xsd:date ; .
  • 14.
    SHACL Walkthrough schema:PersonShape a sh:NodeShape; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:maxCount 1 ; sh:lessThan foaf:deathDate ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . … property foaf:birthDate … … value must be less than all values of foaf:deathDate :AlbertEinstein rdf:type foaf:Person ; foaf:givenName "Albert" ; foaf:familyName "Einstein" ; foaf:birthDate "1979-03-14"^^xsd:date ; foaf:deathDate "1955-04-18"^^xsd:date ; .
  • 15.
    SHACL Walkthrough schema:PersonShape a sh:NodeShape; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:maxCount 1 ; sh:lessThan foaf:deathDate ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . … property schema:address … … conforms to another node shape
  • 16.
    SHACL Compact Syntax schema:PersonShape ash:NodeShape ; sh:targetClass foaf:Person ; sh:property [ sh:path foaf:givenName ; sh:datatype xsd:string ; ] ; sh:property [ sh:path foaf:birthDate ; sh:lessThan foaf:deathDate ; sh:maxCount 1 ; ] ; sh:property [ sh:path foaf:address ; sh:node foaf:AddressShape ; ] . shape schema:PersonShape -> foaf:Person { foaf:givenName datatype=xsd:string . foaf:birthDate [0..1] lessThan=foaf:deathDate . foaf:address @foaf:AddressShape . }
  • 17.
    Targets Classes ● sh:targetClass ● Implicit(with the class declaration) sh:targetSubjectsOf property ● c.f. rdfs:domain sh:targetObjectsOf property ● c.f. rdfs:range sh:node ● Specific node SPARQL targets (SHACL-af)
  • 18.
    SHACL Core :Key concepts Targets -- starting points Node shapes Property shapes and Paths -- routes from starting points to nodes to validate Constraints -- validations
  • 19.
    Apache Jena https://jena.apache.org/documentation/shacl/ ● SHACLCore, SHACL SPARQL (the REC) ● SHACL Compact syntax - read and write ● Command line tools ○ Parse and print ○ Validate ● Fuseki service ○ Validate graph ○ Validate at node
  • 20.
    SHACL SPARQL Constraints PREFIXrdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#> PREFIX xsd: <http://www.w3.org/2001/XMLSchema#> PREFIX sh: <http://www.w3.org/ns/shacl#> PREFIX ex: <http://example/> ## SHAPES ex:prefixes sh:declare [ sh:prefix "rdfs"; sh:namespace "http://www.w3.org/2000/01/rdf-schema#"^^xsd:anyURI; ] . :sparqlShape sh:targetClass :CLASS ; sh:sparql [ # Test language tag is in capitals sh:prefixes ex:prefixes ; # Query to return violations. sh:select """ SELECT $this ?value WHERE { $this rdfs:label ?value . BIND(lang(?value) AS ?X) FILTER (!isLiteral(?value) || lcase(?X) != ?X) } """ ; ] . One violation for each result of the query.
  • 21.
    SHACL Idiom PREFIX rdf:<http://www.w3.org/1999/02/22-rdf-syntax-ns#> PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#> PREFIX xsd: <http://www.w3.org/2001/XMLSchema#> PREFIX sh: <http://www.w3.org/ns/shacl#> PREFIX ex: <http://example/> ## Test whether the data graph is empty. ex:global a sh:NodeShape ; sh:targetNode ex:anything ; sh:sparql [ sh:select "SELECT * { ?s ?p ?o } LIMIT 1" ; ] .
  • 22.
  • 23.