sparql-client 3.2.1 → 3.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cfca146902f11c4799f6b955e97deecf31873afc3c05309234cab948f34afd0c
4
- data.tar.gz: 63cbaafab09deeddf3cbbcb23fe013c27ff82b759fa681a32219eebf24a771ba
3
+ metadata.gz: 5eae29702f85f3af2fc135180b3ba19caef6bdec55f07db1cdac357acfead4c7
4
+ data.tar.gz: a55b668567124d55b09d352796559f0c32a05c4b9b88024438c77fccb95d661a
5
5
  SHA512:
6
- metadata.gz: 3aa86e2182d70ab4ca0472c2ae4f5a6c645a95a848dbb6f74f38c4406c298e15a8e704d321d42b3d5a8186f607dcf5ad1304755a575e75e295ce81fa26eecdd8
7
- data.tar.gz: 495bd5bcfed2a73e47c0a890ccce100551befd249216328209f0bf20a920a6d8db1efb6e4691172adbae7aeff58496bf5434f875987f61f7d2c0068116b762b5
6
+ metadata.gz: 3629fa3c547b92359564d9b2e09c26df0f2f56a3bd8f352b4cfc307ebf145dd52a3cc1c2864f2bbf047b9a40a9a1958785f2a4cf1abca2d578a4ba6a19a0de80
7
+ data.tar.gz: f58f8a5668a5f088604d497a254b31130740624a05ccee8254f0e466cd852edaac4185c00c4dac4fdfdfd2509e678e5d7e887538e62e4d7a8099e491c8be5935
data/README.md CHANGED
@@ -4,7 +4,7 @@ This is a [Ruby][] implementation of a [SPARQL][] client for [RDF.rb][].
4
4
 
5
5
  * <https://ruby-rdf.github.io/sparql-client/>
6
6
 
