rdf 1.0.3 → 1.0.4
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.
- checksums.yaml +15 -0
- data/README +18 -0
- data/VERSION +1 -1
- data/lib/rdf/format.rb +34 -8
- data/lib/rdf/mixin/enumerable.rb +20 -3
- data/lib/rdf/mixin/mutable.rb +17 -3
- data/lib/rdf/mixin/queryable.rb +6 -2
- data/lib/rdf/model/graph.rb +45 -16
- data/lib/rdf/model/literal.rb +11 -0
- data/lib/rdf/model/node.rb +8 -0
- data/lib/rdf/model/statement.rb +4 -19
- data/lib/rdf/model/term.rb +29 -5
- data/lib/rdf/model/uri.rb +43 -39
- data/lib/rdf/model/value.rb +39 -13
- data/lib/rdf/nquads.rb +5 -1
- data/lib/rdf/ntriples/reader.rb +110 -19
- data/lib/rdf/ntriples/writer.rb +3 -2
- data/lib/rdf/query.rb +31 -16
- data/lib/rdf/query/solution.rb +5 -3
- data/lib/rdf/util/file.rb +3 -3
- data/lib/rdf/vocab.rb +5 -1
- data/lib/rdf/writer.rb +7 -2
- metadata +5 -18
checksums.yaml
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
---
|
2
|
+
!binary "U0hBMQ==":
|
3
|
+
metadata.gz: !binary |-
|
4
|
+
YjI3YmJmYTZkOGMwMTc2M2VkYTY4YWFiZGQ2YWRlN2E0NmQ5YzIxOQ==
|
5
|
+
data.tar.gz: !binary |-
|
6
|
+
NmU0NTA4ODAwNTNkNzJmMWQ1M2U3M2IyODFiNjJkYjRhM2ZiNjM2ZA==
|
7
|
+
!binary "U0hBNTEy":
|
8
|
+
metadata.gz: !binary |-
|
9
|
+
NTM5MDM3NjEzMWZhZTYwMjg1MGZjOGY5OTY4ODMyNDIxNjZjOTJiYTdiZDhk
|
10
|
+
YzAyZGUyYzllYjU1ZWZkMjM4NzEzMWU4NzViNGI0ZGI4YWMzZWEyZWJlZTkz
|
11
|
+
MzRjOTgyMzE1ZWZjN2UyYTIwZGM5ZWI4ZDRjYjhmODg0MGY5ZGM=
|
12
|
+
data.tar.gz: !binary |-
|
13
|
+
ZTA3MDBiYzUyYTBlYjJlNTk1Njg5NDYwNzI5ZTY3MGIzNjU5NmEyMjlkZTVl
|
14
|
+
MzQ4MTFjMmQyZTE1NDgwODc0ZTk4YThlYzRmYjJmOTBhYjdlYzQxOGFiZTg1
|
15
|
+
Y2MxOTQ4NDBhNzg3YzNmYjIwNWIwNjUyYTNiYzE3MzEzZTAwMzI=
|
data/README
CHANGED
@@ -115,6 +115,23 @@ A specific sub-type of Writer can also be invoked directly:
|
|
115
115
|
|
116
116
|
graph.dump(:nquads)
|
117
117
|
|
118
|
+
## Reader/Writer convenience methods
|
119
|
+
{RDF::Enumerable} implements `to_{format}` for each available instance of {RDF::Reader}.
|
120
|
+
For example, if `rdf/turtle` is loaded, this allows the following:
|
121
|
+
|
122
|
+
graph = RDF::Graph.new << [:hello, RDF::DC.title, "Hello, world!"]
|
123
|
+
graph.to_ttl
|
124
|
+
|
125
|
+
Similarly, {RDF::Mutable} implements `from_{format}` for each available instance
|
126
|
+
of {RDF::Writer}. For example:
|
127
|
+
|
128
|
+
graph = RDF::Graph.new
|
129
|
+
graph.from_ttl("[ a <http://www.w3.org/1999/02/22-rdf-syntax-ns#Resource>]")
|
130
|
+
|
131
|
+
Note that no prefixes are loaded automatically, however they can be provided as arguments:
|
132
|
+
|
133
|
+
graph.from_ttl("[ a rdf:Resource]", :prefixes => {:rdf => RDF.to_uri})
|
134
|
+
|
118
135
|
### Querying RDF data using basic graph patterns (BGPs)
|
119
136
|
|
120
137
|
require 'rdf/ntriples'
|
@@ -317,6 +334,7 @@ follows:
|
|
317
334
|
|
318
335
|
* Do your best to adhere to the existing coding conventions and idioms.
|
319
336
|
* Don't use hard tabs, and don't leave trailing whitespace on any line.
|
337
|
+
Before committing, run `git diff --check` to make sure of this.
|
320
338
|
* Do document every method you add using [YARD][] annotations. Read the
|
321
339
|
[tutorial][YARD-GS] or just look at the existing code for examples.
|
322
340
|
* Don't touch the `.gemspec` or `VERSION` files. If you need to change them,
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
1.0.
|
1
|
+
1.0.4
|
data/lib/rdf/format.rb
CHANGED
@@ -181,29 +181,55 @@ module RDF
|
|
181
181
|
end
|
182
182
|
|
183
183
|
##
|
184
|
-
# Returns the set of format symbols for
|
184
|
+
# Returns the set of format symbols for available RDF::Reader subclasses.
|
185
185
|
#
|
186
186
|
# @example
|
187
187
|
#
|
188
|
-
#
|
189
|
-
# format = RDF::Format.for(
|
188
|
+
# symbols = RDF::Format.reader_symbols
|
189
|
+
# format = RDF::Format.for(symbols.first)
|
190
190
|
#
|
191
191
|
# @return [Array<Symbol>]
|
192
192
|
def self.reader_symbols
|
193
|
-
|
193
|
+
@@readers.keys.compact.map(&:to_sym).uniq
|
194
194
|
end
|
195
195
|
|
196
196
|
##
|
197
|
-
# Returns the set of
|
197
|
+
# Returns the set of content types for available RDF::Reader subclasses.
|
198
198
|
#
|
199
199
|
# @example
|
200
200
|
#
|
201
|
-
#
|
202
|
-
# format = RDF::Format.for(
|
201
|
+
# content_types = RDF::Format.reader_types
|
202
|
+
# format = RDF::Format.for(:content_type => content_types.first)
|
203
|
+
#
|
204
|
+
# @return [Array<String>]
|
205
|
+
def self.reader_types
|
206
|
+
reader_symbols.map {|s| RDF::Format.for(s).content_type}.flatten.uniq
|
207
|
+
end
|
208
|
+
|
209
|
+
##
|
210
|
+
# Returns the set of format symbols for available RDF::Writer subclasses.
|
211
|
+
#
|
212
|
+
# @example
|
213
|
+
#
|
214
|
+
# symbols = RDF::Format.writer_symbols
|
215
|
+
# format = RDF::Format.for(symbols.first)
|
203
216
|
#
|
204
217
|
# @return [Array<Symbol>]
|
205
218
|
def self.writer_symbols
|
206
|
-
|
219
|
+
@@writers.keys.compact.map(&:to_sym).uniq
|
220
|
+
end
|
221
|
+
|
222
|
+
##
|
223
|
+
# Returns the set of content types for available RDF::Writer subclasses.
|
224
|
+
#
|
225
|
+
# @example
|
226
|
+
#
|
227
|
+
# content_types = RDF::Format.writer_types
|
228
|
+
# format = RDF::Format.for(:content_type => content_types.first)
|
229
|
+
#
|
230
|
+
# @return [Array<String>]
|
231
|
+
def self.writer_types
|
232
|
+
writer_symbols.map {|s| RDF::Format.for(s).content_type}.flatten.uniq
|
207
233
|
end
|
208
234
|
|
209
235
|
##
|
data/lib/rdf/mixin/enumerable.rb
CHANGED
@@ -492,7 +492,7 @@ module RDF
|
|
492
492
|
alias_method :enum_objects, :enum_object
|
493
493
|
|
494
494
|
##
|
495
|
-
# Returns all unique RDF contexts.
|
495
|
+
# Returns all unique RDF contexts, other than the default context.
|
496
496
|
#
|
497
497
|
# @param [Hash{Symbol => Boolean}] options
|
498
498
|
# @option options [Boolean] :unique (true)
|
@@ -510,14 +510,15 @@ module RDF
|
|
510
510
|
##
|
511
511
|
# Returns `true` if `self` contains the given RDF context.
|
512
512
|
#
|
513
|
-
# @param [RDF::Resource] value
|
513
|
+
# @param [RDF::Resource, false] value
|
514
|
+
# Use value `false` to query for the default context
|
514
515
|
# @return [Boolean]
|
515
516
|
def has_context?(value)
|
516
517
|
enum_context.include?(value)
|
517
518
|
end
|
518
519
|
|
519
520
|
##
|
520
|
-
# Iterates the given block for each unique RDF context.
|
521
|
+
# Iterates the given block for each unique RDF context, other than the default context.
|
521
522
|
#
|
522
523
|
# If no block was given, returns an enumerator.
|
523
524
|
#
|
@@ -664,5 +665,21 @@ module RDF
|
|
664
665
|
raise RDF::WriterError, "No writer found using #{args.inspect}" unless writer
|
665
666
|
writer.dump(self, nil, options)
|
666
667
|
end
|
668
|
+
|
669
|
+
##
|
670
|
+
# @overload #to_writer
|
671
|
+
# Implements #to_writer for each available instance of {RDF::Writer},
|
672
|
+
# based on the writer symbol.
|
673
|
+
#
|
674
|
+
# @return [String]
|
675
|
+
# @see {RDF::Writer.sym}
|
676
|
+
def method_missing(meth, *args)
|
677
|
+
writer = RDF::Writer.for(meth.to_s[3..-1].to_sym) if meth.to_s[0,3] == "to_"
|
678
|
+
if writer
|
679
|
+
writer.buffer(:standard_prefixes => true) {|w| w << self}
|
680
|
+
else
|
681
|
+
super
|
682
|
+
end
|
683
|
+
end
|
667
684
|
end # Enumerable
|
668
685
|
end # RDF
|
data/lib/rdf/mixin/mutable.rb
CHANGED
@@ -152,6 +152,23 @@ module RDF
|
|
152
152
|
|
153
153
|
alias_method :clear!, :clear
|
154
154
|
|
155
|
+
##
|
156
|
+
# @overload #from_reader
|
157
|
+
# Implements #from_reader for each available instance of {RDF::Reader},
|
158
|
+
# based on the reader symbol.
|
159
|
+
#
|
160
|
+
# Arguments are passed to Reader.new.
|
161
|
+
#
|
162
|
+
# @return [String]
|
163
|
+
# @see {RDF::Reader.sym}
|
164
|
+
def method_missing(meth, *args)
|
165
|
+
reader = RDF::Reader.for(meth.to_s[5..-1].to_sym) if meth.to_s[0,5] == "from_"
|
166
|
+
if reader
|
167
|
+
self << reader.new(*args)
|
168
|
+
else
|
169
|
+
super
|
170
|
+
end
|
171
|
+
end
|
155
172
|
protected
|
156
173
|
|
157
174
|
##
|
@@ -184,8 +201,5 @@ module RDF
|
|
184
201
|
def delete_statement(statement)
|
185
202
|
raise NotImplementedError.new("#{self.class}#delete_statement")
|
186
203
|
end
|
187
|
-
|
188
|
-
protected :delete_statements
|
189
|
-
protected :delete_statement
|
190
204
|
end
|
191
205
|
end
|
data/lib/rdf/mixin/queryable.rb
CHANGED
@@ -147,10 +147,14 @@ module RDF
|
|
147
147
|
query(pattern) do |statement|
|
148
148
|
return statement
|
149
149
|
end
|
150
|
-
|
150
|
+
elsif respond_to?(:each_statement)
|
151
|
+
each_statement do |statement|
|
152
|
+
return statement
|
153
|
+
end
|
151
154
|
else
|
152
|
-
super()
|
155
|
+
return super()
|
153
156
|
end
|
157
|
+
nil
|
154
158
|
end
|
155
159
|
|
156
160
|
##
|
data/lib/rdf/model/graph.rb
CHANGED
@@ -31,15 +31,24 @@ module RDF
|
|
31
31
|
##
|
32
32
|
# Returns the options passed to this graph when it was constructed.
|
33
33
|
#
|
34
|
+
# @!attribute [r] options
|
34
35
|
# @return [Hash{Symbol => Object}]
|
35
36
|
attr_reader :options
|
36
37
|
|
37
38
|
##
|
39
|
+
# Name of this graph, if it is part of an {RDF::Repository}
|
40
|
+
# @!attribute [rw] context
|
38
41
|
# @return [RDF::Resource]
|
39
|
-
# @
|
42
|
+
# @note In the next release, only projections from an
|
43
|
+
# {RDF::Enumerable} supporting contexts will have a context.
|
40
44
|
attr_accessor :context
|
41
45
|
|
46
|
+
alias_method :name, :context
|
47
|
+
alias_method :name=, :context=
|
48
|
+
|
42
49
|
##
|
50
|
+
# {RDF::Queryable} backing this graph.
|
51
|
+
# @!attribute [rw] data
|
43
52
|
# @return [RDF::Queryable]
|
44
53
|
attr_accessor :data
|
45
54
|
|
@@ -72,9 +81,10 @@ module RDF
|
|
72
81
|
# @param [RDF::Resource] context
|
73
82
|
# The context only provides a context for loading relative documents
|
74
83
|
# @param [Hash{Symbol => Object}] options
|
75
|
-
# @
|
76
|
-
#
|
77
|
-
#
|
84
|
+
# @note contexts are only useful when used as a projection
|
85
|
+
# on a `:data` which supports contexts. Otherwise, there is no
|
86
|
+
# such thing as a named graph in RDF 1.1, a repository may have
|
87
|
+
# graphs which are named, but the name is not a property of the graph.
|
78
88
|
# @overload initialize(options)
|
79
89
|
# @param [Hash{Symbol => Object}] options
|
80
90
|
# @yield [graph]
|
@@ -139,12 +149,12 @@ module RDF
|
|
139
149
|
end
|
140
150
|
|
141
151
|
##
|
142
|
-
#
|
152
|
+
# A graph is durable if it's underlying data model is durable
|
143
153
|
#
|
144
154
|
# @return [Boolean]
|
145
155
|
# @see RDF::Durable#durable?
|
146
156
|
def durable?
|
147
|
-
|
157
|
+
@data.durable?
|
148
158
|
end
|
149
159
|
|
150
160
|
##
|
@@ -156,10 +166,9 @@ module RDF
|
|
156
166
|
end
|
157
167
|
|
158
168
|
##
|
159
|
-
# Returns the
|
169
|
+
# Returns the {RDF::Resource} representation of this graph.
|
160
170
|
#
|
161
|
-
# @return [RDF::
|
162
|
-
# @note The next release, graphs will not be named, this will return nil
|
171
|
+
# @return [RDF::Resource]
|
163
172
|
def to_uri
|
164
173
|
context
|
165
174
|
end
|
@@ -169,7 +178,7 @@ module RDF
|
|
169
178
|
#
|
170
179
|
# @return [String]
|
171
180
|
def to_s
|
172
|
-
named? ? context.to_s : "
|
181
|
+
named? ? context.to_s : "default"
|
173
182
|
end
|
174
183
|
|
175
184
|
##
|
@@ -178,7 +187,7 @@ module RDF
|
|
178
187
|
# @return [Boolean]
|
179
188
|
# @see RDF::Enumerable#empty?
|
180
189
|
def empty?
|
181
|
-
|
190
|
+
!@data.has_context?(context || false)
|
182
191
|
end
|
183
192
|
|
184
193
|
##
|
@@ -196,7 +205,7 @@ module RDF
|
|
196
205
|
# @return [Integer]
|
197
206
|
# @see RDF::Enumerable#count
|
198
207
|
def count
|
199
|
-
@data.query(:context => context).count
|
208
|
+
@data.query(:context => context || false).count
|
200
209
|
end
|
201
210
|
|
202
211
|
##
|
@@ -207,7 +216,7 @@ module RDF
|
|
207
216
|
# @see RDF::Enumerable#has_statement?
|
208
217
|
def has_statement?(statement)
|
209
218
|
statement = statement.dup
|
210
|
-
statement.context = context
|
219
|
+
statement.context = context
|
211
220
|
@data.has_statement?(statement)
|
212
221
|
end
|
213
222
|
|
@@ -219,7 +228,27 @@ module RDF
|
|
219
228
|
# @return [Enumerator]
|
220
229
|
# @see RDF::Enumerable#each_statement
|
221
230
|
def each(&block)
|
222
|
-
@data.
|
231
|
+
if @data.respond_to?(:query)
|
232
|
+
@data.query(:context => context || false, &block)
|
233
|
+
elsif @data.respond_to?(:each)
|
234
|
+
@data.each(&block)
|
235
|
+
else
|
236
|
+
@data.to_a.each(&block)
|
237
|
+
end
|
238
|
+
end
|
239
|
+
|
240
|
+
##
|
241
|
+
# Graph equivalence based on the contents of each graph being _exactly_
|
242
|
+
# the same. To determine if the have the same _meaning_, consider
|
243
|
+
# [rdf-isomorphic](http://rubygems.org/gems/rdf-isomorphic).
|
244
|
+
#
|
245
|
+
# @param [RDF::Graph] other
|
246
|
+
# @return [Boolean]
|
247
|
+
# @see http://rubygems.org/gems/rdf-isomorphic
|
248
|
+
def ==(other)
|
249
|
+
other.is_a?(RDF::Graph) &&
|
250
|
+
context == other.context &&
|
251
|
+
statements.to_a == other.statements.to_a
|
223
252
|
end
|
224
253
|
|
225
254
|
##
|
@@ -227,7 +256,7 @@ module RDF
|
|
227
256
|
# @see RDF::Queryable#query
|
228
257
|
def query_pattern(pattern, &block)
|
229
258
|
pattern = pattern.dup
|
230
|
-
pattern.context = context
|
259
|
+
pattern.context = context || false
|
231
260
|
@data.query(pattern, &block)
|
232
261
|
end
|
233
262
|
|
@@ -253,7 +282,7 @@ module RDF
|
|
253
282
|
# @private
|
254
283
|
# @see RDF::Mutable#clear
|
255
284
|
def clear_statements
|
256
|
-
@data.delete(:context => context)
|
285
|
+
@data.delete(:context => context || false)
|
257
286
|
end
|
258
287
|
|
259
288
|
protected :query_pattern
|
data/lib/rdf/model/literal.rb
CHANGED
@@ -343,6 +343,17 @@ module RDF
|
|
343
343
|
self
|
344
344
|
end
|
345
345
|
|
346
|
+
##
|
347
|
+
# Returns the base representation of this URI.
|
348
|
+
#
|
349
|
+
# @return [Sring]
|
350
|
+
def to_base
|
351
|
+
text = %("#{escape(value)}")
|
352
|
+
text << "@#{language}" if has_language?
|
353
|
+
text << "^^#{datatype.to_base}" if has_datatype?
|
354
|
+
text
|
355
|
+
end
|
356
|
+
|
346
357
|
##
|
347
358
|
# Returns the value as a string.
|
348
359
|
#
|
data/lib/rdf/model/node.rb
CHANGED
@@ -137,6 +137,14 @@ module RDF
|
|
137
137
|
end
|
138
138
|
alias_method :===, :==
|
139
139
|
|
140
|
+
##
|
141
|
+
# Returns the base representation of this URI.
|
142
|
+
#
|
143
|
+
# @return [Sring]
|
144
|
+
def to_base
|
145
|
+
to_s
|
146
|
+
end
|
147
|
+
|
140
148
|
##
|
141
149
|
# Returns a string representation of this blank node.
|
142
150
|
#
|
data/lib/rdf/model/statement.rb
CHANGED
@@ -57,6 +57,7 @@ module RDF
|
|
57
57
|
# @option options [RDF::URI] :predicate (nil)
|
58
58
|
# @option options [RDF::Term] :object (nil)
|
59
59
|
# @option options [RDF::Resource] :context (nil)
|
60
|
+
# Note, in RDF 1.1, a context MUST be an IRI.
|
60
61
|
#
|
61
62
|
# @overload initialize(subject, predicate, object, options = {})
|
62
63
|
# @param [RDF::Resource] subject
|
@@ -259,25 +260,9 @@ module RDF
|
|
259
260
|
#
|
260
261
|
# @return [String]
|
261
262
|
def to_s
|
262
|
-
|
263
|
-
|
264
|
-
|
265
|
-
when RDF::URI then "<#{subject}>"
|
266
|
-
else subject.inspect
|
267
|
-
end
|
268
|
-
buffer << " <#{predicate}> "
|
269
|
-
buffer << case object
|
270
|
-
when RDF::Literal then object.to_s
|
271
|
-
when RDF::Node then object.to_s
|
272
|
-
when RDF::URI then "<#{object}>"
|
273
|
-
else object.inspect
|
274
|
-
end
|
275
|
-
buffer << case context
|
276
|
-
when nil then " ."
|
277
|
-
else " <#{context}> ."
|
278
|
-
end
|
279
|
-
buffer.string
|
280
|
-
end
|
263
|
+
(context ? to_quad : to_triple).map do |term|
|
264
|
+
term.respond_to?(:to_base) ? term.to_base : term.inspect
|
265
|
+
end.join(" ") + " ."
|
281
266
|
end
|
282
267
|
|
283
268
|
##
|
data/lib/rdf/model/term.rb
CHANGED
@@ -66,12 +66,36 @@ module RDF
|
|
66
66
|
end
|
67
67
|
|
68
68
|
##
|
69
|
-
# Returns
|
69
|
+
# Returns a base representation of `self`.
|
70
70
|
#
|
71
|
-
# @return [
|
72
|
-
|
73
|
-
|
74
|
-
|
71
|
+
# @return [RDF::Value]
|
72
|
+
def to_base
|
73
|
+
self
|
74
|
+
end
|
75
|
+
|
76
|
+
##
|
77
|
+
# Returns `true` if `self` is a {RDF::Term}.
|
78
|
+
#
|
79
|
+
# @return [Boolean]
|
80
|
+
def term?
|
81
|
+
true
|
75
82
|
end
|
83
|
+
|
84
|
+
protected
|
85
|
+
##
|
86
|
+
# Escape a term using standard character escapes
|
87
|
+
#
|
88
|
+
# @param [String] string
|
89
|
+
# @return [String]
|
90
|
+
def escape(string)
|
91
|
+
string.gsub('\\', '\\\\').
|
92
|
+
gsub("\b", '\\b').
|
93
|
+
gsub("\f", '\\f').
|
94
|
+
gsub("\t", '\\t').
|
95
|
+
gsub("\n", '\\n').
|
96
|
+
gsub("\r", '\\r').
|
97
|
+
gsub('"', '\\"')
|
98
|
+
end
|
99
|
+
|
76
100
|
end # Term
|
77
101
|
end # RDF
|
data/lib/rdf/model/uri.rb
CHANGED
@@ -19,6 +19,7 @@ module RDF
|
|
19
19
|
# @example Getting the string representation of a URI
|
20
20
|
# uri.to_s #=> "http://rdf.rubyforge.org/"
|
21
21
|
#
|
22
|
+
# http://en.wikipedia.org/wiki/Internationalized_Resource_Identifier
|
22
23
|
# @see http://en.wikipedia.org/wiki/Uniform_Resource_Identifier
|
23
24
|
# @see http://www.ietf.org/rfc/rfc3986.txt
|
24
25
|
# @see http://www.ietf.org/rfc/rfc3987.txt
|
@@ -41,54 +42,54 @@ module RDF
|
|
41
42
|
[\\u{A0000}-\\u{AFFFD}]|[\\u{B0000}-\\u{BFFFD}]|[\\u{C0000}-\\u{CFFFD}]|
|
42
43
|
[\\u{D0000}-\\u{DFFFD}]|[\\u{E0000}-\\u{EFFFD}]
|
43
44
|
EOS
|
44
|
-
IPRIVATE = Regexp.compile("[\\uE000-\\uF8FF]|[\\u{F0000}-\\u{FFFFD}]|[\\u100000-\\u10FFFD]")
|
45
|
+
IPRIVATE = Regexp.compile("[\\uE000-\\uF8FF]|[\\u{F0000}-\\u{FFFFD}]|[\\u100000-\\u10FFFD]").freeze
|
45
46
|
end
|
46
47
|
|
47
|
-
SCHEME = Regexp.compile("[A-za-z](?:[A-Za-z0-9+-\.])*")
|
48
|
-
PORT = Regexp.compile("[0-9]*")
|
49
|
-
IP_literal = Regexp.compile("\\[[0-9A-Fa-f:\\.]*\\]") # Simplified, no IPvFuture
|
50
|
-
PCT_ENCODED = Regexp.compile("%[0-9A-Fa-f]{2}")
|
51
|
-
GEN_DELIMS = Regexp.compile("[:/\\?\\#\\[\\]@]")
|
52
|
-
SUB_DELIMS = Regexp.compile("[!\\$&'\\(\\)\\*\\+,;=]")
|
53
|
-
RESERVED = Regexp.compile("(?:#{GEN_DELIMS}|#{SUB_DELIMS})")
|
54
|
-
UNRESERVED = Regexp.compile("[A-Za-z0-9]|-|\\.|_|~")
|
48
|
+
SCHEME = Regexp.compile("[A-za-z](?:[A-Za-z0-9+-\.])*").freeze
|
49
|
+
PORT = Regexp.compile("[0-9]*").freeze
|
50
|
+
IP_literal = Regexp.compile("\\[[0-9A-Fa-f:\\.]*\\]").freeze # Simplified, no IPvFuture
|
51
|
+
PCT_ENCODED = Regexp.compile("%[0-9A-Fa-f]{2}").freeze
|
52
|
+
GEN_DELIMS = Regexp.compile("[:/\\?\\#\\[\\]@]").freeze
|
53
|
+
SUB_DELIMS = Regexp.compile("[!\\$&'\\(\\)\\*\\+,;=]").freeze
|
54
|
+
RESERVED = Regexp.compile("(?:#{GEN_DELIMS}|#{SUB_DELIMS})").freeze
|
55
|
+
UNRESERVED = Regexp.compile("[A-Za-z0-9]|-|\\.|_|~").freeze
|
55
56
|
|
56
57
|
if RUBY_VERSION >= '1.9'
|
57
|
-
IUNRESERVED = Regexp.compile("[A-Za-z0-9]|-|\\.|_|~|#{UCSCHAR}")
|
58
|
+
IUNRESERVED = Regexp.compile("[A-Za-z0-9]|-|\\.|_|~|#{UCSCHAR}").freeze
|
58
59
|
else
|
59
|
-
IUNRESERVED = Regexp.compile("[A-Za-z0-9]|-|\\.|_|~")
|
60
|
+
IUNRESERVED = Regexp.compile("[A-Za-z0-9]|-|\\.|_|~").freeze
|
60
61
|
end
|
61
62
|
|
62
|
-
IPCHAR = Regexp.compile("(?:#{IUNRESERVED}|#{PCT_ENCODED}|#{SUB_DELIMS}|:|@)")
|
63
|
+
IPCHAR = Regexp.compile("(?:#{IUNRESERVED}|#{PCT_ENCODED}|#{SUB_DELIMS}|:|@)").freeze
|
63
64
|
|
64
65
|
if RUBY_VERSION >= '1.9'
|
65
|
-
IQUERY = Regexp.compile("(?:#{IPCHAR}|#{IPRIVATE}|/|\\?)*")
|
66
|
+
IQUERY = Regexp.compile("(?:#{IPCHAR}|#{IPRIVATE}|/|\\?)*").freeze
|
66
67
|
else
|
67
|
-
IQUERY = Regexp.compile("(?:#{IPCHAR}|/|\\?)*")
|
68
|
+
IQUERY = Regexp.compile("(?:#{IPCHAR}|/|\\?)*").freeze
|
68
69
|
end
|
69
70
|
|
70
|
-
IFRAGMENT = Regexp.compile("(?:#{IPCHAR}|/|\\?)*")
|
71
|
+
IFRAGMENT = Regexp.compile("(?:#{IPCHAR}|/|\\?)*").freeze.freeze
|
71
72
|
|
72
|
-
ISEGMENT = Regexp.compile("(?:#{IPCHAR})*")
|
73
|
-
ISEGMENT_NZ = Regexp.compile("(?:#{IPCHAR})+")
|
74
|
-
ISEGMENT_NZ_NC = Regexp.compile("(?:(?:#{IUNRESERVED})|(?:#{PCT_ENCODED})|(?:#{SUB_DELIMS})|@)+")
|
73
|
+
ISEGMENT = Regexp.compile("(?:#{IPCHAR})*").freeze
|
74
|
+
ISEGMENT_NZ = Regexp.compile("(?:#{IPCHAR})+").freeze
|
75
|
+
ISEGMENT_NZ_NC = Regexp.compile("(?:(?:#{IUNRESERVED})|(?:#{PCT_ENCODED})|(?:#{SUB_DELIMS})|@)+").freeze
|
75
76
|
|
76
|
-
IPATH_ABEMPTY = Regexp.compile("(?:/#{ISEGMENT})*")
|
77
|
-
IPATH_ABSOLUTE = Regexp.compile("/(?:(?:#{ISEGMENT_NZ})(/#{ISEGMENT})*)?")
|
78
|
-
IPATH_NOSCHEME = Regexp.compile("(?:#{ISEGMENT_NZ_NC})(?:/#{ISEGMENT})*")
|
79
|
-
IPATH_ROOTLESS = Regexp.compile("(?:#{ISEGMENT_NZ})(?:/#{ISEGMENT})*")
|
80
|
-
IPATH_EMPTY = Regexp.compile("")
|
77
|
+
IPATH_ABEMPTY = Regexp.compile("(?:/#{ISEGMENT})*").freeze
|
78
|
+
IPATH_ABSOLUTE = Regexp.compile("/(?:(?:#{ISEGMENT_NZ})(/#{ISEGMENT})*)?").freeze
|
79
|
+
IPATH_NOSCHEME = Regexp.compile("(?:#{ISEGMENT_NZ_NC})(?:/#{ISEGMENT})*").freeze
|
80
|
+
IPATH_ROOTLESS = Regexp.compile("(?:#{ISEGMENT_NZ})(?:/#{ISEGMENT})*").freeze
|
81
|
+
IPATH_EMPTY = Regexp.compile("").freeze
|
81
82
|
|
82
|
-
IREG_NAME = Regexp.compile("(?:(?:#{IUNRESERVED})|(?:#{PCT_ENCODED})|(?:#{SUB_DELIMS}))*")
|
83
|
-
IHOST = Regexp.compile("(?:#{IP_literal})|(?:#{IREG_NAME})")
|
84
|
-
IUSERINFO = Regexp.compile("(?:(?:#{IUNRESERVED})|(?:#{PCT_ENCODED})|(?:#{SUB_DELIMS})|:)*")
|
85
|
-
IAUTHORITY = Regexp.compile("(?:#{IUSERINFO}@)?#{IHOST}(?::#{PORT})?")
|
83
|
+
IREG_NAME = Regexp.compile("(?:(?:#{IUNRESERVED})|(?:#{PCT_ENCODED})|(?:#{SUB_DELIMS}))*").freeze
|
84
|
+
IHOST = Regexp.compile("(?:#{IP_literal})|(?:#{IREG_NAME})").freeze
|
85
|
+
IUSERINFO = Regexp.compile("(?:(?:#{IUNRESERVED})|(?:#{PCT_ENCODED})|(?:#{SUB_DELIMS})|:)*").freeze
|
86
|
+
IAUTHORITY = Regexp.compile("(?:#{IUSERINFO}@)?#{IHOST}(?::#{PORT})?").freeze
|
86
87
|
|
87
|
-
IRELATIVE_PART = Regexp.compile("(?:(?://#{IAUTHORITY}(?:#{IPATH_ABEMPTY}))|(?:#{IPATH_ABSOLUTE})|(?:#{IPATH_NOSCHEME})|(?:#{IPATH_EMPTY}))")
|
88
|
-
IRELATIVE_REF = Regexp.compile("^#{IRELATIVE_PART}(?:\\?#{IQUERY})?(?:\\##{IFRAGMENT})?$")
|
88
|
+
IRELATIVE_PART = Regexp.compile("(?:(?://#{IAUTHORITY}(?:#{IPATH_ABEMPTY}))|(?:#{IPATH_ABSOLUTE})|(?:#{IPATH_NOSCHEME})|(?:#{IPATH_EMPTY}))").freeze
|
89
|
+
IRELATIVE_REF = Regexp.compile("^#{IRELATIVE_PART}(?:\\?#{IQUERY})?(?:\\##{IFRAGMENT})?$").freeze
|
89
90
|
|
90
|
-
IHIER_PART = Regexp.compile("(?:(?://#{IAUTHORITY}#{IPATH_ABEMPTY})|(?:#{IPATH_ABSOLUTE})|(?:#{IPATH_ROOTLESS})|(?:#{IPATH_EMPTY}))")
|
91
|
-
IRI = Regexp.compile("^#{SCHEME}:(?:#{IHIER_PART})(?:\\?#{IQUERY})?(?:\\##{IFRAGMENT})?$")
|
91
|
+
IHIER_PART = Regexp.compile("(?:(?://#{IAUTHORITY}#{IPATH_ABEMPTY})|(?:#{IPATH_ABSOLUTE})|(?:#{IPATH_ROOTLESS})|(?:#{IPATH_EMPTY}))").freeze
|
92
|
+
IRI = Regexp.compile("^#{SCHEME}:(?:#{IHIER_PART})(?:\\?#{IQUERY})?(?:\\##{IFRAGMENT})?$").freeze
|
92
93
|
|
93
94
|
##
|
94
95
|
# @return [RDF::Util::Cache]
|
@@ -148,14 +149,6 @@ module RDF
|
|
148
149
|
end
|
149
150
|
end
|
150
151
|
|
151
|
-
##
|
152
|
-
# Returns `false`.
|
153
|
-
#
|
154
|
-
# @return [Boolean] `true` or `false`
|
155
|
-
def anonymous?
|
156
|
-
false
|
157
|
-
end
|
158
|
-
|
159
152
|
##
|
160
153
|
# Returns `true`.
|
161
154
|
#
|
@@ -592,6 +585,14 @@ module RDF
|
|
592
585
|
self
|
593
586
|
end
|
594
587
|
|
588
|
+
##
|
589
|
+
# Returns the base representation of this URI.
|
590
|
+
#
|
591
|
+
# @return [Sring]
|
592
|
+
def to_base
|
593
|
+
"<#{escape(@uri.to_s)}>"
|
594
|
+
end
|
595
|
+
|
595
596
|
##
|
596
597
|
# Returns the string representation of this URI.
|
597
598
|
#
|
@@ -641,4 +642,7 @@ module RDF
|
|
641
642
|
end
|
642
643
|
end
|
643
644
|
end # URI
|
645
|
+
|
646
|
+
# RDF::IRI is a synonym for RDF::URI
|
647
|
+
IRI = URI
|
644
648
|
end # RDF
|
data/lib/rdf/model/value.rb
CHANGED
@@ -4,7 +4,8 @@ module RDF
|
|
4
4
|
#
|
5
5
|
# This is the basis for the RDF.rb class hierarchy. Anything that can be a
|
6
6
|
# term of {RDF::Statement RDF statements} should directly or indirectly
|
7
|
-
# include this module
|
7
|
+
# include this module, but it does not define classes that can be included
|
8
|
+
# within a {RDF::Statement}, for this see {RDF::Term}.
|
8
9
|
#
|
9
10
|
# @example Checking if a value is a resource (blank node or URI reference)
|
10
11
|
# value.resource?
|
@@ -19,15 +20,16 @@ module RDF
|
|
19
20
|
# @example Checking if a value is a literal
|
20
21
|
# value.literal?
|
21
22
|
#
|
22
|
-
# @see RDF::Graph
|
23
23
|
# @see RDF::Literal
|
24
24
|
# @see RDF::Node
|
25
25
|
# @see RDF::Resource
|
26
|
-
# @see RDF::Statement
|
27
26
|
# @see RDF::URI
|
27
|
+
# @see RDF::Graph
|
28
|
+
# @see RDF::List
|
29
|
+
# @see RDF::Statement
|
28
30
|
module Value
|
29
31
|
##
|
30
|
-
# Returns `true` if `self` is a
|
32
|
+
# Returns `true` if `self` is a {RDF::Graph}.
|
31
33
|
#
|
32
34
|
# @return [Boolean]
|
33
35
|
def graph?
|
@@ -35,23 +37,31 @@ module RDF
|
|
35
37
|
end
|
36
38
|
|
37
39
|
##
|
38
|
-
# Returns `true` if `self` is a
|
40
|
+
# Returns `true` if `self` is a {RDF::Statement}.
|
39
41
|
#
|
40
42
|
# @return [Boolean]
|
41
|
-
def
|
43
|
+
def statement?
|
42
44
|
false
|
43
45
|
end
|
44
46
|
|
45
47
|
##
|
46
|
-
# Returns `true` if `self` is a
|
48
|
+
# Returns `true` if `self` is a {RDF::List}.
|
47
49
|
#
|
48
50
|
# @return [Boolean]
|
49
|
-
def
|
51
|
+
def list?
|
50
52
|
false
|
51
53
|
end
|
52
54
|
|
53
55
|
##
|
54
|
-
# Returns `true` if `self` is a
|
56
|
+
# Returns `true` if `self` is a {RDF::Term}.
|
57
|
+
#
|
58
|
+
# @return [Boolean]
|
59
|
+
def term?
|
60
|
+
false
|
61
|
+
end
|
62
|
+
|
63
|
+
##
|
64
|
+
# Returns `true` if `self` is a {RDF::Resource}.
|
55
65
|
#
|
56
66
|
# @return [Boolean]
|
57
67
|
def resource?
|
@@ -59,10 +69,18 @@ module RDF
|
|
59
69
|
end
|
60
70
|
|
61
71
|
##
|
62
|
-
# Returns `true` if `self` is a
|
72
|
+
# Returns `true` if `self` is a {RDF::Literal}.
|
63
73
|
#
|
64
74
|
# @return [Boolean]
|
65
|
-
def
|
75
|
+
def literal?
|
76
|
+
false
|
77
|
+
end
|
78
|
+
|
79
|
+
##
|
80
|
+
# Returns `true` if `self` is a {RDF::Node}.
|
81
|
+
#
|
82
|
+
# @return [Boolean]
|
83
|
+
def node?
|
66
84
|
false
|
67
85
|
end
|
68
86
|
|
@@ -77,7 +95,7 @@ module RDF
|
|
77
95
|
end
|
78
96
|
|
79
97
|
##
|
80
|
-
# Returns `true` if `self` is a URI
|
98
|
+
# Returns `true` if `self` is a {RDF::URI}.
|
81
99
|
#
|
82
100
|
# @return [Boolean]
|
83
101
|
def uri?
|
@@ -85,7 +103,7 @@ module RDF
|
|
85
103
|
end
|
86
104
|
|
87
105
|
##
|
88
|
-
# Returns `true` if `self` is a
|
106
|
+
# Returns `true` if `self` is a {RDF::Query::Variable}.
|
89
107
|
#
|
90
108
|
# @return [Boolean]
|
91
109
|
# @since 0.1.7
|
@@ -93,6 +111,14 @@ module RDF
|
|
93
111
|
false
|
94
112
|
end
|
95
113
|
|
114
|
+
##
|
115
|
+
# Is this an anonymous value?
|
116
|
+
#
|
117
|
+
# @return [Boolean] `true` or `false`
|
118
|
+
def anonymous?
|
119
|
+
false
|
120
|
+
end
|
121
|
+
|
96
122
|
##
|
97
123
|
# Returns `true` if the value has a valid representation
|
98
124
|
#
|
data/lib/rdf/nquads.rb
CHANGED
@@ -14,12 +14,13 @@ module RDF
|
|
14
14
|
# RDF::Format.for("etc/doap.nq")
|
15
15
|
# RDF::Format.for(:file_name => "etc/doap.nq")
|
16
16
|
# RDF::Format.for(:file_extension => "nq")
|
17
|
+
# RDF::Format.for(:content_type => "application/n-quads")
|
17
18
|
# RDF::Format.for(:content_type => "text/x-nquads")
|
18
19
|
#
|
19
20
|
# @see http://sw.deri.org/2008/07/n-quads/#mediatype
|
20
21
|
# @since 0.4.0
|
21
22
|
class Format < RDF::Format
|
22
|
-
content_type '
|
23
|
+
content_type 'application/n-quads', :extension => :nq, :alias => ['text/x-nquads']
|
23
24
|
content_encoding 'utf-8'
|
24
25
|
|
25
26
|
reader { RDF::NQuads::Reader }
|
@@ -78,6 +79,9 @@ module RDF
|
|
78
79
|
predicate = read_uriref(:intern => true) || fail_predicate
|
79
80
|
object = read_uriref || read_node || read_literal || fail_object
|
80
81
|
context = read_uriref || read_node || read_literal
|
82
|
+
if validate? && !read_eos
|
83
|
+
raise RDF::ReaderError, "expected end of statement in line #{lineno}: #{current_line.inspect}"
|
84
|
+
end
|
81
85
|
return [subject, predicate, object, {:context => context}]
|
82
86
|
end
|
83
87
|
rescue RDF::ReaderError => e
|
data/lib/rdf/ntriples/reader.rb
CHANGED
@@ -28,20 +28,6 @@ module RDF::NTriples
|
|
28
28
|
class Reader < RDF::Reader
|
29
29
|
format RDF::NTriples::Format
|
30
30
|
|
31
|
-
# @see http://www.w3.org/TR/rdf-testcases/#ntrip_grammar
|
32
|
-
COMMENT = /^#\s*(.*)$/.freeze
|
33
|
-
NODEID = /^_:([A-Za-z][A-Za-z0-9\-_]*)/.freeze
|
34
|
-
URIREF = /^<([^>]+)>/.freeze
|
35
|
-
LITERAL_PLAIN = /^"((?:\\"|[^"])*)"/.freeze
|
36
|
-
LITERAL_WITH_LANGUAGE = /^"((?:\\"|[^"])*)"@([a-z]+[\-A-Za-z0-9]*)/.freeze
|
37
|
-
LITERAL_WITH_DATATYPE = /^"((?:\\"|[^"])*)"\^\^<([^>]+)>/.freeze
|
38
|
-
LANGUAGE_TAG = /^@([a-z]+[\-A-Za-z0-9]*)/.freeze
|
39
|
-
DATATYPE_URI = /^\^\^<([^>]+)>/.freeze
|
40
|
-
LITERAL = Regexp.union(LITERAL_WITH_LANGUAGE, LITERAL_WITH_DATATYPE, LITERAL_PLAIN).freeze
|
41
|
-
SUBJECT = Regexp.union(URIREF, NODEID).freeze
|
42
|
-
PREDICATE = Regexp.union(URIREF).freeze
|
43
|
-
OBJECT = Regexp.union(URIREF, NODEID, LITERAL).freeze
|
44
|
-
|
45
31
|
# @see http://www.w3.org/TR/rdf-testcases/#ntrip_strings
|
46
32
|
ESCAPE_CHARS = ["\b", "\f", "\t", "\n", "\r", "\"", "\\"].freeze
|
47
33
|
ESCAPE_CHAR4 = /\\u([0-9A-Fa-f]{4,4})/.freeze
|
@@ -51,6 +37,97 @@ module RDF::NTriples
|
|
51
37
|
ESCAPE_SURROGATE1 = (0xD800..0xDBFF).freeze
|
52
38
|
ESCAPE_SURROGATE2 = (0xDC00..0xDFFF).freeze
|
53
39
|
|
40
|
+
|
41
|
+
# Terminals from rdf-turtle.
|
42
|
+
#
|
43
|
+
# @see http://www.w3.org/TR/n-triples/
|
44
|
+
# @see http://www.w3.org/TR/turtle/
|
45
|
+
if RUBY_VERSION >= '1.9'
|
46
|
+
##
|
47
|
+
# Unicode regular expressions for Ruby 1.9+ with the Oniguruma engine.
|
48
|
+
U_CHARS1 = Regexp.compile(<<-EOS.gsub(/\s+/, ''))
|
49
|
+
[\\u00C0-\\u00D6]|[\\u00D8-\\u00F6]|[\\u00F8-\\u02FF]|
|
50
|
+
[\\u0370-\\u037D]|[\\u037F-\\u1FFF]|[\\u200C-\\u200D]|
|
51
|
+
[\\u2070-\\u218F]|[\\u2C00-\\u2FEF]|[\\u3001-\\uD7FF]|
|
52
|
+
[\\uF900-\\uFDCF]|[\\uFDF0-\\uFFFD]|[\\u{10000}-\\u{EFFFF}]
|
53
|
+
EOS
|
54
|
+
U_CHARS2 = Regexp.compile("\\u00B7|[\\u0300-\\u036F]|[\\u203F-\\u2040]").freeze
|
55
|
+
IRI_RANGE = Regexp.compile("[[^<>\"{}|^`\\\\]&&[^\\x00-\\x20]]").freeze
|
56
|
+
else
|
57
|
+
##
|
58
|
+
# UTF-8 regular expressions for Ruby 1.8.x.
|
59
|
+
U_CHARS1 = Regexp.compile(<<-EOS.gsub(/\s+/, ''))
|
60
|
+
\\xC3[\\x80-\\x96]| (?# [\\u00C0-\\u00D6]|)
|
61
|
+
\\xC3[\\x98-\\xB6]| (?# [\\u00D8-\\u00F6]|)
|
62
|
+
\\xC3[\\xB8-\\xBF]|[\\xC4-\\xCB][\\x80-\\xBF]| (?# [\\u00F8-\\u02FF]|)
|
63
|
+
\\xCD[\\xB0-\\xBD]| (?# [\\u0370-\\u037D]|)
|
64
|
+
\\xCD\\xBF|[\\xCE-\\xDF][\\x80-\\xBF]| (?# [\\u037F-\\u1FFF]|)
|
65
|
+
\\xE0[\\xA0-\\xBF][\\x80-\\xBF]| (?# ...)
|
66
|
+
\\xE1[\\x80-\\xBF][\\x80-\\xBF]| (?# ...)
|
67
|
+
\\xE2\\x80[\\x8C-\\x8D]| (?# [\\u200C-\\u200D]|)
|
68
|
+
\\xE2\\x81[\\xB0-\\xBF]| (?# [\\u2070-\\u218F]|)
|
69
|
+
\\xE2[\\x82-\\x85][\\x80-\\xBF]| (?# ...)
|
70
|
+
\\xE2\\x86[\\x80-\\x8F]| (?# ...)
|
71
|
+
\\xE2[\\xB0-\\xBE][\\x80-\\xBF]| (?# [\\u2C00-\\u2FEF]|)
|
72
|
+
\\xE2\\xBF[\\x80-\\xAF]| (?# ...)
|
73
|
+
\\xE3\\x80[\\x81-\\xBF]| (?# [\\u3001-\\uD7FF]|)
|
74
|
+
\\xE3[\\x81-\\xBF][\\x80-\\xBF]| (?# ...)
|
75
|
+
[\\xE4-\\xEC][\\x80-\\xBF][\\x80-\\xBF]| (?# ...)
|
76
|
+
\\xED[\\x80-\\x9F][\\x80-\\xBF]| (?# ...)
|
77
|
+
\\xEF[\\xA4-\\xB6][\\x80-\\xBF]| (?# [\\uF900-\\uFDCF]|)
|
78
|
+
\\xEF\\xB7[\\x80-\\x8F]| (?# ...)
|
79
|
+
\\xEF\\xB7[\\xB0-\\xBF]| (?# [\\uFDF0-\\uFFFD]|)
|
80
|
+
\\xEF[\\xB8-\\xBE][\\x80-\\xBF]| (?# ...)
|
81
|
+
\\xEF\\xBF[\\x80-\\xBD]| (?# ...)
|
82
|
+
\\xF0[\\x90-\\xBF][\\x80-\\xBF][\\x80-\\xBF]| (?# [\\u{10000}-\\u{EFFFF}])
|
83
|
+
[\\xF1-\\xF2][\\x80-\\xBF][\\x80-\\xBF][\\x80-\\xBF]|
|
84
|
+
\\xF3[\\x80-\\xAF][\\x80-\\xBF][\\x80-\\xBF] (?# ...)
|
85
|
+
EOS
|
86
|
+
U_CHARS2 = Regexp.compile(<<-EOS.gsub(/\s+/, ''))
|
87
|
+
\\xC2\\xB7| (?# \\u00B7|)
|
88
|
+
\\xCC[\\x80-\\xBF]|\\xCD[\\x80-\\xAF]| (?# [\\u0300-\\u036F]|)
|
89
|
+
\\xE2\\x80\\xBF|\\xE2\\x81\\x80 (?# [\\u203F-\\u2040])
|
90
|
+
EOS
|
91
|
+
IRI_RANGE = Regexp.compile(<<-EOS.gsub(/\s+/, ''))
|
92
|
+
\\x21| (?# ")
|
93
|
+
[\\x23-\\x3b]|\\x3d| (?# < & >)
|
94
|
+
[\\x3f-\\x5b]|\\x5d|\\x5f| (?# \ ^ `)
|
95
|
+
[\\x61-\\x7a]| (?# { } |)
|
96
|
+
[\\x7e-\\xff]
|
97
|
+
EOS
|
98
|
+
end
|
99
|
+
|
100
|
+
# 163s
|
101
|
+
PN_CHARS_BASE = /[A-Z]|[a-z]|#{U_CHARS1}/.freeze
|
102
|
+
# 164s
|
103
|
+
PN_CHARS_U = /_|#{PN_CHARS_BASE}/.freeze
|
104
|
+
# 166s
|
105
|
+
PN_CHARS = /-|[0-9]|#{PN_CHARS_U}|#{U_CHARS2}/.freeze
|
106
|
+
# 159s
|
107
|
+
ECHAR = /\\[tbnrf\\"']/.freeze
|
108
|
+
# 18
|
109
|
+
IRIREF = /<((?:#{IRI_RANGE}|#{ESCAPE_CHAR})*)>/.freeze
|
110
|
+
# 141s
|
111
|
+
BLANK_NODE_LABEL = /_:((?:[0-9]|#{PN_CHARS_U})(?:(?:#{PN_CHARS}|\.)*#{PN_CHARS})?)/.freeze
|
112
|
+
# 144s
|
113
|
+
LANGTAG = /@([a-zA-Z]+(?:-[a-zA-Z0-9]+)*)/.freeze
|
114
|
+
# 22
|
115
|
+
STRING_LITERAL_QUOTE = /"((?:[^\"\\\n\r]|#{ECHAR}|#{ESCAPE_CHAR})*)"/.freeze
|
116
|
+
|
117
|
+
# @see http://www.w3.org/TR/rdf-testcases/#ntrip_grammar
|
118
|
+
COMMENT = /^#\s*(.*)$/.freeze
|
119
|
+
NODEID = /^#{BLANK_NODE_LABEL}/.freeze
|
120
|
+
URIREF = /^#{IRIREF}/.freeze
|
121
|
+
LITERAL_PLAIN = /^#{STRING_LITERAL_QUOTE}/.freeze
|
122
|
+
LITERAL_WITH_LANGUAGE = /^#{STRING_LITERAL_QUOTE}#{LANGTAG}/.freeze
|
123
|
+
LITERAL_WITH_DATATYPE = /^#{STRING_LITERAL_QUOTE}\^\^#{IRIREF}/.freeze
|
124
|
+
DATATYPE_URI = /^\^\^#{IRIREF}/.freeze
|
125
|
+
LITERAL = Regexp.union(LITERAL_WITH_LANGUAGE, LITERAL_WITH_DATATYPE, LITERAL_PLAIN).freeze
|
126
|
+
SUBJECT = Regexp.union(URIREF, NODEID).freeze
|
127
|
+
PREDICATE = Regexp.union(URIREF).freeze
|
128
|
+
OBJECT = Regexp.union(URIREF, NODEID, LITERAL).freeze
|
129
|
+
END_OF_STATEMENT = /^\s*\.\s*$/.freeze
|
130
|
+
|
54
131
|
##
|
55
132
|
# Reconstructs an RDF value from its serialized N-Triples
|
56
133
|
# representation.
|
@@ -124,6 +201,7 @@ module RDF::NTriples
|
|
124
201
|
# @see http://blog.grayproductions.net/articles/understanding_m17n
|
125
202
|
# @see http://yehudakatz.com/2010/05/17/encodings-unabridged/
|
126
203
|
def self.unescape(string)
|
204
|
+
string = string.to_s
|
127
205
|
string = string.dup.force_encoding(Encoding::ASCII_8BIT) if string.respond_to?(:force_encoding)
|
128
206
|
|
129
207
|
# Decode \t|\n|\r|\"|\\ character escapes:
|
@@ -135,8 +213,10 @@ module RDF::NTriples
|
|
135
213
|
if ESCAPE_SURROGATE1.include?($1.hex) && ESCAPE_SURROGATE2.include?($2.hex)
|
136
214
|
s = [$1, $2].pack('H*H*')
|
137
215
|
s = s.respond_to?(:force_encoding) ?
|
138
|
-
|
139
|
-
|
216
|
+
# for Ruby 1.9+
|
217
|
+
s.force_encoding(Encoding::UTF_16BE).encode!(Encoding::UTF_8) :
|
218
|
+
# for Ruby 1.8.x
|
219
|
+
Iconv.conv('UTF-8', 'UTF-16BE', s)
|
140
220
|
else
|
141
221
|
s = [$1.hex].pack('U*') << '\u' << $2
|
142
222
|
end
|
@@ -159,7 +239,7 @@ module RDF::NTriples
|
|
159
239
|
def read_value
|
160
240
|
begin
|
161
241
|
read_statement
|
162
|
-
rescue RDF::ReaderError
|
242
|
+
rescue RDF::ReaderError
|
163
243
|
read_uriref || read_node || read_literal
|
164
244
|
end
|
165
245
|
end
|
@@ -177,6 +257,9 @@ module RDF::NTriples
|
|
177
257
|
subject = read_uriref || read_node || fail_subject
|
178
258
|
predicate = read_uriref(:intern => true) || fail_predicate
|
179
259
|
object = read_uriref || read_node || read_literal || fail_object
|
260
|
+
if validate? && !read_eos
|
261
|
+
raise RDF::ReaderError, "expected end of statement in line #{lineno}: #{current_line.inspect}"
|
262
|
+
end
|
180
263
|
return [subject, predicate, object]
|
181
264
|
end
|
182
265
|
rescue RDF::ReaderError => e
|
@@ -201,6 +284,7 @@ module RDF::NTriples
|
|
201
284
|
uri_str = self.class.unescape(uri_str)
|
202
285
|
uri = RDF::URI.send(intern? && options[:intern] ? :intern : :new, uri_str)
|
203
286
|
uri.validate! if validate?
|
287
|
+
raise RDF::ReaderError, "uri not absolute" if validate? && !uri.absolute?
|
204
288
|
uri.canonicalize! if canonicalize?
|
205
289
|
uri
|
206
290
|
end
|
@@ -210,7 +294,7 @@ module RDF::NTriples
|
|
210
294
|
# @return [RDF::Node]
|
211
295
|
# @see http://www.w3.org/TR/rdf-testcases/#ntrip_grammar (nodeID)
|
212
296
|
def read_node
|
213
|
-
|
297
|
+
if node_id = match(NODEID)
|
214
298
|
@nodes ||= {}
|
215
299
|
@nodes[node_id] ||= RDF::Node.new(node_id)
|
216
300
|
end
|
@@ -223,7 +307,7 @@ module RDF::NTriples
|
|
223
307
|
if literal_str = match(LITERAL_PLAIN)
|
224
308
|
literal_str = self.class.unescape(literal_str)
|
225
309
|
literal = case
|
226
|
-
when language = match(
|
310
|
+
when language = match(LANGTAG)
|
227
311
|
RDF::Literal.new(literal_str, :language => language)
|
228
312
|
when datatype = match(/^(\^\^)/) # FIXME
|
229
313
|
RDF::Literal.new(literal_str, :datatype => read_uriref || fail_object)
|
@@ -235,5 +319,12 @@ module RDF::NTriples
|
|
235
319
|
literal
|
236
320
|
end
|
237
321
|
end
|
322
|
+
|
323
|
+
##
|
324
|
+
# @return [Boolean]
|
325
|
+
# @see http://www.w3.org/TR/rdf-testcases/#ntrip_grammar (triple)
|
326
|
+
def read_eos
|
327
|
+
match(END_OF_STATEMENT)
|
328
|
+
end
|
238
329
|
end # Reader
|
239
330
|
end # RDF::NTriples
|
data/lib/rdf/ntriples/writer.rb
CHANGED
@@ -209,7 +209,7 @@ module RDF::NTriples
|
|
209
209
|
# @param [Hash{Symbol => Object}] options
|
210
210
|
# @return [String]
|
211
211
|
def format_node(node, options = {})
|
212
|
-
|
212
|
+
node.to_base
|
213
213
|
end
|
214
214
|
|
215
215
|
##
|
@@ -219,7 +219,7 @@ module RDF::NTriples
|
|
219
219
|
# @param [Hash{Symbol => Object}] options
|
220
220
|
# @return [String]
|
221
221
|
def format_uri(uri, options = {})
|
222
|
-
|
222
|
+
uri.to_base
|
223
223
|
end
|
224
224
|
|
225
225
|
##
|
@@ -231,6 +231,7 @@ module RDF::NTriples
|
|
231
231
|
def format_literal(literal, options = {})
|
232
232
|
case literal
|
233
233
|
when RDF::Literal
|
234
|
+
# Note, escaping here is more robust than in Term
|
234
235
|
text = quoted(escaped(literal.value))
|
235
236
|
text << "@#{literal.language}" if literal.has_language?
|
236
237
|
text << "^^<#{uri_for(literal.datatype)}>" if literal.has_datatype?
|
data/lib/rdf/query.rb
CHANGED
@@ -129,10 +129,12 @@ module RDF
|
|
129
129
|
# @option options [RDF::Resource, RDF::Query::Variable, false] :context (nil)
|
130
130
|
# Default context for matching against queryable.
|
131
131
|
# Named queries either match against a specifically named
|
132
|
-
#
|
133
|
-
# Names that are against unbound variables match either
|
134
|
-
# or named
|
132
|
+
# graphs if the name is an {RDF::Resource} or bound {RDF::Query::Variable}.
|
133
|
+
# Names that are against unbound variables match either default
|
134
|
+
# or named graphs.
|
135
135
|
# The name of `false` will only match against the default context.
|
136
|
+
# @option options [RDF::Resource, RDF::Query::Variable, false] :name (nil)
|
137
|
+
# Alias for `:context`.
|
136
138
|
# @yield [query]
|
137
139
|
# @yieldparam [RDF::Query] query
|
138
140
|
# @yieldreturn [void] ignored
|
@@ -146,9 +148,11 @@ module RDF
|
|
146
148
|
# @option options [RDF::Resource, RDF::Query::Variable, false] :context (nil)
|
147
149
|
# Default context for matching against queryable.
|
148
150
|
# Named queries either match against a specifically named
|
149
|
-
#
|
150
|
-
# Names that are against unbound variables match either
|
151
|
-
# or named
|
151
|
+
# graphs if the name is an {RDF::Resource} or bound {RDF::Query::Variable}.
|
152
|
+
# Names that are against unbound variables match either default
|
153
|
+
# or named graphs.
|
154
|
+
# @option options [RDF::Resource, RDF::Query::Variable, false] :name (nil)
|
155
|
+
# Alias for `:context`.
|
152
156
|
# @yield [query]
|
153
157
|
# @yieldparam [RDF::Query] query
|
154
158
|
# @yieldreturn [void] ignored
|
@@ -157,7 +161,9 @@ module RDF
|
|
157
161
|
patterns << @options if patterns.empty?
|
158
162
|
@variables = {}
|
159
163
|
@solutions = @options.delete(:solutions) || Solutions.new
|
160
|
-
context = @options.
|
164
|
+
context = @options.fetch(:context, @options.fetch(:name, nil))
|
165
|
+
@options.delete(:context)
|
166
|
+
@options.delete(:name)
|
161
167
|
|
162
168
|
@patterns = case patterns.first
|
163
169
|
when Hash then compile_hash_patterns(HashPatternNormalizer.normalize!(patterns.first.dup, @options))
|
@@ -246,6 +252,8 @@ module RDF
|
|
246
252
|
# @option options [RDF::Resource, RDF::Query::Variable, false] context (nil)
|
247
253
|
# Specific context for matching against queryable;
|
248
254
|
# overrides default context defined on query.
|
255
|
+
# @option options [RDF::Resource, RDF::Query::Variable, false] name (nil)
|
256
|
+
# Alias for `:context`.
|
249
257
|
# @option options [Hash{Symbol => RDF::Term}] solutions
|
250
258
|
# optional initial solutions for chained queries
|
251
259
|
# @return [RDF::Query::Solutions]
|
@@ -264,7 +272,7 @@ module RDF
|
|
264
272
|
@solutions = options[:solutions] || (Solutions.new << RDF::Query::Solution.new({}))
|
265
273
|
|
266
274
|
patterns = @patterns
|
267
|
-
context = options.fetch(:context, self.context)
|
275
|
+
context = options.fetch(:context, options.fetch(:name, self.context))
|
268
276
|
|
269
277
|
# Add context to pattern, if necessary
|
270
278
|
unless context.nil?
|
@@ -349,27 +357,34 @@ module RDF
|
|
349
357
|
Query.new(self.patterns + other.patterns)
|
350
358
|
end
|
351
359
|
|
352
|
-
# Is this
|
360
|
+
# Is this query scoped to a named graph?
|
353
361
|
# @return [Boolean]
|
354
362
|
def named?
|
355
363
|
!!options[:context]
|
356
364
|
end
|
357
365
|
|
358
|
-
# Is this
|
366
|
+
# Is this query scoped to the default graph?
|
367
|
+
# @return [Boolean]
|
368
|
+
def default?
|
369
|
+
options[:context] == false
|
370
|
+
end
|
371
|
+
|
372
|
+
# Is this query unscoped? This indicates that it can return results from
|
373
|
+
# either a named graph or the default graph.
|
359
374
|
# @return [Boolean]
|
360
375
|
def unnamed?
|
361
|
-
|
376
|
+
options[:context].nil?
|
362
377
|
end
|
363
378
|
|
364
|
-
#
|
365
|
-
# @param [RDF::
|
366
|
-
# @return [RDF::
|
379
|
+
# Scope the query to named graphs matching value
|
380
|
+
# @param [RDF::IRI, RDF::Query::Variable] value
|
381
|
+
# @return [RDF::IRI, RDF::Query::Variable]
|
367
382
|
def context=(value)
|
368
383
|
options[:context] = value
|
369
384
|
end
|
370
385
|
|
371
|
-
#
|
372
|
-
# @return [RDF::
|
386
|
+
# Scope of this query, if any
|
387
|
+
# @return [RDF::IRI, RDF::Query::Variable]
|
373
388
|
def context
|
374
389
|
options[:context]
|
375
390
|
end
|
data/lib/rdf/query/solution.rb
CHANGED
@@ -22,9 +22,11 @@ class RDF::Query
|
|
22
22
|
#
|
23
23
|
class Solution
|
24
24
|
# Undefine all superfluous instance methods:
|
25
|
-
undef_method(*
|
26
|
-
|
27
|
-
|
25
|
+
undef_method(*instance_methods.
|
26
|
+
map(&:to_s).
|
27
|
+
select {|m| m =~ /^\w+$/}.
|
28
|
+
reject {|m| %w(object_id dup instance_eval inspect to_s class).include?(m) || m[0,2] == '__'}.
|
29
|
+
map(&:to_sym))
|
28
30
|
|
29
31
|
include Enumerable
|
30
32
|
|
data/lib/rdf/util/file.rb
CHANGED
@@ -29,17 +29,17 @@ module RDF; module Util
|
|
29
29
|
# to override this implementation to provide more control over HTTP
|
30
30
|
# headers and redirect following.
|
31
31
|
# @option options [Array, String] :headers
|
32
|
-
# HTTP Request headers, passed to Kernel.open.
|
32
|
+
# HTTP Request headers, passed to Kernel.open. (Ruby >= 1.9 only)
|
33
33
|
# @return [IO] File stream
|
34
34
|
# @yield [IO] File stream
|
35
35
|
# @note HTTP headers not passed to `Kernel.open` for Ruby versions < 1.9.
|
36
36
|
def self.open_file(filename_or_url, options = {}, &block)
|
37
37
|
filename_or_url = $1 if filename_or_url.to_s.match(/^file:(.*)$/)
|
38
|
-
options[:headers] ||= {}
|
39
|
-
options[:headers]['Accept'] ||= RDF::Reader.map {|r| r.format.content_type}.uniq.join(", ")
|
40
38
|
if RUBY_VERSION < "1.9"
|
41
39
|
Kernel.open(filename_or_url.to_s, &block)
|
42
40
|
else
|
41
|
+
options[:headers] ||= {}
|
42
|
+
options[:headers]['Accept'] ||= (RDF::Format.reader_types + %w(*/*;q=0.1)).join(", ")
|
43
43
|
Kernel.open(filename_or_url.to_s, options[:headers], &block)
|
44
44
|
end
|
45
45
|
end
|
data/lib/rdf/vocab.rb
CHANGED
@@ -129,7 +129,11 @@ module RDF
|
|
129
129
|
end
|
130
130
|
|
131
131
|
# Undefine all superfluous instance methods:
|
132
|
-
undef_method(*
|
132
|
+
undef_method(*instance_methods.
|
133
|
+
map(&:to_s).
|
134
|
+
select {|m| m =~ /^\w+$/}.
|
135
|
+
reject {|m| %w(object_id dup instance_eval inspect to_s class).include?(m) || m[0,2] == '__'}.
|
136
|
+
map(&:to_sym))
|
133
137
|
|
134
138
|
##
|
135
139
|
# @param [RDF::URI, String, #to_s] uri
|
data/lib/rdf/writer.rb
CHANGED
@@ -466,8 +466,13 @@ module RDF
|
|
466
466
|
# @param [String] string
|
467
467
|
# @return [String]
|
468
468
|
def escaped(string)
|
469
|
-
string.gsub('\\', '\\\\').
|
470
|
-
|
469
|
+
string.gsub('\\', '\\\\').
|
470
|
+
gsub("\b", '\\b').
|
471
|
+
gsub("\f", '\\f').
|
472
|
+
gsub("\t", '\\t').
|
473
|
+
gsub("\n", '\\n').
|
474
|
+
gsub("\r", '\\r').
|
475
|
+
gsub('"', '\\"')
|
471
476
|
end
|
472
477
|
|
473
478
|
##
|
metadata
CHANGED
@@ -1,8 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rdf
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
5
|
-
prerelease:
|
4
|
+
version: 1.0.4
|
6
5
|
platform: ruby
|
7
6
|
authors:
|
8
7
|
- Arto Bendiken
|
@@ -11,12 +10,11 @@ authors:
|
|
11
10
|
autorequire:
|
12
11
|
bindir: bin
|
13
12
|
cert_chain: []
|
14
|
-
date: 2013-
|
13
|
+
date: 2013-03-23 00:00:00.000000000 Z
|
15
14
|
dependencies:
|
16
15
|
- !ruby/object:Gem::Dependency
|
17
16
|
name: addressable
|
18
17
|
requirement: !ruby/object:Gem::Requirement
|
19
|
-
none: false
|
20
18
|
requirements:
|
21
19
|
- - ! '>='
|
22
20
|
- !ruby/object:Gem::Version
|
@@ -24,7 +22,6 @@ dependencies:
|
|
24
22
|
type: :runtime
|
25
23
|
prerelease: false
|
26
24
|
version_requirements: !ruby/object:Gem::Requirement
|
27
|
-
none: false
|
28
25
|
requirements:
|
29
26
|
- - ! '>='
|
30
27
|
- !ruby/object:Gem::Version
|
@@ -32,7 +29,6 @@ dependencies:
|
|
32
29
|
- !ruby/object:Gem::Dependency
|
33
30
|
name: rdf-spec
|
34
31
|
requirement: !ruby/object:Gem::Requirement
|
35
|
-
none: false
|
36
32
|
requirements:
|
37
33
|
- - ~>
|
38
34
|
- !ruby/object:Gem::Version
|
@@ -40,7 +36,6 @@ dependencies:
|
|
40
36
|
type: :development
|
41
37
|
prerelease: false
|
42
38
|
version_requirements: !ruby/object:Gem::Requirement
|
43
|
-
none: false
|
44
39
|
requirements:
|
45
40
|
- - ~>
|
46
41
|
- !ruby/object:Gem::Version
|
@@ -48,7 +43,6 @@ dependencies:
|
|
48
43
|
- !ruby/object:Gem::Dependency
|
49
44
|
name: rspec
|
50
45
|
requirement: !ruby/object:Gem::Requirement
|
51
|
-
none: false
|
52
46
|
requirements:
|
53
47
|
- - ! '>='
|
54
48
|
- !ruby/object:Gem::Version
|
@@ -56,7 +50,6 @@ dependencies:
|
|
56
50
|
type: :development
|
57
51
|
prerelease: false
|
58
52
|
version_requirements: !ruby/object:Gem::Requirement
|
59
|
-
none: false
|
60
53
|
requirements:
|
61
54
|
- - ! '>='
|
62
55
|
- !ruby/object:Gem::Version
|
@@ -64,7 +57,6 @@ dependencies:
|
|
64
57
|
- !ruby/object:Gem::Dependency
|
65
58
|
name: yard
|
66
59
|
requirement: !ruby/object:Gem::Requirement
|
67
|
-
none: false
|
68
60
|
requirements:
|
69
61
|
- - ! '>='
|
70
62
|
- !ruby/object:Gem::Version
|
@@ -72,7 +64,6 @@ dependencies:
|
|
72
64
|
type: :development
|
73
65
|
prerelease: false
|
74
66
|
version_requirements: !ruby/object:Gem::Requirement
|
75
|
-
none: false
|
76
67
|
requirements:
|
77
68
|
- - ! '>='
|
78
69
|
- !ruby/object:Gem::Version
|
@@ -170,30 +161,26 @@ files:
|
|
170
161
|
homepage: http://ruby-rdf.github.com/
|
171
162
|
licenses:
|
172
163
|
- Public Domain
|
164
|
+
metadata: {}
|
173
165
|
post_install_message:
|
174
166
|
rdoc_options: []
|
175
167
|
require_paths:
|
176
168
|
- lib
|
177
169
|
required_ruby_version: !ruby/object:Gem::Requirement
|
178
|
-
none: false
|
179
170
|
requirements:
|
180
171
|
- - ! '>='
|
181
172
|
- !ruby/object:Gem::Version
|
182
173
|
version: 1.8.1
|
183
174
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
184
|
-
none: false
|
185
175
|
requirements:
|
186
176
|
- - ! '>='
|
187
177
|
- !ruby/object:Gem::Version
|
188
178
|
version: '0'
|
189
|
-
segments:
|
190
|
-
- 0
|
191
|
-
hash: -2150851322746438702
|
192
179
|
requirements: []
|
193
180
|
rubyforge_project: rdf
|
194
|
-
rubygems_version:
|
181
|
+
rubygems_version: 2.0.3
|
195
182
|
signing_key:
|
196
|
-
specification_version:
|
183
|
+
specification_version: 4
|
197
184
|
summary: A Ruby library for working with Resource Description Framework (RDF) data.
|
198
185
|
test_files: []
|
199
186
|
has_rdoc: false
|