sparql 3.1.5 → 3.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (144) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +35 -28
  3. data/VERSION +1 -1
  4. data/bin/sparql +14 -4
  5. data/lib/sparql/algebra/aggregate.rb +1 -1
  6. data/lib/sparql/algebra/evaluatable.rb +4 -4
  7. data/lib/sparql/algebra/expression.rb +4 -1
  8. data/lib/sparql/algebra/extensions.rb +96 -29
  9. data/lib/sparql/algebra/operator/abs.rb +23 -3
  10. data/lib/sparql/algebra/operator/add.rb +21 -2
  11. data/lib/sparql/algebra/operator/alt.rb +26 -2
  12. data/lib/sparql/algebra/operator/and.rb +25 -3
  13. data/lib/sparql/algebra/operator/asc.rb +20 -1
  14. data/lib/sparql/algebra/operator/ask.rb +17 -1
  15. data/lib/sparql/algebra/operator/avg.rb +18 -2
  16. data/lib/sparql/algebra/operator/base.rb +18 -1
  17. data/lib/sparql/algebra/operator/bgp.rb +5 -1
  18. data/lib/sparql/algebra/operator/bnode.rb +34 -11
  19. data/lib/sparql/algebra/operator/bound.rb +22 -1
  20. data/lib/sparql/algebra/operator/ceil.rb +26 -3
  21. data/lib/sparql/algebra/operator/clear.rb +16 -2
  22. data/lib/sparql/algebra/operator/coalesce.rb +33 -11
  23. data/lib/sparql/algebra/operator/compare.rb +48 -33
  24. data/lib/sparql/algebra/operator/concat.rb +26 -2
  25. data/lib/sparql/algebra/operator/construct.rb +31 -7
  26. data/lib/sparql/algebra/operator/contains.rb +25 -3
  27. data/lib/sparql/algebra/operator/copy.rb +19 -2
  28. data/lib/sparql/algebra/operator/count.rb +18 -2
  29. data/lib/sparql/algebra/operator/create.rb +19 -2
  30. data/lib/sparql/algebra/operator/dataset.rb +17 -0
  31. data/lib/sparql/algebra/operator/datatype.rb +26 -7
  32. data/lib/sparql/algebra/operator/day.rb +24 -6
  33. data/lib/sparql/algebra/operator/delete.rb +27 -2
  34. data/lib/sparql/algebra/operator/delete_data.rb +23 -2
  35. data/lib/sparql/algebra/operator/delete_where.rb +24 -2
  36. data/lib/sparql/algebra/operator/desc.rb +20 -1
  37. data/lib/sparql/algebra/operator/describe.rb +27 -4
  38. data/lib/sparql/algebra/operator/distinct.rb +18 -1
  39. data/lib/sparql/algebra/operator/divide.rb +27 -3
  40. data/lib/sparql/algebra/operator/drop.rb +17 -2
  41. data/lib/sparql/algebra/operator/encode_for_uri.rb +25 -3
  42. data/lib/sparql/algebra/operator/equal.rb +13 -3
  43. data/lib/sparql/algebra/operator/exists.rb +28 -4
  44. data/lib/sparql/algebra/operator/exprlist.rb +12 -1
  45. data/lib/sparql/algebra/operator/extend.rb +33 -18
  46. data/lib/sparql/algebra/operator/filter.rb +27 -5
  47. data/lib/sparql/algebra/operator/floor.rb +26 -3
  48. data/lib/sparql/algebra/operator/graph.rb +13 -0
  49. data/lib/sparql/algebra/operator/greater_than.rb +14 -4
  50. data/lib/sparql/algebra/operator/greater_than_or_equal.rb +14 -4
  51. data/lib/sparql/algebra/operator/group.rb +34 -8
  52. data/lib/sparql/algebra/operator/group_concat.rb +20 -8
  53. data/lib/sparql/algebra/operator/hours.rb +24 -6
  54. data/lib/sparql/algebra/operator/if.rb +21 -4
  55. data/lib/sparql/algebra/operator/in.rb +18 -1
  56. data/lib/sparql/algebra/operator/insert.rb +22 -2
  57. data/lib/sparql/algebra/operator/insert_data.rb +23 -2
  58. data/lib/sparql/algebra/operator/iri.rb +22 -5
  59. data/lib/sparql/algebra/operator/is_blank.rb +20 -2
  60. data/lib/sparql/algebra/operator/is_iri.rb +20 -2
  61. data/lib/sparql/algebra/operator/is_literal.rb +20 -2
  62. data/lib/sparql/algebra/operator/is_numeric.rb +22 -4
  63. data/lib/sparql/algebra/operator/is_triple.rb +62 -0
  64. data/lib/sparql/algebra/operator/join.rb +22 -1
  65. data/lib/sparql/algebra/operator/lang.rb +26 -1
  66. data/lib/sparql/algebra/operator/lang_matches.rb +23 -2
  67. data/lib/sparql/algebra/operator/lcase.rb +24 -3
  68. data/lib/sparql/algebra/operator/left_join.rb +29 -1
  69. data/lib/sparql/algebra/operator/less_than.rb +14 -4
  70. data/lib/sparql/algebra/operator/less_than_or_equal.rb +14 -4
  71. data/lib/sparql/algebra/operator/load.rb +25 -2
  72. data/lib/sparql/algebra/operator/max.rb +18 -2
  73. data/lib/sparql/algebra/operator/md5.rb +23 -6
  74. data/lib/sparql/algebra/operator/min.rb +19 -3
  75. data/lib/sparql/algebra/operator/minus.rb +25 -7
  76. data/lib/sparql/algebra/operator/minutes.rb +24 -6
  77. data/lib/sparql/algebra/operator/modify.rb +41 -5
  78. data/lib/sparql/algebra/operator/month.rb +24 -6
  79. data/lib/sparql/algebra/operator/move.rb +20 -2
  80. data/lib/sparql/algebra/operator/multiply.rb +27 -4
  81. data/lib/sparql/algebra/operator/negate.rb +24 -4
  82. data/lib/sparql/algebra/operator/not.rb +25 -4
  83. data/lib/sparql/algebra/operator/not_equal.rb +16 -1
  84. data/lib/sparql/algebra/operator/notexists.rb +30 -6
  85. data/lib/sparql/algebra/operator/notin.rb +20 -3
  86. data/lib/sparql/algebra/operator/notoneof.rb +12 -2
  87. data/lib/sparql/algebra/operator/now.rb +25 -6
  88. data/lib/sparql/algebra/operator/object.rb +59 -0
  89. data/lib/sparql/algebra/operator/or.rb +26 -3
  90. data/lib/sparql/algebra/operator/order.rb +27 -2
  91. data/lib/sparql/algebra/operator/path.rb +29 -2
  92. data/lib/sparql/algebra/operator/path_opt.rb +21 -2
  93. data/lib/sparql/algebra/operator/path_plus.rb +21 -2
  94. data/lib/sparql/algebra/operator/path_star.rb +20 -2
  95. data/lib/sparql/algebra/operator/plus.rb +43 -4
  96. data/lib/sparql/algebra/operator/predicate.rb +59 -0
  97. data/lib/sparql/algebra/operator/prefix.rb +24 -3
  98. data/lib/sparql/algebra/operator/project.rb +51 -5
  99. data/lib/sparql/algebra/operator/rand.rb +31 -3
  100. data/lib/sparql/algebra/operator/reduced.rb +18 -1
  101. data/lib/sparql/algebra/operator/regex.rb +27 -19
  102. data/lib/sparql/algebra/operator/replace.rb +27 -7
  103. data/lib/sparql/algebra/operator/reverse.rb +20 -2
  104. data/lib/sparql/algebra/operator/round.rb +26 -3
  105. data/lib/sparql/algebra/operator/same_term.rb +25 -7
  106. data/lib/sparql/algebra/operator/sample.rb +31 -9
  107. data/lib/sparql/algebra/operator/seconds.rb +24 -6
  108. data/lib/sparql/algebra/operator/seq.rb +20 -2
  109. data/lib/sparql/algebra/operator/sequence.rb +0 -10
  110. data/lib/sparql/algebra/operator/sha1.rb +19 -2
  111. data/lib/sparql/algebra/operator/sha256.rb +19 -2
  112. data/lib/sparql/algebra/operator/sha384.rb +19 -2
  113. data/lib/sparql/algebra/operator/sha512.rb +19 -2
  114. data/lib/sparql/algebra/operator/slice.rb +27 -5
  115. data/lib/sparql/algebra/operator/str.rb +22 -2
  116. data/lib/sparql/algebra/operator/strafter.rb +26 -3
  117. data/lib/sparql/algebra/operator/strbefore.rb +26 -3
  118. data/lib/sparql/algebra/operator/strdt.rb +23 -2
  119. data/lib/sparql/algebra/operator/strends.rb +26 -4
  120. data/lib/sparql/algebra/operator/strlang.rb +26 -7
  121. data/lib/sparql/algebra/operator/strlen.rb +24 -3
  122. data/lib/sparql/algebra/operator/strstarts.rb +26 -3
  123. data/lib/sparql/algebra/operator/struuid.rb +30 -10
  124. data/lib/sparql/algebra/operator/subject.rb +61 -0
  125. data/lib/sparql/algebra/operator/substr.rb +24 -3
  126. data/lib/sparql/algebra/operator/subtract.rb +29 -3
  127. data/lib/sparql/algebra/operator/sum.rb +18 -2
  128. data/lib/sparql/algebra/operator/table.rb +42 -4
  129. data/lib/sparql/algebra/operator/timezone.rb +24 -6
  130. data/lib/sparql/algebra/operator/tz.rb +23 -6
  131. data/lib/sparql/algebra/operator/ucase.rb +24 -3
  132. data/lib/sparql/algebra/operator/union.rb +29 -6
  133. data/lib/sparql/algebra/operator/update.rb +25 -4
  134. data/lib/sparql/algebra/operator/using.rb +32 -2
  135. data/lib/sparql/algebra/operator/uuid.rb +28 -9
  136. data/lib/sparql/algebra/operator/with.rb +38 -4
  137. data/lib/sparql/algebra/operator/year.rb +24 -6
  138. data/lib/sparql/algebra/operator.rb +112 -7
  139. data/lib/sparql/algebra/sxp_extensions.rb +3 -3
  140. data/lib/sparql/grammar/meta.rb +5390 -2410
  141. data/lib/sparql/grammar/parser11.rb +119 -53
  142. data/lib/sparql/grammar/terminals11.rb +2 -0
  143. data/lib/sparql/grammar.rb +0 -25
  144. metadata +40 -34
