sparql 3.1.5 → 3.2.0

Sign up to get free protection for your applications and to get access to all the features.
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,7 +3,14 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL `count` set function.
5
5
  #
6
- # @example
6
+ # [127] Aggregate::= 'COUNT' '(' 'DISTINCT'? ( '*' | Expression ) ')' ...
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX : <http://www.example.org/>
10
+ # SELECT (COUNT(?O) AS ?C)
11
+ # WHERE { ?S ?P ?O }
12
+ #
13
+ # @example SSE
7
14
  # (prefix ((: <http://www.example.org>))
8
15
  # (project (?C)
9
16
  # (extend ((?C ??.0))
@@ -22,9 +29,18 @@ module SPARQL; module Algebra
22
29
  # @param [Enumerable<Array<RDF::Term>>] enum
23
30
  # enum of evaluated operand
24
31
  # @return [RDF::Literal::Integer] The number of non-error terms in the multiset
25
- def apply(enum)
32
+ def apply(enum, **options)
26
33
  RDF::Literal(enum.length)
27
34
  end
35
+
36
+ ##
37
+ #
38
+ # Returns a partial SPARQL grammar for this operator.
39
+ #
40
+ # @return [String]
41
+ def to_sparql(**options)
42
+ "COUNT(#{operands.to_sparql(**options)})"
43
+ end
28
44
  end # Count
29
45
  end # Operator
30
46
  end; end # SPARQL::Algebra
@@ -8,8 +8,13 @@ module SPARQL; module Algebra
8
8
  #
9
9
  # This is a no-op for RDF.rb implementations, unless the graph exists
10
10
  #
11
- # @example
12
- # (create silent <graph>)
11
+ # [34] Create ::= 'CREATE' 'SILENT'? GraphRef
12
+ #
13
+ # @example SPARQL Grammar
14
+ # CREATE SILENT GRAPH <http://example.org/g1>
15
+ #
16
+ # @example SSE
17
+ # (update (create silent <http://example.org/g1>))
13
18
  #
14
19
  # @see https://www.w3.org/TR/sparql11-update/#create
15
20
  class Create < Operator
@@ -43,6 +48,18 @@ module SPARQL; module Algebra
43
48
  end
44
49
  queryable
45
50
  end
51
+
52
+ ##
53
+ #
54
+ # Returns a partial SPARQL grammar for this operator.
55
+ #
56
+ # @return [String]
57
+ def to_sparql(**options)
58
+ *args, last = operands.dup
59
+ args += [:GRAPH, last]
60
+
61
+ "CREATE " + args.to_sparql(**options)
62
+ end
46
63
  end # Create
47
64
  end # Operator
48
65
  end; end # SPARQL::Algebra
@@ -158,6 +158,23 @@ module SPARQL; module Algebra
158
158
  aggregate.default(*default_datasets.select {|name| queryable.has_graph?(name)})
159
159
  aggregate.query(operands.last, depth: options[:depth].to_i + 1, **options, &base)
160
160
  end
161
+
162
+ ##
163
+ #
164
+ # Returns a partial SPARQL grammar for this operator.
165
+ #
166
+ # @return [String]
167
+ def to_sparql(**options)
168
+ operands[0].each_with_object('') do |graph, str|
169
+ str << if graph.is_a?(Array)
170
+ "FROM #{graph[0].upcase} #{graph[1].to_sparql(**options)}\n"
171
+ else
172
+ "FROM #{graph.to_sparql(**options)}\n"
173
+ end
174
+ end.tap do |str|
175
+ str << operands[1].to_sparql(**options)
176
+ end
177
+ end
161
178
  end # Dataset
162
179
  end # Operator
163
180
  end; end # SPARQL::Algebra
@@ -3,13 +3,23 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL `datatype` operator.
5
5
  #
6
- # @example
6
+ # [121] BuiltInCall ::= ... | 'DATATYPE' '(' Expression ')'
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
10
+ # PREFIX : <http://example.org/things#>
11
+ # SELECT ?x ?v
12
+ # WHERE
13
+ # { ?x :p ?v .
14
+ # FILTER ( datatype(?v) = xsd:double ) .
15
+ # }
16
+ #
17
+ # @example SSE
7
18
  # (prefix ((xsd: <http://www.w3.org/2001/XMLSchema#>)