7
- [![Gem Version](https://badge.fury.io/rb/sparql-client.png)](https://badge.fury.io/rb/sparql-client)
7
+ [![Gem Version](https://badge.fury.io/rb/sparql-client.svg)](https://badge.fury.io/rb/sparql-client)
8
8
  [![Build Status](https://github.com/ruby-rdf/sparql-client/workflows/CI/badge.svg?branch=develop)](https://github.com/ruby-rdf/sparql-client/actions?query=workflow%3ACI)
9
9
  [![Coverage Status](https://coveralls.io/repos/ruby-rdf/sparql-client/badge.svg?branch=master&service=github)](https://coveralls.io/github/ruby-rdf/sparql-client?branch=master)
10
10
  [![Gitter chat](https://badges.gitter.im/ruby-rdf/rdf.png)](https://gitter.im/ruby-rdf/rdf)
@@ -124,11 +124,11 @@ sparql.delete_data(data)
124
124
 
125
125
  ## Dependencies
126
126
 
127
- * [Ruby](https://ruby-lang.org/) (>= 2.6)
128
- * [RDF.rb](https://rubygems.org/gems/rdf) (~> 3.2)
127
+ * [Ruby](https://ruby-lang.org/) (>= 3.0)
128
+ * [RDF.rb](https://rubygems.org/gems/rdf) (~> 3.3)
129
129
  * [Net::HTTP::Persistent](https://rubygems.org/gems/net-http-persistent) (~> 4.0, >= 4.0.1)
130
- * Soft dependency on [SPARQL](https://rubygems.org/gems/sparql) (~> 3.2)
131
- * Soft dependency on [Nokogiri](https://rubygems.org/gems/nokogiri) (>= 1.12)
130
+ * Soft dependency on [SPARQL](https://rubygems.org/gems/sparql) (~> 3.3)
131
+ * Soft dependency on [Nokogiri](https://rubygems.org/gems/nokogiri) (>= 1.15)
132
132
 
133
133
  ## Installation
134
134
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 3.2.1
1
+ 3.3.0
@@ -111,7 +111,7 @@ class SPARQL::Client
111
111
 
112
112
  ##
113
113
  # @example ASK WHERE { ?s ?p ?o . }
114
- # query.ask.where([:s, :p, :o])
114
+ # Query.ask.where([:s, :p, :o])
115
115
  #
116
116
  # @return [Query]
117
117
  # @see https://www.w3.org/TR/sparql11-query/#ask
@@ -122,13 +122,13 @@ class SPARQL::Client
122
122
 
123
123
  ##
124
124
  # @example `SELECT * WHERE { ?s ?p ?o . }`
125
- # query.select.where([:s, :p, :o])
125
+ # Query.select.where([:s, :p, :o])
126
126
  #
127
127
  # @example `SELECT ?s WHERE {?s ?p ?o .}`
128
- # query.select(:s).where([:s, :p, :o])
128
+ # Query.select(:s).where([:s, :p, :o])
129
129
  #
130
130
  # @example `SELECT COUNT(?uri as ?c) WHERE {?uri a owl:Class}`
131
- # query.select(count: {uri: :c}).where([:uri, RDF.type, RDF::OWL.Class])
131
+ # Query.select(count: {uri: :c}).where([:uri, RDF.type, RDF::OWL.Class])
132
132
  #
133
133
  # @param [Array<Symbol>, Hash{Symbol => RDF::Query::Variable}] variables
134
134
  # @return [Query]
@@ -144,7 +144,7 @@ class SPARQL::Client
144
144
 
145
145
  ##
146
146
  # @example DESCRIBE * WHERE { ?s ?p ?o . }
147
- # query.describe.where([:s, :p, :o])
147
+ # Query.describe.where([:s, :p, :o])
148
148
  #
149
149
  # @param [Array<Symbol>] variables
150
150
  # @return [Query]
@@ -158,7 +158,7 @@ class SPARQL::Client
158
158
 
159
159
  ##
160
160
  # @example CONSTRUCT { ?s ?p ?o . } WHERE { ?s ?p ?o . }
161
- # query.construct([:s, :p, :o]).where([:s, :p, :o])
161
+ # Query.construct([:s, :p, :o]).where([:s, :p, :o])
162
162
  #
163
163
  # @param [Array<RDF::Query::Pattern, Array>] patterns
164
164
  # @return [Query]
@@ -170,7 +170,7 @@ class SPARQL::Client
170
170
 
171
171
  ##
172
172
  # @example SELECT * FROM <a> WHERE \{ ?s ?p ?o . \}
173
- # query.select.from(RDF::URI.new(a)).where([:s, :p, :o])
173
+ # Query.select.from(RDF::URI.new(a)).where([:s, :p, :o])
174
174
  #
175
175
  # @param [RDF::URI] uri
176
176
  # @return [Query]
@@ -182,22 +182,22 @@ class SPARQL::Client
182
182
 
183
183
  ##
184
184
  # @example SELECT * WHERE { ?s ?p ?o . }
185
- # query.select.where([:s, :p, :o])
186
- # query.select.whether([:s, :p, :o])
185
+ # Query.select.where([:s, :p, :o])
186
+ # Query.select.whether([:s, :p, :o])
187
187
  #
188
188
  # @example SELECT * WHERE { { SELECT * WHERE { ?s ?p ?o . } } . ?s ?p ?o . }
189
- # subquery = query.select.where([:s, :p, :o])
190
- # query.select.where([:s, :p, :o], subquery)
189
+ # subquery = Query.select.where([:s, :p, :o])
190
+ # Query.select.where([:s, :p, :o], subquery)
191
191
  #
192
192
  # @example SELECT * WHERE { { SELECT * WHERE { ?s ?p ?o . } } . ?s ?p ?o . }
193
- # query.select.where([:s, :p, :o]) do |q|
193
+ # Query.select.where([:s, :p, :o]) do |q|
194
194
  # q.select.where([:s, :p, :o])
195
195
  # end
196
196
  #
197
197
  # Block form can be used for chaining calls in addition to creating sub-select queries.
198
198
  #
199
199
  # @example SELECT * WHERE { ?s ?p ?o . } ORDER BY ?o
200
- # query.select.where([:s, :p, :o]) do
200
+ # Query.select.where([:s, :p, :o]) do
201
201
  # order(:o)
202
202
  # end
203
203
  #
@@ -236,14 +236,14 @@ class SPARQL::Client
236
236
 
237
237
  ##
238
238
  # @example SELECT * WHERE { ?s ?p ?o . } ORDER BY ?o
239
- # query.select.where([:s, :p, :o]).order(:o)
240
- # query.select.where([:s, :p, :o]).order_by(:o)
239
+ # Query.select.where([:s, :p, :o]).order(:o)
240
+ # Query.select.where([:s, :p, :o]).order_by(:o)
241
241
  #
242
242
  # @example SELECT * WHERE { ?s ?p ?o . } ORDER BY ?o ?p
243
- # query.select.where([:s, :p, :o]).order_by(:o, :p)
243
+ # Query.select.where([:s, :p, :o]).order_by(:o, :p)
244
244
  #
245
245
  # @example SELECT * WHERE { ?s ?p ?o . } ORDER BY ASC(?o) DESC(?p)
246
- # query.select.where([:s, :p, :o]).order_by(o: :asc, p: :desc)
246
+ # Query.select.where([:s, :p, :o]).order_by(o: :asc, p: :desc)
247
247
  #
248
248
  # @param [Array<Symbol, String>] variables
249
249
  # @return [Query]
@@ -257,8 +257,8 @@ class SPARQL::Client
257
257
 
258
258
  ##
259
259
  # @example SELECT * WHERE { ?s ?p ?o . } ORDER BY ASC(?o)
260
- # query.select.where([:s, :p, :o]).order.asc(:o)
261
- # query.select.where([:s, :p, :o]).asc(:o)
260
+ # Query.select.where([:s, :p, :o]).order.asc(:o)
261
+ # Query.select.where([:s, :p, :o]).asc(:o)
262
262
  #
263
263
  # @param [Array<Symbol, String>] var
264
264
  # @return [Query]
@@ -270,8 +270,8 @@ class SPARQL::Client
270
270
 
271
271
  ##
272
272
  # @example SELECT * WHERE { ?s ?p ?o . } ORDER BY DESC(?o)
273
- # query.select.where([:s, :p, :o]).order.desc(:o)
274
- # query.select.where([:s, :p, :o]).desc(:o)
273
+ # Query.select.where([:s, :p, :o]).order.desc(:o)
274
+ # Query.select.where([:s, :p, :o]).desc(:o)
275
275
  #
276
276
  # @param [Array<Symbol, String>] var
277
277
  # @return [Query]
@@ -283,7 +283,7 @@ class SPARQL::Client
283
283
 
284
284
  ##
285
285
  # @example SELECT ?s WHERE { ?s ?p ?o . } GROUP BY ?s
286
- # query.select(:s).where([:s, :p, :o]).group_by(:s)
286
+ # Query.select(:s).where([:s, :p, :o]).group_by(:s)
287
287
  #
288
288
  # @param [Array<Symbol, String>] variables
289
289
  # @return [Query]
@@ -297,7 +297,7 @@ class SPARQL::Client
297
297
 
298
298
  ##
299
299
  # @example SELECT DISTINCT ?s WHERE { ?s ?p ?o . }
300
- # query.select(:s).distinct.where([:s, :p, :o])
300
+ # Query.select(:s).distinct.where([:s, :p, :o])
301
301
  #
302
302
  # @return [Query]
303
303
  # @see https://www.w3.org/TR/sparql11-query/#modDuplicates
@@ -308,7 +308,7 @@ class SPARQL::Client
308
308
 
309
309
  ##
310
310
  # @example SELECT REDUCED ?s WHERE { ?s ?p ?o . }
311
- # query.select(:s).reduced.where([:s, :p, :o])
311
+ # Query.select(:s).reduced.where([:s, :p, :o])
312
312
  #
313
313
  # @return [Query]
314
314
  # @see https://www.w3.org/TR/sparql11-query/#modDuplicates
@@ -319,7 +319,8 @@ class SPARQL::Client
319
319
 
320
320
  ##
321
321
  # @example SELECT * WHERE { GRAPH ?g { ?s ?p ?o . } }
322
- # query.select.graph(:g).where([:s, :p, :o])
322
+ # Query.select.graph(:g).where([:s, :p, :o])
323
+ #
323
324
  # @param [RDF::Value] graph_uri_or_var
324
325
  # @return [Query]
325
326
  # @see https://www.w3.org/TR/sparql11-query/#queryDataset
@@ -335,7 +336,7 @@ class SPARQL::Client
335
336
 
336
337
  ##
337
338
  # @example SELECT * WHERE { ?s ?p ?o . } OFFSET 100
338
- # query.select.where([:s, :p, :o]).offset(100)
339
+ # Query.select.where([:s, :p, :o]).offset(100)
339
340
  #
340
341
  # @param [Integer, #to_i] start
341
342
  # @return [Query]
@@ -346,7 +347,7 @@ class SPARQL::Client
346
347
 
347
348
  ##
348
349
  # @example SELECT * WHERE { ?s ?p ?o . } LIMIT 10
349
- # query.select.where([:s, :p, :o]).limit(10)
350
+ # Query.select.where([:s, :p, :o]).limit(10)
350
351
  #
351
352
  # @param [Integer, #to_i] length
352
353
  # @return [Query]
@@ -357,7 +358,7 @@ class SPARQL::Client
357
358
 
358
359
  ##
359
360
  # @example SELECT * WHERE { ?s ?p ?o . } OFFSET 100 LIMIT 10
360
- # query.select.where([:s, :p, :o]).slice(100, 10)
361
+ # Query.select.where([:s, :p, :o]).slice(100, 10)
361
362
  #
362
363
  # @param [Integer, #to_i] start
363
364
  # @param [Integer, #to_i] length
@@ -371,7 +372,7 @@ class SPARQL::Client
371
372
  ##
372
373
  # @overload prefix(prefix: uri)
373
374
  # @example PREFIX dc: <http://purl.org/dc/elements/1.1/> PREFIX foaf: <http://xmlns.com/foaf/0.1/> SELECT * WHERE \{ ?s ?p ?o . \}
374
- # query.select.
375
+ # Query.select.
375
376
  # prefix(dc: RDF::URI("http://purl.org/dc/elements/1.1/")).
376
377
  # prefix(foaf: RDF::URI("http://xmlns.com/foaf/0.1/")).
377
378
  # where([:s, :p, :o])
@@ -382,7 +383,7 @@ class SPARQL::Client
382
383
  #
383
384
  # @overload prefix(string)
384
385
  # @example PREFIX dc: <http://purl.org/dc/elements/1.1/> PREFIX foaf: <http://xmlns.com/foaf/0.1/> SELECT * WHERE \{ ?s ?p ?o . \}
385
- # query.select.
386
+ # Query.select.
386
387
  # prefix("dc: <http://purl.org/dc/elements/1.1/>").
387
388
  # prefix("foaf: <http://xmlns.com/foaf/0.1/>").
388
389
  # where([:s, :p, :o])
@@ -406,13 +407,13 @@ class SPARQL::Client
406
407
 
407
408
  ##
408
409
  # @example SELECT * WHERE \{ ?s ?p ?o . OPTIONAL \{ ?s a ?o . ?s \<http://purl.org/dc/terms/abstract\> ?o . \} \}
409
- # query.select.where([:s, :p, :o]).
410
+ # Query.select.where([:s, :p, :o]).
410
411
  # optional([:s, RDF.type, :o], [:s, RDF::Vocab::DC.abstract, :o])
411
412
  #
412
413
  # The block form can be used for adding filters:
413
414
  #
414
415
  # @example ASK WHERE { ?s ?p ?o . OPTIONAL { ?s ?p ?o . FILTER(regex(?s, 'Abiline, Texas'))} }
415
- # query.ask.where([:s, :p, :o]).optional([:s, :p, :o]) do
416
+ # Query.ask.where([:s, :p, :o]).optional([:s, :p, :o]) do
416
417
  # filter("regex(?s, 'Abiline, Texas')")
417
418
  # end
418
419
  #
@@ -441,22 +442,89 @@ class SPARQL::Client
441
442
  self
442
443
  end
443
444
 
445
+ ##
446
+ # Federated Queries via the SERVICE keyword.
447
+ #
448
+ # Supports limited use of the SERVICE keyword with an endpoint term, a sequence of patterns, a query, or a block.
449
+ #
450
+ # @example SELECT * WHERE \{ ?s ?p1 ?o1 . SERVICE ?l \{ ?s ?p2 ?o2 \} \}
451
+ # Query.select.where([:s, :p1, :o1]).
452
+ # service(:l, [:s, :p2, :o2])
453
+ #
454
+ # @example SELECT * WHERE \{ ?book <http://purl.org/dc/terms/title> ?title . SERVICE ?l \{ ?book <http://purl.org/dc/elements/1.1/title> ?title . FILTER(langmatches(?title, 'en')) \} \}
455
+ # query1 = SPARQL::Client::Query.select.
456
+ # where([:book, RDF::Vocab::DC11.title, :title]).
457
+ # filter("langmatches(?title, 'en')")
458
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).service(?l, query1)
459
+ #
460
+ # The block form can be used for more complicated queries, using the `select` form (note, use either block or argument forms, not both):
461
+ #
462
+ # @example SELECT * WHERE \{ ?book dc:title ?title \} SERVICE ?l \{ ?book dc11:title ?title \}
463
+ # query1 = SPARQL::Client::Query.select.where([:book, RDF::Vocab::DC11.title, :title])
464
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).service :l do |q|
465
+ # q.select.
466
+ # where([:book, RDF::Vocab::DC11.title, :title])
467
+ # end
468
+ #
469
+ # @example SELECT * WHERE \{ ?s ?p1 ?o1 . SERVICE SILENT ?l \{ ?s ?p2 ?o2 \} \}
470
+ # Query.select.where([:s, :p1, :o1]).
471
+ # service(:l, [:s, :p2, :o2], silent: true)
472
+ #
473
+ # @param [Array<RDF::Query::Pattern, Array>] patterns
474
+ # splat of zero or more patterns followed by zero or more queries.
475
+ # @param [Boolean] silent
476
+ # @yield [query]
477
+ # Yield form with or without argument; without an argument, evaluates within the query.
478
+ # @yieldparam [SPARQL::Client::Query] query used for adding select clauses.
479
+ # @return [Query]
480
+ # @see https://www.w3.org/TR/sparql11-federated-query/
481
+ def service(endpoint, *patterns, silent: false, &block)
482
+ service = {
483
+ endpoint: (endpoint.is_a?(Symbol) ? RDF::Query::Variable.new(endpoint) : endpoint),
484
+ silent: silent,
485
+ query: nil
486
+ }
487
+ (options[:services] ||= []) << service
488
+
489
+ if block_given?
490
+ raise ArgumentError, "#service requires either arguments or a block, not both." unless patterns.empty?
491
+ # Evaluate calls in a new query instance
492
+ query = self.class.select.where
493
+ case block.arity
494
+ when 1 then block.call(query)
495
+ else query.instance_eval(&block)
496
+ end
497
+ service[:query] = query
498
+ elsif patterns.all? {|p| p.is_a?(SPARQL::Client::Query)}
499
+ # With argument form, all must be patterns or queries
500
+ raise ArgumentError, "#service arguments are triple patterns or a query, not both." if patterns.length != 1
501
+ service[:query] = patterns.first
502
+ elsif patterns.all? {|p| p.is_a?(Array)}
503
+ # With argument form, all must be patterns, or queries
504
+ service[:query] = self.class.select.where(*patterns)
505
+ else
506
+ raise ArgumentError, "#service arguments are triple patterns a query, not both."
507
+ end
508
+
509
+ self
510
+ end
511
+
444
512
  ##
445
513
  # @example SELECT * WHERE \{ ?book dc:title ?title \} UNION \{ ?book dc11:title ?title \}
446
- # query.select.where([:book, RDF::Vocab::DC.title, :title]).
514
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).
447
515
  # union([:book, RDF::Vocab::DC11.title, :title])
448
516
  #
449
517
  # @example SELECT * WHERE \{ ?book dc:title ?title \} UNION \{ ?book dc11:title ?title . FILTER(langmatches(lang(?title), 'EN'))\}
450
518
  # query1 = SPARQL::Client::Query.select.
451
519
  # where([:book, RDF::Vocab::DC11.title, :title]).
452
520
  # filter("langmatches(?title, 'en')")
453
- # query.select.where([:book, RDF::Vocab::DC.title, :title]).union(query1)
521
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).union(query1)
454
522
  #
455
523
  # The block form can be used for more complicated queries, using the `select` form (note, use either block or argument forms, not both):
456
524
  #
457
525
  # @example SELECT * WHERE \{ ?book dc:title ?title \} UNION \{ ?book dc11:title ?title . FILTER(langmatches(lang(?title), 'EN'))\}
458
526
  # query1 = SPARQL::Client::Query.select.where([:book, RDF::Vocab::DC11.title, :title]).filter("langmatches(?title, 'en')")
459
- # query.select.where([:book, RDF::Vocab::DC.title, :title]).union do |q|
527
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).union do |q|
460
528
  # q.select.
461
529
  # where([:book, RDF::Vocab::DC11.title, :title]).
462
530
  # filter("langmatches(?title, 'en')")
@@ -468,7 +536,7 @@ class SPARQL::Client
468
536
  # Yield form with or without argument; without an argument, evaluates within the query.
469
537
  # @yieldparam [SPARQL::Client::Query] query used for adding select clauses.
470
538
  # @return [Query]
471
- # @see https://www.w3.org/TR/sparql11-query/#optionals
539
+ # @see https://www.w3.org/TR/sparql11-query/#alternatives
472
540
  def union(*patterns, &block)
473
541
  options[:unions] ||= []
474
542
 
@@ -488,7 +556,7 @@ class SPARQL::Client
488
556
  # With argument form, all must be patterns, or queries
489
557
  options[:unions] << self.class.select.where(*patterns)
490
558
  else
491
- raise ArgumentError, "#union arguments are triple patters or queries, not both."
559
+ raise ArgumentError, "#union arguments are triple patterns or queries, not both."
492
560
  end
493
561
 
494
562
  self
@@ -496,20 +564,20 @@ class SPARQL::Client
496
564
 
497
565
  ##
498
566
  # @example SELECT * WHERE \{ ?book dc:title ?title . MINUS \{ ?book dc11:title ?title \} \}
499
- # query.select.where([:book, RDF::Vocab::DC.title, :title]).
567
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).
500
568
  # minus([:book, RDF::Vocab::DC11.title, :title])
501
569
  #
502
570
  # @example SELECT * WHERE \{ ?book dc:title ?title MINUS \{ ?book dc11:title ?title . FILTER(langmatches(lang(?title), 'EN')) \} \}
503
571
  # query1 = SPARQL::Client::Query.select.
504
572
  # where([:book, RDF::Vocab::DC11.title, :title]).
505
573
  # filter("langmatches(?title, 'en')")
506
- # query.select.where([:book, RDF::Vocab::DC.title, :title]).minus(query1)
574
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).minus(query1)
507
575
  #
508
576
  # The block form can be used for more complicated queries, using the `select` form (note, use either block or argument forms, not both):
509
577
  #
510
578
  # @example SELECT * WHERE \{ ?book dc:title ?title MINUS \{ ?book dc11:title ?title . FILTER(langmatches(lang(?title), 'EN'))\} \}
511
579
  # query1 = SPARQL::Client::Query.select.where([:book, RDF::Vocab::DC11.title, :title]).filter("langmatches(?title, 'en')")
512
- # query.select.where([:book, RDF::Vocab::DC.title, :title]).minus do |q|
580
+ # Query.select.where([:book, RDF::Vocab::DC.title, :title]).minus do |q|
513
581
  # q.select.
514
582
  # where([:book, RDF::Vocab::DC11.title, :title]).
515
583
  # filter("langmatches(?title, 'en')")
@@ -521,7 +589,7 @@ class SPARQL::Client
521
589
  # Yield form with or without argument; without an argument, evaluates within the query.
522
590
  # @yieldparam [SPARQL::Client::Query] query used for adding select clauses.
523
591
  # @return [Query]
524
- # @see https://www.w3.org/TR/sparql11-query/#optionals
592
+ # @see https://www.w3.org/TR/sparql11-query/#negation
525
593
  def minus(*patterns, &block)
526
594
  options[:minuses] ||= []
527
595
 
@@ -541,7 +609,7 @@ class SPARQL::Client
541
609
  # With argument form, all must be patterns, or queries
542
610
  options[:minuses] << self.class.select.where(*patterns)
543
611
  else
544
- raise ArgumentError, "#minus arguments are triple patters or queries, not both."
612
+ raise ArgumentError, "#minus arguments are triple patterns or queries, not both."
545
613
  end
546
614
 
547
615
  self
@@ -557,12 +625,12 @@ class SPARQL::Client
557
625
  #
558
626
  # @overload values(vars, *data)
559
627
  # @example single variable with multiple values
560
- # query.select
628
+ # Query.select
561
629
  # .where([:s, RDF::URI('http://purl.org/dc/terms/title'), :title])
562
630
  # .values(:title, "This title", "Another title")
563
631
  #
564
632
  # @example multiple variables with multiple values
565
- # query.select
633
+ # Query.select
566
634
  # .where([:s, RDF::URI('http://purl.org/dc/terms/title'), :title],
567
635
  # [:s, RDF.type, :type])
568
636
  # .values([:type, :title],
@@ -570,7 +638,7 @@ class SPARQL::Client
570
638
  # [RDF::URI('http://pcdm.org/models#Collection', 'Another title'])
571
639
  #
572
640
  # @example multiple variables with UNDEF
573
- # query.select
641
+ # Query.select
574
642
  # .where([:s, RDF::URI('http://purl.org/dc/terms/title'), :title],
575
643
  # [:s, RDF.type, :type])
576
644
  # .values([:type, :title],
@@ -626,7 +694,7 @@ class SPARQL::Client
626
694
 
627
695
  ##
628
696
  # @example ASK WHERE { ?s ?p ?o . FILTER(regex(?s, 'Abiline, Texas')) }
629
- # query.ask.where([:s, :p, :o]).filter("regex(?s, 'Abiline, Texas')")
697
+ # Query.ask.where([:s, :p, :o]).filter("regex(?s, 'Abiline, Texas')")
630
698
  # @return [Query]
631
699
  def filter(string)
632
700
  ((options[:filters] ||= []) << Filter.new(string)) if string and not string.empty?
@@ -796,6 +864,16 @@ class SPARQL::Client
796
864
  if options[:filters]
797
865
  buffer += options[:filters].map(&:to_s)
798
866
  end
867
+
868
+ if options[:services]
869
+ options[:services].each do |service|
870
+ buffer << 'SERVICE'
871
+ buffer << 'SILENT' if service[:silent]
872
+ buffer << SPARQL::Client.serialize_value(service[:endpoint])
873
+ buffer << service[:query].to_s_ggp
874
+ end
875
+ end
876
+
799
877
  if options[:values]
800
878
  vars = options[:values].first.map {|var| SPARQL::Client.serialize_value(var)}
801
879
  buffer << "VALUES (#{vars.join(' ')}) {"
data/lib/sparql/client.rb CHANGED
@@ -540,7 +540,7 @@ module SPARQL
540
540
  result.elements.each do |binding|
541
541
  name = binding.attr('name').to_sym
542
542
  value = binding.elements.first
543
- row[name] = parse_xml_value(value, nodes)
543
+ row[name] = parse_xml_value(value, nodes) if value
544
544
  end
545
545
  RDF::Query::Solution.new(row)
546
546
  end
@@ -563,7 +563,7 @@ module SPARQL
563
563
  result.elements.each do |binding|
564
564
  name = binding.attributes['name'].to_sym
565
565
  value = binding.select { |node| node.kind_of?(::REXML::Element) }.first
566
- row[name] = parse_xml_value(value, nodes)
566
+ row[name] = parse_xml_value(value, nodes) if value
567
567
  end
568
568
  RDF::Query::Solution.new(row)
569
569
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sparql-client
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.2.1
4
+ version: 3.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Arto Bendiken
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2022-03-16 00:00:00.000000000 Z
13
+ date: 2023-08-26 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rdf
@@ -18,20 +18,14 @@ dependencies:
18
18
  requirements:
19
19
  - - "~>"
20
20
  - !ruby/object:Gem::Version
21
- version: '3.2'
22
- - - ">="
23
- - !ruby/object:Gem::Version
24
- version: 3.2.6
21
+ version: '3.3'
25
22
  type: :runtime
26
23
  prerelease: false
27
24
  version_requirements: !ruby/object:Gem::Requirement
28
25
  requirements:
29
26
  - - "~>"
30
27
  - !ruby/object:Gem::Version
31
- version: '3.2'
32
- - - ">="
33
- - !ruby/object:Gem::Version
34
- version: 3.2.6
28
+ version: '3.3'
35
29
  - !ruby/object:Gem::Dependency
36
30
  name: net-http-persistent
37
31
  requirement: !ruby/object:Gem::Requirement
@@ -41,7 +35,7 @@ dependencies:
41
35
  version: '4.0'
42
36
  - - ">="
43
37
  - !ruby/object:Gem::Version
44
- version: 4.0.1
38
+ version: 4.0.2
45
39
  type: :runtime
46
40
  prerelease: false
47
41
  version_requirements: !ruby/object:Gem::Requirement
@@ -51,49 +45,49 @@ dependencies:
51
45
  version: '4.0'
52
46
  - - ">="
53
47
  - !ruby/object:Gem::Version
54
- version: 4.0.1
48
+ version: 4.0.2
55
49
  - !ruby/object:Gem::Dependency
56
50
  name: rdf-spec
57
51
  requirement: !ruby/object:Gem::Requirement
58
52
  requirements:
59
53
  - - "~>"
60
54
  - !ruby/object:Gem::Version
61
- version: '3.2'
55
+ version: '3.3'
62
56
  type: :development
63
57
  prerelease: false
64
58
  version_requirements: !ruby/object:Gem::Requirement
65
59
  requirements:
66
60
  - - "~>"
67
61
  - !ruby/object:Gem::Version
68
- version: '3.2'
62
+ version: '3.3'
69
63
  - !ruby/object:Gem::Dependency
70
64
  name: sparql
71
65
  requirement: !ruby/object:Gem::Requirement
72
66
  requirements:
73
67
  - - "~>"
74
68
  - !ruby/object:Gem::Version
75
- version: '3.2'
69
+ version: '3.3'
76
70
  type: :development
77
71
  prerelease: false
78
72
  version_requirements: !ruby/object:Gem::Requirement
79
73
  requirements:
80
74
  - - "~>"
81
75
  - !ruby/object:Gem::Version
82
- version: '3.2'
76
+ version: '3.3'
83
77
  - !ruby/object:Gem::Dependency
84
78
  name: rspec
85
79
  requirement: !ruby/object:Gem::Requirement
86
80
  requirements:
87
81
  - - "~>"
88
82
  - !ruby/object:Gem::Version
89
- version: '3.10'
83
+ version: '3.12'
90
84
  type: :development
91
85
  prerelease: false
92
86
  version_requirements: !ruby/object:Gem::Requirement
93
87
  requirements:
94
88
  - - "~>"
95
89
  - !ruby/object:Gem::Version
96
- version: '3.10'
90
+ version: '3.12'
97
91
  - !ruby/object:Gem::Dependency
98
92
  name: rspec-its
99
93
  requirement: !ruby/object:Gem::Requirement
@@ -114,14 +108,14 @@ dependencies:
114
108
  requirements:
115
109
  - - "~>"
116
110
  - !ruby/object:Gem::Version
117
- version: '3.14'
111
+ version: '3.19'
118
112
  type: :development
119
113
  prerelease: false
120
114
  version_requirements: !ruby/object:Gem::Requirement
121
115
  requirements:
122
116
  - - "~>"
123
117
  - !ruby/object:Gem::Version
124
- version: '3.14'
118
+ version: '3.19'
125
119
  - !ruby/object:Gem::Dependency
126
120
  name: yard
127
121
  requirement: !ruby/object:Gem::Requirement
@@ -173,14 +167,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
173
167
  requirements:
174
168
  - - ">="
175
169
  - !ruby/object:Gem::Version
176
- version: '2.6'
170
+ version: '3.0'
177
171
  required_rubygems_version: !ruby/object:Gem::Requirement
178
172
  requirements:
179
173
  - - ">="
180
174
  - !ruby/object:Gem::Version
181
175
  version: '0'
182
176
  requirements: []
183
- rubygems_version: 3.3.3
177
+ rubygems_version: 3.2.33
184
178
  signing_key:
185
179
  specification_version: 4
186
180
  summary: SPARQL client for RDF.rb.