@@ -3,13 +3,16 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL GraphPattern `minus` operator.
5
5
  #
6
- # @example
7
- # (prefix ((ex: <http://www.w3.org/2009/sparql/docs/tests/data-sparql11/negation#>))
8
- # (project (?animal)
9
- # (minus
10
- # (bgp (triple ?animal <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> ex:Animal))
11
- # (filter (|| (= ?type ex:Reptile) (= ?type ex:Insect))
12
- # (bgp (triple ?animal <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> ?type))))))
6
+ # [66] MinusGraphPattern ::= 'MINUS' GroupGraphPattern
7
+ #
8
+ # @example SPARQL Grammar
9
+ # SELECT * { ?s ?p ?o MINUS { ?s ?q ?v } }
10
+ #
11
+ # @example SSE
12
+ # (minus
13
+ # (bgp
14
+ # (triple ?s ?p ?o))
15
+ # (bgp (triple ?s ?q ?v)))
13
16
  #
14
17
  # @see https://www.w3.org/TR/xpath-functions/#func-numeric-unary-minus
15
18
  # @see https://www.w3.org/TR/sparql11-query/#sparqlAlgebra
@@ -66,6 +69,21 @@ module SPARQL; module Algebra
66
69
  @operands = ops
67
70
  self
68
71
  end