8
- # (rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>)
9
- # (: <http://example.org/>))
10
- # (project (?s)
11
- # (filter (= (datatype (xsd:double ?v)) xsd:double)
12
- # (bgp (triple ?s :p ?v)))))
19
+ # (: <http://example.org/things#>))
20
+ # (project (?x ?v)
21
+ # (filter (= (datatype ?v) xsd:double)
22
+ # (bgp (triple ?x :p ?v)))))
13
23
  #
14
24
  # @see https://www.w3.org/TR/sparql11-query/#func-datatype
15
25
  class Datatype < Operator::Unary
@@ -27,12 +37,21 @@ module SPARQL; module Algebra
27
37
  # a typed or simple literal
28
38
  # @return [RDF::URI] the datatype IRI, or `xsd:string` for simple literals
29
39
  # @raise [TypeError] if the operand is not a typed or simple literal
30
- def apply(literal)
40
+ def apply(literal, **options)
31
41
  case literal
32
42
  when RDF::Literal then literal.datatype
33
43
  else raise TypeError, "expected an RDF::Literal, but got #{literal.inspect}"
34
44
  end
35
45
  end
46
+
47
+ ##
48
+ #
49
+ # Returns a partial SPARQL grammar for this operator.
50
+ #
51
+ # @return [String]
52
+ def to_sparql(**options)
53
+ "DATATYPE(#{operands.last.to_sparql(**options)})"
54
+ end
36
55
  end # Datatype
37
56
  end # Operator
38
57
  end; end # SPARQL::Algebra
@@ -3,11 +3,20 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL logical `day` operator.
5
5
  #
6
- # @example
7
- # (prefix ((: <http://example.org/>))
8
- # (project (?s ?x)
9
- # (extend ((?x (day ?date)))
10
- # (bgp (triple ?s :date ?date)))))
6
+ # [121] BuiltInCall ::= ... | 'DAY' '(' Expression ')'
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX : <http://example.org/>
10
+ # SELECT ?s (DAY(?date) AS ?x) WHERE {
11
+ # ?s :date ?date
12
+ # }
13
+ #
14
+ # @example SSE
15
+ # (prefix
16
+ # ((: <http://example.org/>))
17
+ # (project (?s ?x)
18
+ # (extend ((?x (day ?date)))
19
+ # (bgp (triple ?s :date ?date)))))
11
20
  #
12
21
  # @see https://www.w3.org/TR/sparql11-query/#func-day
13
22
  class Day < Operator::Unary
@@ -22,10 +31,19 @@ module SPARQL; module Algebra
22
31
  # the operand
23
32
  # @return [RDF::Literal]
24
33
  # @raise [TypeError] if the operand is not a simple literal
25
- def apply(operand)
34
+ def apply(operand, **options)
26
35
  raise TypeError, "expected an RDF::Literal::DateTime, but got #{operand.inspect}" unless operand.is_a?(RDF::Literal::DateTime)
27
36
  RDF::Literal(operand.object.day)
28
37
  end
38
+
39
+ ##
40
+ #
41
+ # Returns a partial SPARQL grammar for this operator.
42
+ #
43
+ # @return [String]
44
+ def to_sparql(**options)
45
+ "DAY(#{operands.last.to_sparql(**options)})"
46
+ end
29
47
  end # Day
30
48
  end # Operator
31
49
  end; end # SPARQL::Algebra
@@ -6,8 +6,24 @@ module SPARQL; module Algebra
6
6
  #
7
7
  # The DELETE operation is a form of the DELETE/INSERT operation having no INSERT section
8
8
  #
9
- # @example
10
- # (delete ((triple ?s ?p ?o))))
9
+ # [42] DeleteClause ::= 'DELETE' QuadPattern
10
+ #
11
+ # @example SPARQL Grammar
12
+ # PREFIX : <http://example.org/>
13
+ # PREFIX foaf: <http://xmlns.com/foaf/0.1/>
14
+ #
15
+ # DELETE { ?s ?p ?o }
16
+ # WHERE { :a foaf:knows ?s . ?s ?p ?o }
17
+ #
18
+ # @example SSE
19
+ # (prefix ((: <http://example.org/>)
20
+ # (foaf: <http://xmlns.com/foaf/0.1/>))
21
+ # (update
22
+ # (modify
23
+ # (bgp
24
+ # (triple :a foaf:knows ?s)
25
+ # (triple ?s ?p ?o))
26
+ # (delete ((triple ?s ?p ?o))))))
11
27
  #
