From bcc1305c48451d8a5bc2a0a57b82af20cc17e33c Mon Sep 17 00:00:00 2001 From: Andy Pfister Date: Mon, 20 Nov 2023 15:25:56 +0100 Subject: [PATCH 1/3] Flatten closed_results before assignment I originally discovered the issue because of the following error messages in one of our tests: ``` undefined method `conform?' for [(ValidationResult (value "Undefiniert") (focus ) (path ) (shape shacl:RicoRecordResourceWithCategoryShape) (resultSeverity shacl:Violation) (component shacl:ClosedConstraintComponent) (message "closed node has extra property")) ]:Array next unless results.all?(&:conform?) ^^^^^ # /Users/apf/.rbenv/versions/3.1.4/lib/ruby/gems/3.1.0/gems/shacl-0.4.0/lib/shacl/algebra/or.rb:34:in `all?' ``` I wondered where this array was coming from and did some deep-dives using the debugger. Since both `builtin_results` and `op_results` get flattend, I assume it should be the same for `closed_results`. --- lib/shacl/algebra/node_shape.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/shacl/algebra/node_shape.rb b/lib/shacl/algebra/node_shape.rb index a144993..89c5d5f 100644 --- a/lib/shacl/algebra/node_shape.rb +++ b/lib/shacl/algebra/node_shape.rb @@ -44,7 +44,7 @@ def conforms(node, depth: 0, **options) resultSeverity: options[:severity], component: RDF::Vocab::SHACL.ClosedConstraintComponent, **options) - end.compact + end.flatten.compact elsif @options[:ignoredProperties] raise SHACL::Error, "shape has ignoredProperties without being closed" end From 0f5bd089a9b65b6887c4e04293863e7e79e43e27 Mon Sep 17 00:00:00 2001 From: Andy Pfister Date: Tue, 21 Nov 2023 18:52:52 +0100 Subject: [PATCH 2/3] Add test --- spec/shapes_spec.rb | 80 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 80 insertions(+) diff --git a/spec/shapes_spec.rb b/spec/shapes_spec.rb index c358798..f719e31 100644 --- a/spec/shapes_spec.rb +++ b/spec/shapes_spec.rb @@ -43,6 +43,86 @@ sxp: [:ValidationReport, true, []].to_sxp } } + }, + "nested node shape with closed properties": { + shape: %( + @prefix sh: . + @prefix rdfs: . + @prefix rdf: . + @prefix ex: . + + ex:WithLabelShape a sh:NodeShape ; + sh:closed true ; + sh:property [ + sh:path rdfs:label ; + sh:minCount 1 ; + sh:maxCount 1 ; + ] . + + ex:WithCommentShape a sh:NodeShape ; + sh:closed true ; + sh:property [ + sh:path rdfs:comment ; + sh:minCount 1 ; + sh:maxCount 1 ; + ] . + + ex:ResourceShape a sh:NodeShape ; + sh:targetClass ex:Resource ; + sh:or ( ex:WithLabelShape ex:WithCommentShape ) . + + ), + sxp: %{(shapes + ( + (NodeShape + (id ) + (type shacl:NodeShape) + (closed true) + (PropertyShape (id _:b0) (path rdfs:label) (minCount 1) (maxCount 1))) + (NodeShape + (id ) + (type shacl:NodeShape) + (closed true) + (PropertyShape (id _:b1) (path rdfs:comment) (minCount 1) (maxCount 1))) + (NodeShape + (id ) + (type shacl:NodeShape) + (targetClass ) + (or + (NodeShape + (id ) + (type shacl:NodeShape) + (closed true) + (PropertyShape (id _:b0) (path rdfs:label) (minCount 1) (maxCount 1))) + (NodeShape + (id ) + (type shacl:NodeShape) + (closed true) + (PropertyShape (id _:b1) (path rdfs:comment) (minCount 1) (maxCount 1))) + )) ))}, + data: { + "node which is neither of given shapes": { + input: %( + @prefix ex: . + @prefix rdfs: . + + ex:Resource1 a ex:Resource ; + rdfs:label "A Resource with a label" ; + ex:extraProperty "This should not be here" .), + valid: false, + sxp: %{ + (ValidationReport #f + ( + (ValidationResult + (value ) + (focus ) + (shape ) + (resultSeverity shacl:Violation) + (component shacl:OrConstraintComponent) + (message "node does not conform to any shape")) )) + } + } + } } }.each do |name, params| context name do From a4860f095b93dc4507b0367a07bcab1c96e9a125 Mon Sep 17 00:00:00 2001 From: Gregg Kellogg Date: Tue, 21 Nov 2023 14:44:54 -0800 Subject: [PATCH 3/3] Version 0.4.1. --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 1d0ba9e..267577d 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -0.4.0 +0.4.1