72
+
73
+ ##
74
+ #
75
+ # Returns a partial SPARQL grammar for this operator.
76
+ #
77
+ # @param [Boolean] top_level (true)
78
+ # Treat this as a top-level, generating SELECT ... WHERE {}
79
+ # @return [String]
80
+ def to_sparql(top_level: true, **options)
81
+ str = operands.first.to_sparql(top_level: false, **options) + "\n"
82
+ str << "MINUS {\n"
83
+ str << operands.last.to_sparql(top_level: false, **options)
84
+ str << "\n}"
85
+ top_level ? Operator.to_sparql(str, **options) : str
86
+ end
69
87
  end # Minus
70
88
  end # Operator
71
89
  end; end # SPARQL::Algebra
@@ -5,11 +5,20 @@ module SPARQL; module Algebra
5
5
  #
6
6
  # Returns the minutes part of the lexical form of `arg`. The value is as given in the lexical form of the XSD dateTime.
7
7
  #
8
- # @example
9
- # (prefix ((: <http://example.org/>))
10
- # (project (?s ?x)
11
- # (extend ((?x (minutes ?date)))
12
- # (bgp (triple ?s :date ?date)))))
8
+ # [121] BuiltInCall ::= ... | 'MINUTES' '(' Expression ')'
9
+ #
10
+ # @example SPARQL Grammar
11
+ # PREFIX : <http://example.org/>
12
+ # SELECT ?s (MINUTES(?date) AS ?x) WHERE {
13
+ # ?s :date ?date
14
+ # }
15
+ #
16
+ # @example SSE
17
+ # (prefix
18
+ # ((: <http://example.org/>))
19
+ # (project (?s ?x)
20
+ # (extend ((?x (minutes ?date)))
21
+ # (bgp (triple ?s :date ?date)))))
13
22
  #
14
23
  # @see https://www.w3.org/TR/sparql11-query/#func-minutes
15
24
  class Minutes < Operator::Unary
@@ -24,10 +33,19 @@ module SPARQL; module Algebra
24
33
  # the operand
25
34
  # @return [RDF::Literal]
26
35
  # @raise [TypeError] if the operand is not a simple literal
27
- def apply(operand)
36
+ def apply(operand, **options)
28
37
  raise TypeError, "expected an RDF::Literal::DateTime, but got #{operand.inspect}" unless operand.is_a?(RDF::Literal::DateTime)
29
38
  RDF::Literal(operand.object.minute)
30
39
  end