12
28
  # @see https://www.w3.org/TR/sparql11-update/#delete
13
29
  class Delete < Operator::Unary
@@ -52,6 +68,15 @@ module SPARQL; module Algebra
52
68
  end
53
69
  queryable
54
70
  end
71
+
72
+ ##
73
+ #
74
+ # Returns a partial SPARQL grammar for this term.
75
+ #
76
+ # @return [String]
77
+ def to_sparql(**options)
78
+ "DELETE {\n" + operands.first.to_sparql(as_statement: true, **options) + "\n}"
79
+ end
55
80
  end # Delete
56
81
  end # Operator
57
82
  end; end # SPARQL::Algebra
@@ -6,8 +6,18 @@ module SPARQL; module Algebra
6
6
  #
7
7
  # The DELETE DATA operation removes some triples, given inline in the request, if the respective graphs in the Graph Store contain those
8
8
  #
9
- # @example
10
- # (deleteData ((triple :a foaf:knows :c)))
9
+ # [39] DeleteData ::= 'DELETE DATA' QuadData
10
+ #
11
+ # @example SPARQL Grammar
12
+ # PREFIX : <http://example.org/>
13
+ # PREFIX foaf: <http://xmlns.com/foaf/0.1/>
14
+ # DELETE DATA {
15
+ # :a foaf:knows :b .
16
+ # }
17
+ #
18
+ # @example SSE
19
+ # (prefix ((: <http://example.org/>) (foaf: <http://xmlns.com/foaf/0.1/>))
20
+ # (update (deleteData ((triple :a foaf:knows :b)))))
11
21
  #
12
22
  # @see https://www.w3.org/TR/sparql11-update/#deleteData
13
23
  class DeleteData < Operator::Unary
@@ -36,6 +46,17 @@ module SPARQL; module Algebra
36
46
  end
37
47
  queryable
38
48
  end
49
+
50
+ ##
51
+ #
52
+ # Returns a partial SPARQL grammar for this term.
53
+ #
54
+ # @return [String]
55
+ def to_sparql(**options)
56
+ "DELETE DATA {\n" +
57
+ operands.first.to_sparql(as_statement: true, top_level: false, delimiter: "\n", **options) +
58
+ "\n}"
59
+ end
39
60
  end # DeleteData
40
61
  end # Operator
41
62
  end; end # SPARQL::Algebra
@@ -6,8 +6,19 @@ module SPARQL; module Algebra
6
6
  #
7
7
  # The DELETE WHERE operation is a shortcut form for the DELETE/INSERT operation where bindings matched by the WHERE clause are used to define the triples in a graph that will be deleted.
8
8
  #
9
- # @example
10
- # (deleteWhere ((triple :a foaf:knows ?b))
9
+ # [40] DeleteWhere ::= 'DELETE WHERE' QuadPattern
10
+ #
11
+ # @example SPARQL Grammar
12
+ # PREFIX : <http://example.org/>
13
+ # PREFIX foaf: <http://xmlns.com/foaf/0.1/>
14
+ # DELETE WHERE { :a foaf:knows ?b }
15
+ #
16
+ # @example SSE
17
+ # (prefix
18
+ # ((: <http://example.org/>)
19
+ # (foaf: <http://xmlns.com/foaf/0.1/>))
20
+ # (update
21
+ # (deleteWhere ((triple :a foaf:knows ?b)))))
11
22
  #
12
23
  # @see https://www.w3.org/TR/sparql11-update/#deleteWhere
13
24
  class DeleteWhere < Operator::Unary
@@ -52,6 +63,17 @@ module SPARQL; module Algebra
52
63
  end
53
64
  queryable
54
65
  end
66
+
67
+ ##
68
+ #
69
+ # Returns a partial SPARQL grammar for this term.
70
+ #
71
+ # @return [String]
72
+ def to_sparql(**options)
73
+ "DELETE WHERE {\n" +
74
+ operands.first.to_sparql(as_statement: true, top_level: false, delimiter: "\n", **options) +
75
+ "\n}"
76
+ end
55
77
  end # DeleteWhere
