json-ld 3.1.2 → 3.1.7
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 +4 -4
- data/README.md +124 -48
- data/VERSION +1 -1
- data/bin/jsonld +27 -30
- data/lib/json/ld.rb +6 -2
- data/lib/json/ld/api.rb +33 -24
- data/lib/json/ld/compact.rb +65 -37
- data/lib/json/ld/conneg.rb +1 -1
- data/lib/json/ld/context.rb +612 -539
- data/lib/json/ld/expand.rb +158 -77
- data/lib/json/ld/format.rb +20 -7
- data/lib/json/ld/from_rdf.rb +40 -17
- data/lib/json/ld/reader.rb +20 -11
- data/lib/json/ld/streaming_reader.rb +578 -0
- data/lib/json/ld/to_rdf.rb +9 -5
- data/lib/json/ld/writer.rb +10 -3
- data/spec/compact_spec.rb +207 -2
- data/spec/context_spec.rb +13 -60
- data/spec/expand_spec.rb +248 -0
- data/spec/from_rdf_spec.rb +181 -0
- data/spec/matchers.rb +1 -1
- data/spec/reader_spec.rb +33 -34
- data/spec/streaming_reader_spec.rb +237 -0
- data/spec/suite_helper.rb +14 -8
- data/spec/suite_to_rdf_spec.rb +1 -0
- data/spec/to_rdf_spec.rb +206 -0
- data/spec/writer_spec.rb +193 -0
- metadata +9 -6
@@ -0,0 +1,237 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
require_relative 'spec_helper'
|
3
|
+
require 'rdf/spec/reader'
|
4
|
+
|
5
|
+
describe JSON::LD::Reader do
|
6
|
+
let!(:doap) {File.expand_path("../../etc/doap.jsonld", __FILE__)}
|
7
|
+
let!(:doap_nt) {File.expand_path("../../etc/doap.nt", __FILE__)}
|
8
|
+
let!(:doap_count) {File.open(doap_nt).each_line.to_a.length}
|
9
|
+
let(:logger) {RDF::Spec.logger}
|
10
|
+
|
11
|
+
after(:each) {|example| puts logger.to_s if example.exception}
|
12
|
+
|
13
|
+
it_behaves_like 'an RDF::Reader' do
|
14
|
+
let(:reader_input) {File.read(doap)}
|
15
|
+
let(:reader) {JSON::LD::Reader.new(reader_input, stream: true)}
|
16
|
+
let(:reader_count) {doap_count}
|
17
|
+
end
|
18
|
+
|
19
|
+
context "when validating", pending: ("JRuby support for jsonlint" if RUBY_ENGINE == "jruby") do
|
20
|
+
it "detects invalid JSON" do
|
21
|
+
expect do |b|
|
22
|
+
described_class.new(StringIO.new(%({"a": "b", "a": "c"})), validate: true, logger: false).each_statement(&b)
|
23
|
+
end.to raise_error(RDF::ReaderError)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
context :interface do
|
28
|
+
{
|
29
|
+
plain: %q({
|
30
|
+
"@context": {"foaf": "http://xmlns.com/foaf/0.1/"},
|
31
|
+
"@type": "foaf:Person",
|
32
|
+
"@id": "_:bnode1",
|
33
|
+
"foaf:homepage": "http://example.com/bob/",
|
34
|
+
"foaf:name": "Bob"
|
35
|
+
}),
|
36
|
+
leading_comment: %q(
|
37
|
+
// A comment before content
|
38
|
+
{
|
39
|
+
"@context": {"foaf": "http://xmlns.com/foaf/0.1/"},
|
40
|
+
"@type": "foaf:Person",
|
41
|
+
"@id": "_:bnode1",
|
42
|
+
"foaf:homepage": "http://example.com/bob/",
|
43
|
+
"foaf:name": "Bob"
|
44
|
+
}),
|
45
|
+
script: %q(<script type="application/ld+json">
|
46
|
+
{
|
47
|
+
"@context": {"foaf": "http://xmlns.com/foaf/0.1/"},
|
48
|
+
"@type": "foaf:Person",
|
49
|
+
"@id": "_:bnode1",
|
50
|
+
"foaf:homepage": "http://example.com/bob/",
|
51
|
+
"foaf:name": "Bob"
|
52
|
+
}
|
53
|
+
</script>),
|
54
|
+
script_comments: %q(<script type="application/ld+json">
|
55
|
+
// A comment before content
|
56
|
+
{
|
57
|
+
"@context": {"foaf": "http://xmlns.com/foaf/0.1/"},
|
58
|
+
"@type": "foaf:Person",
|
59
|
+
"@id": "_:bnode1",
|
60
|
+
"foaf:homepage": "http://example.com/bob/",
|
61
|
+
"foaf:name": "Bob"
|
62
|
+
}
|
63
|
+
</script>),
|
64
|
+
}.each do |variant, src|
|
65
|
+
context variant do
|
66
|
+
subject {src}
|
67
|
+
|
68
|
+
describe "#initialize" do
|
69
|
+
it "yields reader given string" do
|
70
|
+
inner = double("inner")
|
71
|
+
expect(inner).to receive(:called).with(JSON::LD::Reader)
|
72
|
+
JSON::LD::Reader.new(subject, stream: true) do |reader|
|
73
|
+
inner.called(reader.class)
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
it "yields reader given IO" do
|
78
|
+
inner = double("inner")
|
79
|
+
expect(inner).to receive(:called).with(JSON::LD::Reader)
|
80
|
+
JSON::LD::Reader.new(StringIO.new(subject), stream: true) do |reader|
|
81
|
+
inner.called(reader.class)
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
it "returns reader" do
|
86
|
+
expect(JSON::LD::Reader.new(subject, stream: true)).to be_a(JSON::LD::Reader)
|
87
|
+
end
|
88
|
+
end
|
89
|
+
|
90
|
+
describe "#each_statement" do
|
91
|
+
it "yields statements" do
|
92
|
+
inner = double("inner")
|
93
|
+
expect(inner).to receive(:called).with(RDF::Statement).exactly(3)
|
94
|
+
JSON::LD::Reader.new(subject, stream: true).each_statement do |statement|
|
95
|
+
inner.called(statement.class)
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
describe "#each_triple" do
|
101
|
+
it "yields statements" do
|
102
|
+
inner = double("inner")
|
103
|
+
expect(inner).to receive(:called).exactly(3)
|
104
|
+
JSON::LD::Reader.new(subject, stream: true).each_triple do |subject, predicate, object|
|
105
|
+
inner.called(subject.class, predicate.class, object.class)
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
111
|
+
end
|
112
|
+
|
113
|
+
context "Selected toRdf tests" do
|
114
|
+
{
|
115
|
+
"e004": {
|
116
|
+
input: %({
|
117
|
+
"@context": {
|
118
|
+
"mylist1": {"@id": "http://example.com/mylist1", "@container": "@list"}
|
119
|
+
},
|
120
|
+
"@id": "http://example.org/id",
|
121
|
+
"mylist1": { "@list": [ ] },
|
122
|
+
"http://example.org/list1": { "@list": [ null ] },
|
123
|
+
"http://example.org/list2": { "@list": [ {"@value": null} ] }
|
124
|
+
}),
|
125
|
+
expect: %(
|
126
|
+
<http://example.org/id> <http://example.com/mylist1> <http://www.w3.org/1999/02/22-rdf-syntax-ns#nil> .
|
127
|
+
<http://example.org/id> <http://example.org/list1> <http://www.w3.org/1999/02/22-rdf-syntax-ns#nil> .
|
128
|
+
<http://example.org/id> <http://example.org/list2> <http://www.w3.org/1999/02/22-rdf-syntax-ns#nil> .
|
129
|
+
)
|
130
|
+
},
|
131
|
+
"e015": {
|
132
|
+
input: %({
|
133
|
+
"@context": {
|
134
|
+
"myset2": {"@id": "http://example.com/myset2", "@container": "@set" }
|
135
|
+
},
|
136
|
+
"@id": "http://example.org/id",
|
137
|
+
"myset2": [ [], { "@set": [ null ] }, [ null ] ]
|
138
|
+
}),
|
139
|
+
expect: %(
|
140
|
+
)
|
141
|
+
},
|
142
|
+
"in06": {
|
143
|
+
input: %({
|
144
|
+
"@context": {
|
145
|
+
"@version": 1.1,
|
146
|
+
"@vocab": "http://example.org/vocab#",
|
147
|
+
"@base": "http://example.org/base/",
|
148
|
+
"id": "@id",
|
149
|
+
"type": "@type",
|
150
|
+
"data": "@nest",
|
151
|
+
"links": "@nest",
|
152
|
+
"relationships": "@nest",
|
153
|
+
"self": {"@type": "@id"},
|
154
|
+
"related": {"@type": "@id"}
|
155
|
+
},
|
156
|
+
"data": [{
|
157
|
+
"type": "articles",
|
158
|
+
"id": "1",
|
159
|
+
"author": {
|
160
|
+
"data": { "type": "people", "id": "9" }
|
161
|
+
}
|
162
|
+
}]
|
163
|
+
}),
|
164
|
+
expect: %(
|
165
|
+
<http://example.org/base/1> <http://example.org/vocab#author> <http://example.org/base/9> .
|
166
|
+
<http://example.org/base/1> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://example.org/vocab#articles> .
|
167
|
+
<http://example.org/base/9> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <http://example.org/vocab#people> .
|
168
|
+
),
|
169
|
+
pending: "@nest defining @id"
|
170
|
+
}
|
171
|
+
}.each do |name, params|
|
172
|
+
it name do
|
173
|
+
run_to_rdf params
|
174
|
+
end
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
describe "test suite" do
|
179
|
+
require_relative 'suite_helper'
|
180
|
+
m = Fixtures::SuiteTest::Manifest.open("#{Fixtures::SuiteTest::STREAM_SUITE}stream-toRdf-manifest.jsonld")
|
181
|
+
describe m.name do
|
182
|
+
m.entries.each do |t|
|
183
|
+
specify "#{t.property('@id')}: #{t.name}#{' (negative test)' unless t.positiveTest?}" do
|
184
|
+
pending "Generalized RDF" if t.options[:produceGeneralizedRdf]
|
185
|
+
pending "@nest defining @id" if %w(#tin06).include?(t.property('@id'))
|
186
|
+
pending "double @reverse" if %w(#te043).include?(t.property('@id'))
|
187
|
+
pending "graph map containing named graph" if %w(#te084 #te087 #te098 #te101 #te105 #te106).include?(t.property('@id'))
|
188
|
+
pending "named graphs" if %w(#t0029 #te021).include?(t.property('@id'))
|
189
|
+
|
190
|
+
if %w(#t0118).include?(t.property('@id'))
|
191
|
+
expect {t.run self}.to write(/Statement .* is invalid/).to(:error)
|
192
|
+
elsif %w(#twf07).include?(t.property('@id'))
|
193
|
+
expect {t.run self}.to write(/skipping graph statement within invalid graph name/).to(:error)
|
194
|
+
elsif %w(#te075).include?(t.property('@id'))
|
195
|
+
expect {t.run self}.to write(/is invalid/).to(:error)
|
196
|
+
elsif %w(#te005 #tpr34 #tpr35 #tpr36 #tpr37 #tpr38 #tpr39 #te119 #te120).include?(t.property('@id'))
|
197
|
+
expect {t.run self}.to write("beginning with '@' are reserved for future use").to(:error)
|
198
|
+
elsif %w(#te068).include?(t.property('@id'))
|
199
|
+
expect {t.run self}.to write("[DEPRECATION]").to(:error)
|
200
|
+
elsif %w(#twf05).include?(t.property('@id'))
|
201
|
+
expect {t.run self}.to write("@language must be valid BCP47").to(:error)
|
202
|
+
else
|
203
|
+
expect {t.run self}.not_to write.to(:error)
|
204
|
+
end
|
205
|
+
end
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end unless ENV['CI']
|
209
|
+
|
210
|
+
def run_to_rdf(params)
|
211
|
+
input = params[:input]
|
212
|
+
logger.info("input: #{input}")
|
213
|
+
output = RDF::Repository.new
|
214
|
+
if params[:expect]
|
215
|
+
RDF::NQuads::Reader.new(params[:expect], validate: false) {|r| output << r}
|
216
|
+
logger.info("expect (quads): #{output.dump(:nquads, validate: false)}")
|
217
|
+
else
|
218
|
+
logger.info("expect: #{Regexp.new params[:exception]}")
|
219
|
+
end
|
220
|
+
|
221
|
+
graph = params[:graph] || RDF::Repository.new
|
222
|
+
pending params.fetch(:pending, "test implementation") if !input || params[:pending]
|
223
|
+
if params[:exception]
|
224
|
+
expect do |b|
|
225
|
+
JSON::LD::Reader.new(input, stream: true, validate: true, logger: false, **params).each_statement(&b)
|
226
|
+
end.to raise_error {|er| expect(er.message).to include params[:exception]}
|
227
|
+
else
|
228
|
+
if params[:write]
|
229
|
+
expect{JSON::LD::Reader.new(input, stream: true, logger: logger, **params) {|st| graph << st}}.to write(params[:write]).to(:error)
|
230
|
+
else
|
231
|
+
expect{JSON::LD::Reader.new(input, stream: true, logger: logger, **params) {|st| graph << st}}.not_to write.to(:error)
|
232
|
+
end
|
233
|
+
logger.info("results (quads): #{graph.dump(:nquads, validate: false)}")
|
234
|
+
expect(graph).to be_equivalent_graph(output, logger: logger, inputDocument: input)
|
235
|
+
end
|
236
|
+
end
|
237
|
+
end
|
data/spec/suite_helper.rb
CHANGED
@@ -6,6 +6,7 @@ module RDF::Util
|
|
6
6
|
LOCAL_PATHS = {
|
7
7
|
"https://w3c.github.io/json-ld-api/tests/" => ::File.expand_path("../json-ld-api/tests", __FILE__) + '/',
|
8
8
|
"https://w3c.github.io/json-ld-framing/tests/" => ::File.expand_path("../json-ld-framing/tests", __FILE__) + '/',
|
9
|
+
"https://w3c.github.io/json-ld-streaming/tests/" => ::File.expand_path("../json-ld-streaming/tests", __FILE__) + '/',
|
9
10
|
"file:" => ""
|
10
11
|
}
|
11
12
|
|
@@ -74,6 +75,7 @@ module Fixtures
|
|
74
75
|
module SuiteTest
|
75
76
|
SUITE = RDF::URI("https://w3c.github.io/json-ld-api/tests/")
|
76
77
|
FRAME_SUITE = RDF::URI("https://w3c.github.io/json-ld-framing/tests/")
|
78
|
+
STREAM_SUITE = RDF::URI("https://w3c.github.io/json-ld-streaming/tests/")
|
77
79
|
|
78
80
|
class Manifest < JSON::LD::Resource
|
79
81
|
attr_accessor :manifest_url
|
@@ -228,14 +230,14 @@ module Fixtures
|
|
228
230
|
JSON::LD::API.fromRdf(repo, logger: logger, **options)
|
229
231
|
when "jld:ToRDFTest"
|
230
232
|
repo = RDF::Repository.new
|
231
|
-
|
232
|
-
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
233
|
+
if manifest_url.to_s.include?('stream')
|
234
|
+
JSON::LD::Reader.open(input_loc, stream: true, logger: logger, **options) do |statement|
|
235
|
+
repo << statement
|
236
|
+
end
|
237
|
+
else
|
238
|
+
JSON::LD::API.toRdf(input_loc, logger: logger, **options) do |statement|
|
239
|
+
repo << statement
|
237
240
|
end
|
238
|
-
repo << statement
|
239
241
|
end
|
240
242
|
logger.info "nq: #{repo.map(&:to_nquads)}"
|
241
243
|
repo
|
@@ -320,7 +322,11 @@ module Fixtures
|
|
320
322
|
raise "Expected status #{t.property('expectErrorCode')}, not #{last_response.status}"
|
321
323
|
end
|
322
324
|
when "jld:ToRDFTest"
|
323
|
-
|
325
|
+
if t.manifest_url.to_s.include?('stream')
|
326
|
+
JSON::LD::Reader.open(t.input_loc, stream: true, logger: logger, **options).each_statement {}
|
327
|
+
else
|
328
|
+
JSON::LD::API.toRdf(t.input_loc, logger: logger, **options) {}
|
329
|
+
end
|
324
330
|
else
|
325
331
|
success("Unknown test type: #{testType}")
|
326
332
|
end
|
data/spec/suite_to_rdf_spec.rb
CHANGED
@@ -9,6 +9,7 @@ describe JSON::LD do
|
|
9
9
|
m.entries.each do |t|
|
10
10
|
specify "#{t.property('@id')}: #{t.name}#{' (negative test)' unless t.positiveTest?}" do
|
11
11
|
pending "Generalized RDF" if t.options[:produceGeneralizedRdf]
|
12
|
+
pending "RDF*" if t.property('@id') == '#te122'
|
12
13
|
if %w(#t0118).include?(t.property('@id'))
|
13
14
|
expect {t.run self}.to write(/Statement .* is invalid/).to(:error)
|
14
15
|
elsif %w(#te075).include?(t.property('@id'))
|
data/spec/to_rdf_spec.rb
CHANGED
@@ -1175,6 +1175,212 @@ describe JSON::LD::API do
|
|
1175
1175
|
end
|
1176
1176
|
end
|
1177
1177
|
|
1178
|
+
context "JSON-LD*" do
|
1179
|
+
{
|
1180
|
+
"node with embedded subject without rdfstar option": {
|
1181
|
+
input: %({
|
1182
|
+
"@id": {
|
1183
|
+
"@id": "ex:rei",
|
1184
|
+
"ex:prop": "value"
|
1185
|
+
},
|
1186
|
+
"ex:prop": "value2"
|
1187
|
+
}),
|
1188
|
+
exception: JSON::LD::JsonLdError::InvalidIdValue
|
1189
|
+
},
|
1190
|
+
}.each do |title, params|
|
1191
|
+
it(title) {run_to_rdf params}
|
1192
|
+
end
|
1193
|
+
|
1194
|
+
{
|
1195
|
+
"node with embedded subject having no @id": {
|
1196
|
+
input: %({
|
1197
|
+
"@id": {
|
1198
|
+
"ex:prop": "value"
|
1199
|
+
},
|
1200
|
+
"ex:prop": "value2"
|
1201
|
+
}),
|
1202
|
+
expected: %(
|
1203
|
+
<<_:b0 <ex:prop> "value">> <ex:prop> "value2" .
|
1204
|
+
),
|
1205
|
+
},
|
1206
|
+
"node with embedded subject having IRI @id": {
|
1207
|
+
input: %({
|
1208
|
+
"@id": {
|
1209
|
+
"@id": "ex:rei",
|
1210
|
+
"ex:prop": "value"
|
1211
|
+
},
|
1212
|
+
"ex:prop": "value2"
|
1213
|
+
}),
|
1214
|
+
expected: %(
|
1215
|
+
<<<ex:rei> <ex:prop> "value">> <ex:prop> "value2" .
|
1216
|
+
),
|
1217
|
+
},
|
1218
|
+
"node with embedded subject having BNode @id": {
|
1219
|
+
input: %({
|
1220
|
+
"@id": {
|
1221
|
+
"@id": "_:rei",
|
1222
|
+
"ex:prop": "value"
|
1223
|
+
},
|
1224
|
+
"ex:prop": "value2"
|
1225
|
+
}),
|
1226
|
+
expected: %(
|
1227
|
+
<<_:b0 <ex:prop> "value">> <ex:prop> "value2" .
|
1228
|
+
),
|
1229
|
+
},
|
1230
|
+
"node with embedded subject having a type": {
|
1231
|
+
input: %({
|
1232
|
+
"@id": {
|
1233
|
+
"@id": "ex:rei",
|
1234
|
+
"@type": "ex:Type"
|
1235
|
+
},
|
1236
|
+
"ex:prop": "value2"
|
1237
|
+
}),
|
1238
|
+
expected: %(
|
1239
|
+
<<<ex:rei> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <ex:Type>>> <ex:prop> "value2" .
|
1240
|
+
),
|
1241
|
+
},
|
1242
|
+
"node with embedded subject having an IRI value": {
|
1243
|
+
input: %({
|
1244
|
+
"@id": {
|
1245
|
+
"@id": "ex:rei",
|
1246
|
+
"ex:prop": {"@id": "ex:value"}
|
1247
|
+
},
|
1248
|
+
"ex:prop": "value2"
|
1249
|
+
}),
|
1250
|
+
expected: %(
|
1251
|
+
<<<ex:rei> <ex:prop> <ex:value>>> <ex:prop> "value2" .
|
1252
|
+
),
|
1253
|
+
},
|
1254
|
+
"node with embedded subject having an BNode value": {
|
1255
|
+
input: %({
|
1256
|
+
"@id": {
|
1257
|
+
"@id": "ex:rei",
|
1258
|
+
"ex:prop": {"@id": "_:value"}
|
1259
|
+
},
|
1260
|
+
"ex:prop": "value2"
|
1261
|
+
}),
|
1262
|
+
expected: %(
|
1263
|
+
<<<ex:rei> <ex:prop> _:b0>> <ex:prop> "value2" .
|
1264
|
+
),
|
1265
|
+
},
|
1266
|
+
"node with recursive embedded subject": {
|
1267
|
+
input: %({
|
1268
|
+
"@id": {
|
1269
|
+
"@id": {
|
1270
|
+
"@id": "ex:rei",
|
1271
|
+
"ex:prop": "value3"
|
1272
|
+
},
|
1273
|
+
"ex:prop": "value"
|
1274
|
+
},
|
1275
|
+
"ex:prop": "value2"
|
1276
|
+
}),
|
1277
|
+
expected: %(
|
1278
|
+
<<<<<ex:rei> <ex:prop> "value3">> <ex:prop> "value">> <ex:prop> "value2" .
|
1279
|
+
),
|
1280
|
+
},
|
1281
|
+
"illegal node with subject having no property": {
|
1282
|
+
input: %({
|
1283
|
+
"@id": {
|
1284
|
+
"@id": "ex:rei"
|
1285
|
+
},
|
1286
|
+
"ex:prop": "value3"
|
1287
|
+
}),
|
1288
|
+
exception: JSON::LD::JsonLdError::InvalidEmbeddedNode
|
1289
|
+
},
|
1290
|
+
"illegal node with subject having multiple properties": {
|
1291
|
+
input: %({
|
1292
|
+
"@id": {
|
1293
|
+
"@id": "ex:rei",
|
1294
|
+
"ex:prop": ["value1", "value2"]
|
1295
|
+
},
|
1296
|
+
"ex:prop": "value3"
|
1297
|
+
}),
|
1298
|
+
exception: JSON::LD::JsonLdError::InvalidEmbeddedNode
|
1299
|
+
},
|
1300
|
+
"illegal node with subject having multiple types": {
|
1301
|
+
input: %({
|
1302
|
+
"@id": {
|
1303
|
+
"@id": "ex:rei",
|
1304
|
+
"@type": ["ex:Type1", "ex:Type2"]
|
1305
|
+
},
|
1306
|
+
"ex:prop": "value3"
|
1307
|
+
}),
|
1308
|
+
exception: JSON::LD::JsonLdError::InvalidEmbeddedNode
|
1309
|
+
},
|
1310
|
+
"illegal node with subject having type and property": {
|
1311
|
+
input: %({
|
1312
|
+
"@id": {
|
1313
|
+
"@id": "ex:rei",
|
1314
|
+
"@type": "ex:Type",
|
1315
|
+
"ex:prop": "value"
|
1316
|
+
},
|
1317
|
+
"ex:prop": "value2"
|
1318
|
+
}),
|
1319
|
+
exception: JSON::LD::JsonLdError::InvalidEmbeddedNode
|
1320
|
+
},
|
1321
|
+
"node with embedded object": {
|
1322
|
+
input: %({
|
1323
|
+
"@id": "ex:subj",
|
1324
|
+
"ex:value": {
|
1325
|
+
"@id": {
|
1326
|
+
"@id": "ex:rei",
|
1327
|
+
"ex:prop": "value"
|
1328
|
+
}
|
1329
|
+
}
|
1330
|
+
}),
|
1331
|
+
expected: %(
|
1332
|
+
<ex:subj> <ex:value> <<<ex:rei> <ex:prop> "value">> .
|
1333
|
+
),
|
1334
|
+
},
|
1335
|
+
"node with embedded object having properties": {
|
1336
|
+
input: %({
|
1337
|
+
"@id": "ex:subj",
|
1338
|
+
"ex:value": {
|
1339
|
+
"@id": {
|
1340
|
+
"@id": "ex:rei",
|
1341
|
+
"ex:prop": "value"
|
1342
|
+
},
|
1343
|
+
"ex:prop": "value2"
|
1344
|
+
}
|
1345
|
+
}),
|
1346
|
+
expected: %(
|
1347
|
+
<ex:subj> <ex:value> <<<ex:rei> <ex:prop> "value">> .
|
1348
|
+
<<<ex:rei> <ex:prop> "value">> <ex:prop> "value2" .
|
1349
|
+
),
|
1350
|
+
},
|
1351
|
+
"node with recursive embedded object": {
|
1352
|
+
input: %({
|
1353
|
+
"@id": "ex:subj",
|
1354
|
+
"ex:value": {
|
1355
|
+
"@id": {
|
1356
|
+
"@id": {
|
1357
|
+
"@id": "ex:rei",
|
1358
|
+
"ex:prop": "value3"
|
1359
|
+
},
|
1360
|
+
"ex:prop": "value"
|
1361
|
+
},
|
1362
|
+
"ex:prop": "value2"
|
1363
|
+
}
|
1364
|
+
}),
|
1365
|
+
expected: %(
|
1366
|
+
<ex:subj> <ex:value> <<<<<ex:rei> <ex:prop> "value3">> <ex:prop> "value">> .
|
1367
|
+
<<<<<ex:rei> <ex:prop> "value3">> <ex:prop> "value">> <ex:prop> "value2" .
|
1368
|
+
),
|
1369
|
+
},
|
1370
|
+
}.each do |title, params|
|
1371
|
+
context(title) do
|
1372
|
+
it "Generates statements" do
|
1373
|
+
output_graph = RDF::Graph.new {|g| g << RDF::NTriples::Reader.new(params[:expected], rdfstar: true)}
|
1374
|
+
run_to_rdf params.merge(rdfstar: true, output: output_graph)
|
1375
|
+
end if params[:expected]
|
1376
|
+
|
1377
|
+
it "Exception" do
|
1378
|
+
run_to_rdf params.merge(rdfstar: true)
|
1379
|
+
end if params[:exception]
|
1380
|
+
end
|
1381
|
+
end
|
1382
|
+
end
|
1383
|
+
|
1178
1384
|
context "exceptions" do
|
1179
1385
|
{
|
1180
1386
|
"Invalid subject" => {
|