40
+
41
+ ##
42
+ #
43
+ # Returns a partial SPARQL grammar for this operator.
44
+ #
45
+ # @return [String]
46
+ def to_sparql(**options)
47
+ "MINUTES(#{operands.last.to_sparql(**options)})"
48
+ end
31
49
  end # Minutes
32
50
  end # Operator
33
51
  end; end # SPARQL::Algebra
@@ -6,11 +6,23 @@ module SPARQL; module Algebra
6
6
  #
7
7
  # Wraps delete/insert
8
8
  #
9
- # @example
10
- # (modify
11
- # (bgp (triple ?a foaf:knows ?b))
12
- # (delete ((triple ?a foaf:knows ?b)))
13
- # (insert ((triple ?b foaf:knows ?a)))
9
+ # [41] Modify ::= ( 'WITH' iri )? ( DeleteClause InsertClause? | InsertClause ) UsingClause* 'WHERE' GroupGraphPattern
10
+ #
11
+ # @example SPARQL Grammar
12
+ # PREFIX : <http://example.org/>
13
+ # PREFIX foaf: <http://xmlns.com/foaf/0.1/>
14
+ # DELETE { ?a foaf:knows ?b }
15
+ # INSERT { ?b foaf:knows ?a }
16
+ # WHERE { ?a foaf:knows ?b }
17
+ #
18
+ # @example SSE
19
+ # (prefix ((: <http://example.org/>)
20
+ # (foaf: <http://xmlns.com/foaf/0.1/>))
21
+ # (update
22
+ # (modify
23
+ # (bgp (triple ?a foaf:knows ?b))
24
+ # (delete ((triple ?a foaf:knows ?b)))
25
+ # (insert ((triple ?b foaf:knows ?a)))) ))
14
26
  #
15
27
  # @see XXX
16
28
  class Modify < Operator
@@ -48,6 +60,30 @@ module SPARQL; module Algebra
48
60
  end
49
61
  queryable
50
62
  end
63
+
64
+ ##
65
+ #
66
+ # Returns a partial SPARQL grammar for this operator.
67
+ #
68
+ # @return [String]
69
+ def to_sparql(**options)
70
+ if operands.first.is_a?(With)
71
+ operands.first.to_sparql(**options)
72
+ else
73
+ # The content of the WHERE clause, may be USING
74
+ content = operands.first.to_sparql(top_level: false, **options)
75
+
76
+ # DELETE | INSERT | DELETE INSERT
77
+ str = operands[1..-1].to_sparql(top_level: false, delimiter: "\n", **options) + "\n"
78
+
79
+ # Append the WHERE or USING clause
80
+ str << if operands.first.is_a?(Using)
81
+ content
82
+ else
83
+ Operator.to_sparql(content, project: nil, **options)
84
+ end
85
+ end
86
+ end
51
87
  end # Modify
52
88
  end # Operator
53
89
  end; end # SPARQL::Algebra
@@ -5,11 +5,20 @@ module SPARQL; module Algebra
5
5
  #
6
6
  # Returns the month part of `arg` as an integer.
7
7
  #
8
- # @example
9
- # (prefix ((: <http://example.org/>))
10
- # (project (?s ?x)
11
- # (extend ((?x (month ?date)))
12
- # (bgp (triple ?s :date ?date)))))
8
+ # [121] BuiltInCall ::= ... | 'MONTH' '(' Expression ')'
9
+ #
10
+ # @example SPARQL Grammar
11
+ # PREFIX : <http://example.org/>
12
+ # SELECT ?s (MONTH(?date) AS ?x) WHERE {
13
+ # ?s :date ?date
14
+ # }
15
+ #
16
+ # @example SSE
17
+ # (prefix
18
+ # ((: <http://example.org/>))
19
+ # (project (?s ?x)
20
+ # (extend ((?x (month ?date)))
21
+ # (bgp (triple ?s :date ?date)))))
13
22
  #
14
23
  # @see https://www.w3.org/TR/sparql11-query/#func-month
15
24
  class Month < Operator::Unary
@@ -24,10 +33,19 @@ module SPARQL; module Algebra
24
33
  # the operand
25
34
  # @return [RDF::Literal]
26
35
  # @raise [TypeError] if the operand is not a simple literal
27
- def apply(operand)
36
+ def apply(operand, **options)
28
37
  raise TypeError, "expected an RDF::Literal::DateTime, but got #{operand.inspect}" unless operand.is_a?(RDF::Literal::DateTime)
29
38
  RDF::Literal(operand.object.month)
30
39
  end
40
+
41
+ ##
42
+ #
43
+ # Returns a partial SPARQL grammar for this operator.
44
+ #
45
+ # @return [String]
46
+ def to_sparql(**options)
47
+ "MONTH(#{operands.last.to_sparql(**options)})"
48
+ end
31
49
  end # Month
32
50
  end # Operator
33
51
  end; end # SPARQL::Algebra