56
78
  end # Operator
57
79
  end; end # SPARQL::Algebra
@@ -3,7 +3,15 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL descending sort operator.
5
5
  #
6
- # @example
6
+ # [24] OrderCondition ::= ( ( 'ASC' | 'DESC' ) BrackettedExpression ) | ( Constraint | Var )
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX foaf: <http://xmlns.com/foaf/0.1/>
10
+ # SELECT ?name
11
+ # WHERE { ?x foaf:name ?name }
12
+ # ORDER BY DESC(?name)
13
+ #
14
+ # @example SSE
7
15
  # (prefix ((foaf: <http://xmlns.com/foaf/0.1/>))
8
16
  # (project (?name)
9
17
  # (order ((desc ?name))
@@ -12,6 +20,17 @@ module SPARQL; module Algebra
12
20
  # @see https://www.w3.org/TR/sparql11-query/#modOrderBy
13
21
  class Desc < Operator::Asc
14
22
  NAME = :desc
23
+
24
+ ##
25
+ #
26
+ # Returns a partial SPARQL grammar for this operator.
27
+ #
28
+ # Provides order to descendant query.
29
+ #
30
+ # @return [String]
31
+ def to_sparql(**options)
32
+ "DESC(#{operands.last.to_sparql(**options)})"
33
+ end
15
34
  end # Desc
16
35
  end # Operator
17
36
  end; end # SPARQL::Algebra
@@ -5,10 +5,16 @@ module SPARQL; module Algebra
5
5
  #
6
6
  # Generages a graph across specified terms using {RDF::Queryable}`#concise_bounded_description`.
7
7
  #
8
- # @example
9
- # (prefix ((exOrg: <http://org.example.com/employees#>))
10
- # (describe (?x)
11
- # (bgp (triple ?x exOrg:employeeId "1234"))))
8
+ # [11] DescribeQuery ::= 'DESCRIBE' ( VarOrIri+ | '*' ) DatasetClause* WhereClause? SolutionModifier ValuesClause
9
+ #
10
+ # @example SPARQL Grammar
11
+ # BASE <http://example.org/>
12
+ # DESCRIBE <u> ?u WHERE { <x> <q> ?u . }
13
+ #
14
+ # @example SSE
15
+ # (base <http://example.org/>
16
+ # (describe (<u> ?u)
17
+ # (bgp (triple <x> <q> ?u))))
12
18
  #
13
19
  # @see https://www.w3.org/TR/sparql11-query/#describe
14
20
  class Describe < Operator::Binary
@@ -66,6 +72,23 @@ module SPARQL; module Algebra
66
72
  def query_yields_statements?
67
73
  true
68
74
  end
75
+
76
+ ##
77
+ #
78
+ # Returns a partial SPARQL grammar for this term.
79
+ #
80
+ # @return [String]
81
+ def to_sparql(**options)
82
+ str = "DESCRIBE "
83
+ str << if operands[0].empty?
84
+ "*"
85
+ else
86
+ operands[0].map { |e| e.to_sparql(**options) }.join(" ")
87
+ end
88
+
89
+ str << "\n"
90
+ str << operands[1].to_sparql(top_level: true, project: nil, **options)
91
+ end
69
92
  end # Construct
70
93
  end # Operator
71
94
  end; end # SPARQL::Algebra
@@ -3,7 +3,15 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL GraphPattern `distinct` operator.
5
5
  #
6
- # @example
6
+ # [9] SelectClause ::= 'SELECT' ( 'DISTINCT' | 'REDUCED' )? ( ( Var | ( '(' Expression 'AS' Var ')' ) )+ | '*' )
7
+ #
8
+ # @example SPARQL Grammar
9
+ # PREFIX : <http://example.org/>
10
+ # PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
11
+ # SELECT DISTINCT ?v
12
+ # WHERE { ?x ?p ?v }
13
+ #
14
+ # @example SSE
7
15
  # (prefix ((xsd: <http://www.w3.org/2001/XMLSchema#>)
8
16
  # (: <http://example/>))
9
17
  # (distinct
@@ -36,6 +44,15 @@ module SPARQL; module Algebra
36
44
  @solutions.each(&block) if block_given?