@@ -6,8 +6,14 @@ module SPARQL; module Algebra
6
6
  #
7
7
  # The MOVE operation is a shortcut for moving all data from an input graph into a destination graph. The input graph is removed after insertion and data from the destination graph, if any, is removed before insertion.
8
8
  #
9
- # @example
10
- # (move silent <iri> to default)
9
+ # [36] Move ::= 'MOVE' 'SILENT'? GraphOrDefault 'TO' GraphOrDefault
10
+ #
11
+ # @example SPARQL Grammar
12
+ # MOVE SILENT GRAPH <http://www.example.com/g1> TO DEFAULT
13
+ #
14
+ # @example SSE
15
+ # (update
16
+ # (move silent <http://www.example.com/g1> default))
11
17
  #
12
18
  # @see https://www.w3.org/TR/sparql11-update/#move
13
19
  class Move < Operator
@@ -62,6 +68,18 @@ module SPARQL; module Algebra
62
68
  end
63
69
  queryable
64
70
  end
71
+
72
+ ##
73
+ #
74
+ # Returns a partial SPARQL grammar for this operator.
75
+ #
76
+ # @return [String]
77
+ def to_sparql(**options)
78
+ *args, last = operands.dup
79
+ args += [:TO, last]
80
+
81
+ "MOVE " + args.to_sparql(**options)
82
+ end
65
83
  end # Move
66
84
  end # Operator
67
85
  end; end # SPARQL::Algebra
@@ -3,9 +3,23 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL numeric `multiply` operator.
5
5
  #
6
- # @example
7
- # (* ?x ?y)
8
- # (multiply ?x ?y)
6
+ # [117] MultiplicativeExpression::= UnaryExpression ( '*' UnaryExpression | '/' UnaryExpression )*
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX : <http://example.org/>
10
+ # SELECT ?s WHERE {
11
+ # ?s :p ?o .
12
+ # ?s2 :p ?o2 .
13
+ # FILTER(?o * ?o2 = 4) .
14
+ # }
15
+ #
16
+ # @example SSE
17
+ # (prefix ((: <http://example.org/>))
18
+ # (project (?s)
19
+ # (filter (= (* ?o ?o2) 4)
20
+ # (bgp
21
+ # (triple ?s :p ?o)
22
+ # (triple ?s2 :p ?o2)))))
9
23
  #
10
24
  # @see https://www.w3.org/TR/xpath-functions/#func-numeric-multiply
11
25
  class Multiply < Operator::Binary
@@ -22,13 +36,22 @@ module SPARQL; module Algebra
22
36
  # a numeric literal
23
37
  # @return [RDF::Literal::Numeric]
24
38
  # @raise [TypeError] if either operand is not a numeric literal
25
- def apply(left, right)
39
+ def apply(left, right, **options)
26
40
  case
27
41
  when left.is_a?(RDF::Literal::Numeric) && right.is_a?(RDF::Literal::Numeric)
28
42
  left * right
29
43
  else raise TypeError, "expected two RDF::Literal::Numeric operands, but got #{left.inspect} and #{right.inspect}"
30
44
  end
31
45
  end
46
+
47
+ ##
48
+ #
49
+ # Returns a partial SPARQL grammar for this operator.
50
+ #
51
+ # @return [String]
52
+ def to_sparql(**options)
53
+ "#{operands.first.to_sparql(**options)} * #{operands.last.to_sparql(**options)}"
54
+ end
32
55
  end # Multiply
33
56
  end # Operator
34
57
  end; end # SPARQL::Algebra
@@ -3,9 +3,20 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL numeric unary `-` (negation) operator.
5
5
  #
6
- # @example
7
- # (- ?x)
8
- # (negate ?x)
6
+ # [118] UnaryExpression ::= ... | '-' PrimaryExpression
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX : <http://example.org/>
10
+ # SELECT ?s WHERE {
11
+ # ?s :p ?o .
12
+ # FILTER(-?o = -2) .
13
+ # }
14
+ #
15
+ # @example SSE
16
+ # (prefix ((: <http://example.org/>))
17
+ # (project (?s)
18
+ # (filter (= (- ?o) -2)
19
+ # (bgp (triple ?s :p ?o)))))
9
20
  #
10
21
  # @see https://www.w3.org/TR/xpath-functions/#func-numeric-unary-minus
11
22
  class Negate < Operator::Unary
@@ -20,12 +31,21 @@ module SPARQL; module Algebra
20
31
  # a numeric literal
21
32
  # @return [RDF::Literal::Numeric]
22
33
  # @raise [TypeError] if the operand is not a numeric literal
23
- def apply(term)
34
+ def apply(term, **options)
24
35
  case term
25
36
  when RDF::Literal::Numeric then -term
26
37
  else raise TypeError, "expected an RDF::Literal::Numeric, but got #{term.inspect}"
27
38
  end
28
39
  end
40
+
41
+ ##
42
+ #
43
+ # Returns a partial SPARQL grammar for this operator.
44
+ #
45
+ # @return [String]
46
+ def to_sparql(**options)
47
+ "(-#{operands.to_sparql(**options)})"
48
+ end
29
49
  end # Negate
30
50
  end # Operator
31
51
  end; end # SPARQL::Algebra
@@ -3,9 +3,21 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL logical `not` operator.
5
5
  #
6
- # @example
7
- # (! ?x)
8
- # (not ?x)
6
+ # [118] UnaryExpression ::= ... | '!' PrimaryExpression
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX : <http://example.org/ns#>
10
+ # SELECT ?a
11
+ # WHERE {
12
+ # ?a :p ?v .
13
+ # FILTER ( ! ?v ) .
14
+ # }
15
+ #
16
+ # @example SSE
17
+ # (prefix ((: <http://example.org/ns#>))
18
+ # (project (?a)
19
+ # (filter (! ?v)
20
+ # (bgp (triple ?a :p ?v)))))
9
21
  #
10
22
  # @see https://www.w3.org/TR/xpath-functions/#func-not
11
23
  class Not < Operator::Unary
@@ -23,13 +35,22 @@ module SPARQL; module Algebra
23
35
  # the operand
24
36
  # @return [RDF::Literal::Boolean] `true` or `false`
25
37
  # @raise [TypeError] if the operand could not be coerced to a boolean literal
26
- def apply(operand)
38
+ def apply(operand, **options)
27
39
  case bool = boolean(operand)
28
40
  when RDF::Literal::Boolean
29
41
  RDF::Literal(bool.false?)
30
42
  else super
31
43
  end
32
44
  end
45
+
46
+ ##
47
+ #
48
+ # Returns a partial SPARQL grammar for this operator.
49
+ #
50
+ # @return [String]
51
+ def to_sparql(**options)
52
+ "(!" + operands.first.to_sparql(**options) + ")"
53
+ end
33
54
  end # Not
34
55
  end # Operator
35
56
  end; end # SPARQL::Algebra
@@ -3,6 +3,19 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL relational `!=` (not equal) comparison operator.
5
5
  #
6
+ # [114] RelationalExpression ::= NumericExpression ('!=' NumericExpression)?
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
10
+ # PREFIX : <http://example.org/things#>
11
+ # SELECT ?x
12
+ # WHERE { ?x :p ?v . FILTER ( ?v != 1 ) }
13
+ #
14
+ # @example SSE
15
+ # (prefix
16
+ # ((xsd: <http://www.w3.org/2001/XMLSchema#>) (: <http://example.org/things#>))
17
+ # (project (?x) (filter (!= ?v 1) (bgp (triple ?x :p ?v)))))
18
+ #
6
19
  # @see https://www.w3.org/TR/sparql11-query/#OperatorMapping
7
20
  # @see https://www.w3.org/TR/sparql11-query/#func-RDFterm-equal
8
21
  class NotEqual < Equal
@@ -12,13 +25,15 @@ module SPARQL; module Algebra
12
25
  # Returns `true` if the operands are not equal; returns `false`
13
26
  # otherwise.
14
27
  #
28
+ # Comparing unknown datatypes might have different lexical forms but be the same value.
29
+ #
15
30
  # @param [RDF::Term] term1
16
31
  # an RDF term
17
32
  # @param [RDF::Term] term2
18
33
  # an RDF term
19
34
  # @return [RDF::Literal::Boolean] `true` or `false`
20
35
  # @raise [TypeError] if either operand is not an RDF term
21
- def apply(term1, term2)
36
+ def apply(term1, term2, **options)
22
37
  RDF::Literal(super.false?)
23
38
  end
24
39
  end # NotEqual
@@ -5,12 +5,23 @@ module SPARQL; module Algebra
5
5
  #
6
6
  # There is a filter operator EXISTS that takes a graph pattern. EXISTS returns `true`/`false` depending on whether the pattern matches the dataset given the bindings in the current group graph pattern, the dataset and the active graph at this point in the query evaluation. No additional binding of variables occurs. The `NOT EXISTS` form translates into `fn:not(EXISTS{...})`.
7
7
  #
8
- # @example
9
- # (prefix ((ex: <http://www.example.org/>))
10
- # (filter (exists
11
- # (filter (notexists (bgp (triple ?s ?p ex:o2)))
12
- # (bgp (triple ?s ?p ex:o1))))
13
- # (bgp (triple ?s ?p ex:o))))
8
+ # [126] NotExistsFunc ::= 'NOT' 'EXISTS' GroupGraphPattern
9
+ #
10
+ # @example SPARQL Grammar
11
+ # PREFIX ex: <http://www.w3.org/2009/sparql/docs/tests/data-sparql11/negation#>
12
+ # SELECT ?animal {
13
+ # ?animal a ex:Animal
14
+ # FILTER NOT EXISTS { ?animal a ex:Insect }
15
+ # }
16
+ #
17
+ # @example SSE
18
+ # (prefix
19
+ # ((ex: <http://www.w3.org/2009/sparql/docs/tests/data-sparql11/negation#>))
20
+ # (project (?animal)
21
+ # (filter
22
+ # (notexists
23
+ # (bgp (triple ?animal a ex:Insect)))
24
+ # (bgp (triple ?animal a ex:Animal)))) )
14
25
  #