37
45
  @solutions
38
46
  end
47
+
48
+ ##
49
+ #
50
+ # Returns a partial SPARQL grammar for this operator.
51
+ #
52
+ # @return [String]
53
+ def to_sparql(**options)
54
+ operands.first.to_sparql(distinct: true, **options)
55
+ end
39
56
  end # Distinct
40
57
  end # Operator
41
58
  end; end # SPARQL::Algebra
@@ -3,8 +3,23 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL numeric `divide` operator.
5
5
  #
6
- # @example
7
- # (/ 4 2)
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)))))
8
23
  #
9
24
  # @see https://www.w3.org/TR/xpath-functions/#func-numeric-divide
10
25
  class Divide < Operator::Binary
@@ -21,7 +36,7 @@ module SPARQL; module Algebra
21
36
  # a numeric literal
22
37
  # @return [RDF::Literal::Numeric]
23
38
  # @raise [TypeError] if either operand is not a numeric literal
24
- def apply(left, right)
39
+ def apply(left, right, **options)
25
40
  case
26
41
  when left.is_a?(RDF::Literal::Numeric) && right.is_a?(RDF::Literal::Numeric)
27
42
  # For xsd:decimal and xsd:integer operands, if the divisor is
@@ -38,6 +53,15 @@ module SPARQL; module Algebra
38
53
  else raise TypeError, "expected two RDF::Literal::Numeric operands, but got #{left.inspect} and #{right.inspect}"
39
54
  end
40
55
  end
56
+
57
+ ##
58
+ #
59
+ # Returns a partial SPARQL grammar for this operator.
60
+ #
61
+ # @return [String]
62
+ def to_sparql(**options)
63
+ "#{operands.first.to_sparql(**options)} / #{operands.last.to_sparql(**options)}"
64
+ end
41
65
  end # Divide
42
66
  end # Operator
43
67
  end; end # SPARQL::Algebra
@@ -8,8 +8,14 @@ module SPARQL; module Algebra
8
8
  #
9
9
  # Equivalent to `clear` in this implementation
10
10
  #
11
- # @example
12
- # (drop default)
11
+ # [33] Drop ::= 'DROP' 'SILENT'? GraphRefAll
12
+ #
13
+ # @example SPARQL Grammar
14
+ # DROP DEFAULT
15
+ #
16
+ # @example SSE
17
+ # (update
18
+ # (drop default))
13
19
  #
14
20
  # @see https://www.w3.org/TR/sparql11-update/#drop
15
21
  class Drop < Operator
@@ -61,6 +67,15 @@ module SPARQL; module Algebra
61
67
 
62
68
  queryable
63
69
  end
70
+
71
+ ##
72
+ #
73
+ # Returns a partial SPARQL grammar for this operator.
74
+ #
75
+ # @return [String]
76
+ def to_sparql(**options)
77
+ "DROP " + operands.to_sparql(**options)
78
+ end
64
79
  end # Drop
65
80
  end # Operator
66
81
  end; end # SPARQL::Algebra
@@ -5,8 +5,21 @@ module SPARQL; module Algebra
5
5
  ##
6
6
  # The SPARQL logical `abs` operator.
7
7
  #
8
- # @example
9
- # (encode_for_uri ?x)
8
+ # [121] BuiltInCall ::= ... | 'ENCODE_FOR_URI' '(' Expression ')'
9
+ #
10
+ # @example SPARQL Grammar
11
+ # PREFIX : <http://example.org/>
12
+ # PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
13
+ # SELECT ?s ?str (ENCODE_FOR_URI(?str) AS ?encoded) WHERE {
14
+ # ?s :str ?str
15
+ # }
16
+ #
17
+ # @example SSE
18
+ # (prefix
19
+ # ((: <http://example.org/>))
20
+ # (project (?str ?encoded)
21
+ # (extend ((?encoded (encode_for_uri ?str)))
22
+ # (bgp (triple ?s :str ?str)))))
10
23
  #
11
24
  # @see https://www.w3.org/TR/sparql11-query/#func-encode
12
25
  # @see https://www.w3.org/TR/xpath-functions/#func-abs
@@ -27,12 +40,21 @@ module SPARQL; module Algebra
27
40
  # the operand