15
26
  # @see https://www.w3.org/TR/sparql11-query/#func-abs
16
27
  # @see https://www.w3.org/TR/xpath-functions/#func-abs
@@ -34,6 +45,19 @@ module SPARQL; module Algebra
34
45
  queryable = options[:queryable]
35
46
  operand(0).execute(queryable, solutions: solutions, **options).empty?
36
47
  end
48
+
49
+ ##
50
+ #
51
+ # Returns a partial SPARQL grammar for this operator.
52
+ #
53
+ # @param [Boolean] top_level (true)
54
+ # Treat this as a top-level, generating SELECT ... WHERE {}
55
+ # @return [String]
56
+ def to_sparql(top_level: true, **options)
57
+ "NOT EXISTS {\n" +
58
+ operands.last.to_sparql(top_level: false, **options) +
59
+ "\n}"
60
+ end
37
61
  end # NotExists
38
62
  end # Operator
39
63
  end; end # SPARQL::Algebra
@@ -5,8 +5,13 @@ module SPARQL; module Algebra
5
5
  #
6
6
  # Used for filters with more than one expression.
7
7
  #
8
- # @example
9
- # (ask (filter (notin ?o 1 2) (bgp)))
8
+ # [114] RelationalExpression ::= NumericExpression ('NOT' 'IN' ExpressionList)?
9
+ #
10
+ # @example SPARQL Grammar
11
+ # ASK { FILTER(2 NOT IN ()) }
12
+ #
13
+ # @example SSE
14
+ # (ask (filter (notin 2) (bgp)))
10
15
  #
11
16
  # @see https://www.w3.org/TR/sparql11-query/#func-notin
12
17
  class NotIn < Operator
@@ -58,6 +63,18 @@ module SPARQL; module Algebra
58
63
  else RDF::Literal::TRUE
59
64
  end
60
65
  end
61
- end # Exprlist
66
+
67
+ ##
68
+ #
69
+ # Returns a partial SPARQL grammar for this operator.
70
+ #
71
+ # @return [String]
72
+ def to_sparql(**options)
73
+ "(" + operands.first.to_sparql(**options) +
74
+ " NOT IN (" +
75
+ operands[1..-1].map {|e| e.to_sparql(**options)}.join(", ") +
76
+ "))"
77
+ end
78
+ end # NotIn
62
79
  end # Operator
63
80
  end; end # SPARQL::Algebra
@@ -3,8 +3,18 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL Property Path `notoneof` (NegatedPropertySet) operator.
5
5
  #
6
- # @example
7
- # (notoneof ex:p1 ex:p2)
6
+ # [96] PathOneInPropertySet ::= iri | 'a' | '^' ( iri | 'a' )
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX ex: <http://www.example.org/schema#>
10
+ # PREFIX in: <http://www.example.org/instance#>
11
+ # ASK { in:b ^ex:p in:a }
12
+ #
13
+ # @example SSE
14
+ # (prefix ((ex: <http://www.example.org/schema#>)
15
+ # (in: <http://www.example.org/instance#>))
16
+ # (ask
17
+ # (path in:b (reverse ex:p) in:a)))
8
18
  #
9
19
  # @see https://www.w3.org/TR/sparql11-query/#eval_negatedPropertySet
10
20
  class NotOneOf < Operator
@@ -7,11 +7,21 @@ module SPARQL; module Algebra
7
7
  #
8
8
  # Returns an XSD dateTime value for the current query execution. All calls to this function in any one query execution must return the same value. The exact moment returned is not specified.
9
9
  #
10
- # @example
11
- # (prefix ((xsd: <http://www.w3.org/2001/XMLSchema#>))
12
- # (ask (filter (= (datatype ?n) xsd:dateTime)
13
- # (extend ((?n (now)))
14
- # (bgp)))))
10
+ # [121] BuiltInCall ::= ... | 'NOW' NIL
11
+ #
12
+ # @example SPARQL Grammar
13
+ # PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
14
+ # ASK {
15
+ # BIND(NOW() AS ?n)
16
+ # FILTER(DATATYPE(?n) = xsd:dateTime)
17
+ # }
18
+ #
19
+ # @example SSE
20
+ # (prefix ((xsd: <http://www.w3.org/2001/XMLSchema#>))
21
+ # (ask
22
+ # (filter (= (datatype ?n) xsd:dateTime)
23
+ # (extend ((?n (now)))
24
+ # (bgp)))))
15
25
  #