28
41
  # @return [RDF::Literal] literal of same type
29
42
  # @raise [TypeError] if the operand is not a literal value
30
- def apply(operand)
43
+ def apply(operand, **options)
31
44
  case operand
32
45
  when RDF::Literal then RDF::Literal(CGI.escape(operand.to_s))
33
46
  else raise TypeError, "expected an RDF::Literal, but got #{operand.inspect}"
34
47
  end
35
48
  end
49
+
50
+ ##
51
+ #
52
+ # Returns a partial SPARQL grammar for this operator.
53
+ #
54
+ # @return [String]
55
+ def to_sparql(**options)
56
+ "ENCODE_FOR_URI(#{operands.last.to_sparql(**options)})"
57
+ end
36
58
  end # EncodeForURI
37
59
  end # Operator
38
60
  end; end # SPARQL::Algebra
@@ -3,8 +3,18 @@ module SPARQL; module Algebra
3
3
  ##
4
4
  # The SPARQL relational `=` (equal) comparison operator.
5
5
  #
6
- # @example
7
- # (= ?x ?y)
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)))))
8
18
  #
9
19
  # @see https://www.w3.org/TR/sparql11-query/#OperatorMapping
10
20
  # @see https://www.w3.org/TR/sparql11-query/#func-RDFterm-equal
@@ -26,7 +36,7 @@ module SPARQL; module Algebra
26
36
  # @raise [TypeError] if either operand is not an RDF term or operands are not comperable
27
37
  #
28
38
  # @see RDF::Term#==
29
- def apply(term1, term2)
39
+ def apply(term1, term2, **options)
30
40
  term1 = term1.dup.extend(RDF::TypeCheck)
31
41
  term2 = term2.dup.extend(RDF::TypeCheck)
32
42
  RDF::Literal(term1 == term2)
@@ -5,10 +5,21 @@ 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 (bgp (triple ?s ?p ex:o)))
11
- # (bgp (triple ?s ?p ?o))))
8
+ # [125] ExistsFunc ::= 'EXISTS' GroupGraphPattern
9
+ #
10
+ # @example SPARQL Grammar
11
+ # PREFIX : <http://example/>
12
+ # SELECT *
13
+ # WHERE {
14
+ # ?set a :Set .
15
+ # FILTER EXISTS { ?set :member 9 }
16
+ # }
17
+ #
18
+ # @example SSE
19
+ # (prefix ((: <http://example/>))
20
+ # (filter
21
+ # (exists (bgp (triple ?set :member 9)))
22
+ # (bgp (triple ?set a :Set))))
12
23
  #
13
24
  # @see https://www.w3.org/TR/sparql11-query/#func-filter-exists
14
25
  class Exists < Operator::Unary
@@ -32,6 +43,19 @@ module SPARQL; module Algebra
32
43
  depth: options[:depth].to_i + 1,
33
44
  **options).empty?
34
45
  end
46
+
47
+ ##
48
+ #
49
+ # Returns a partial SPARQL grammar for this operator.
50
+ #
51
+ # @param [Boolean] top_level (true)
52
+ # Treat this as a top-level, generating SELECT ... WHERE {}
53
+ # @return [String]
54
+ def to_sparql(top_level: true, **options)
55
+ "EXISTS {\n" +
56
+ operands.last.to_sparql(top_level: false, **options) +
57
+ "\n}"
58
+ end
35
59
  end # Exists
36
60
  end # Operator
37
61
  end; end # SPARQL::Algebra
@@ -5,7 +5,18 @@ module SPARQL; module Algebra
5
5
  #
6
6
  # Used for filters with more than one expression.
7
7
  #
8
- # @example
8
+ # [72] ExpressionList ::= NIL | '(' Expression ( ',' Expression )* ')'
9
+ #
10
+ # @example SPARQL Grammar
11
+ # SELECT ?v ?w
12
+ # {
13
+ # FILTER (?v = 2)
14
+ # FILTER (?w = 3)
15
+ # ?s :p ?v .
16
+ # ?s :q ?w .
17
+ # }
18
+ #
19
+ # @example SSE
9
20
  # (prefix ((: <http://example/>))
10
21
  # (project (?v ?w)
11
22
  # (filter (exprlist (= ?v 2) (= ?w 3))