16
26
  # @see https://www.w3.org/TR/sparql11-query/#func-now
17
27
  class Now < Operator::Nullary
@@ -23,9 +33,18 @@ module SPARQL; module Algebra
23
33
  # Returns an XSD dateTime value for the current query execution. All calls to this function in any one query execution must return the same value. The exact moment returned is not specified.
24
34
  #
25
35
  # @return [RDF::Literal::Double] random value
26
- def apply
36
+ def apply(**options)
27
37
  RDF::Literal(DateTime.now)
28
38
  end
39
+
40
+ ##
41
+ #
42
+ # Returns a partial SPARQL grammar for this operator.
43
+ #
44
+ # @return [String]
45
+ def to_sparql(**options)
46
+ "NOW()"
47
+ end
29
48
  end # Now
30
49
  end # Operator
31
50
  end; end # SPARQL::Algebra
@@ -0,0 +1,59 @@
1
+ module SPARQL; module Algebra
2
+ class Operator
3
+ ##
4
+ # The SPARQL `OBJECT` operator.
5
+ #
6
+ # If triple is an RDF-star triple, the function returns the object of this triple. Passing anything other than an RDF-star triple is an error.
7
+ #
8
+ # [121] BuiltInCall ::= ... | 'OBJECT' '(' Expression ')'
9
+ #
10
+ # @example SPARQL Grammar
11
+ # PREFIX : <http://example.com/ns#>
12
+ # SELECT * {
13
+ # ?t :source :g
14
+ # FILTER(isTriple(?t))
15
+ # FILTER(SUBJECT(?t) = :s)
16
+ # FILTER(PREDICATE(?t) = :p)
17
+ # FILTER(OBJECT(?t) = :o)
18
+ # }
19
+ #
20
+ # @example SSE
21
+ # (prefix
22
+ # ((: <http://example.com/ns#>))
23
+ # (filter
24
+ # (exprlist
25
+ # (isTRIPLE ?t)
26
+ # (= (subject ?t) :s)
27
+ # (= (predicate ?t) :p)
28
+ # (= (object ?t) :o))
29
+ # (bgp (triple ?t :source :g))) )
30
+ #
31
+ # @see https://w3c.github.io/rdf-star/rdf-star-cg-spec.html#object
32
+ class Object < Operator::Unary
33
+ include Evaluatable
34
+
35
+ NAME = :object
36
+
37
+ ##
38
+ # Returns the object part of arg.
39
+ #
40
+ # @param [RDF::Statement] operand
41
+ # the operand
42
+ # @return [RDF::Literal]
43
+ # @raise [TypeError] if the operand is not a statement
44
+ def apply(operand, **options)
45
+ raise TypeError, "expected an RDF::Statement, but got #{operand.inspect}" unless operand.is_a?(RDF::Statement)
46
+ operand.object
47
+ end
48
+
49
+ ##
50
+ #
51
+ # Returns a partial SPARQL grammar for this operator.
52
+ #
53
+ # @return [String]
54
+ def to_sparql(**options)
55
+ "OBJECT(" + operands.last.to_sparql(**options) + ")"
56
+ end
57
+ end # Object
58
+ end # Operator
59
+ end; end # SPARQL::Algebra
@@ -3,9 +3,23 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL logical `or` operator.
5
5
  #
6
- # @example
7
- # (|| ?x ?y)
8
- # (or ?x ?y)
6
+ # [111] ConditionalOrExpression ::= ConditionalAndExpression ( '||' ConditionalAndExpression )*
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
10
+ # PREFIX : <http://example.org/ns#>
11
+ # SELECT ?a
12
+ # WHERE {
13
+ # ?a :p ?v .
14
+ # FILTER ("false"^^xsd:boolean || ?v) .
15
+ # }
16
+ #
17
+ # @example SSE
18
+ # (prefix ((xsd: <http://www.w3.org/2001/XMLSchema#>)
19
+ # (: <http://example.org/ns#>))
20
+ # (project (?a)
21
+ # (filter (|| false ?v)
22
+ # (bgp (triple ?a :p ?v)))))
9
23
  #
10
24
  # @see https://www.w3.org/TR/sparql11-query/#func-logical-or
11
25
  # @see https://www.w3.org/TR/sparql11-query/#evaluation
@@ -63,6 +77,15 @@ module SPARQL; module Algebra
63
77
  else RDF::Literal(left || right)
64
78
  end
65
79
  end
80
+
81
+ ##
82
+ #
83
+ # Returns a partial SPARQL grammar for this operator.
84
+ #
85
+ # @return [String]
86
+ def to_sparql(**options)
87
+ "(#{operands.first.to_sparql(**options)} || #{operands.last.to_sparql(**options)})"
88
+ end
66
89
  end # Or
67
90
  end # Operator
68
91
  end; end # SPARQL::Algebra