when_exe 0.4.0 → 0.4.1

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.
@@ -0,0 +1,574 @@
1
+ # -*- coding: utf-8 -*-
2
+ =begin
3
+ Copyright (C) 2014-2015 Takashi SUGA
4
+
5
+ You may use and/or modify this file according to the license described in the LICENSE.txt file included in this archive.
6
+ =end
7
+
8
+ module When
9
+ #
10
+ # When::Parts::Resource への追加
11
+ #
12
+ module Parts::Resource
13
+
14
+ DocRoot = "http://www.rubydoc.info/gems/when_exe/#{When::VERSION}/When/"
15
+
16
+ Schema = {
17
+ 'reference' => "Locale#reference-instance_method",
18
+ 'label' => "BasicTypes/M17n#label-instance_method",
19
+ 'prev' => "TM/TemporalPosition#prev-instance_method",
20
+ 'succ' => "TM/TemporalPosition#succ-instance_method",
21
+ 'frame' => "TM/TemporalPosition#frame-instance_method",
22
+ 'ruler' => "TM/TemporalPosition#query-instance_method",
23
+ 'coordinate' => "TM/CalDate#cal_date-instance_method",
24
+ 'sdn' => "TM/CalDate#to_i-instance_method",
25
+ 'calendarEra' => "TM/CalDate#calendar_era-instance_method",
26
+ 'referenceEvent' => "TM/Clock#reference_event-instance_method",
27
+ 'referenceTime' => "TM/Clock#reference_time-instance_method",
28
+ 'utcReference' => "TM/Clock#utc_reference-instance_method",
29
+ 'dateBasis' => "TM/Clock#date_basis-instance_method",
30
+ 'referenceFrame' => "TM/Calendar#reference_frame-instance_method",
31
+ 'timeBasis' => "TM/Calendar#time_basis-instance_method",
32
+ 'referenceEvent' => "TM/CalendarEra#reference_event-instance_method",
33
+ 'referenceDate' => "TM/CalendarEra#reference_date-instance_method",
34
+ 'julianReference' => "TM/CalendarEra#julian_reference-instance_method",
35
+ 'datingSystem' => "TM/CalendarEra#dating_system-instance_method",
36
+ 'epoch' => "TM/CalendarEra#epoch-instance_method",
37
+ 'remainder' => "Coordinates/Residue#remainder-instance_method",
38
+ 'divisor' => "Coordinates/Residue#divisor-instance_method",
39
+ 'longitude' => "Coordinates/Spatial#longitude-instance_method",
40
+ 'latitude' => "Coordinates/Spatial#latitude-instance_method",
41
+ 'altitide' => "Coordinates/Spatial#latitude-instance_method",
42
+ 'event' => "CalendarNote#event-instance_method",
43
+ }
44
+
45
+ XSD = 'http://www.w3.org/2001/XMLSchema'
46
+ RDFS = 'http://www.w3.org/2000/01/rdf-schema#'
47
+ RDF = 'http://www.w3.org/1999/02/22-rdf-syntax-ns#'
48
+
49
+ #
50
+ # @private
51
+ #
52
+ module MinimumLinkedDataAPI
53
+
54
+ attr_accessor :iri
55
+ private :iri=
56
+
57
+ def rdf_graph(options={})
58
+ self
59
+ end
60
+ end
61
+
62
+ class << self
63
+
64
+ # context オブジェクトを生成する
65
+ #
66
+ # @param [String] iri self に与える iri
67
+ #
68
+ # @return [Hash]
69
+ #
70
+ def context(iri=nil)
71
+ ts = base_uri.sub(/When\/$/, 'ts#')
72
+ hash = {'ts' => ts}
73
+ Schema.each_pair do |key, ref|
74
+ hash['ts:' + key] = {'@type' => '@id'}
75
+ end
76
+ bless(hash, iri || ts[0..-2])
77
+ end
78
+
79
+ # Schema オブジェクトを生成する
80
+ #
81
+ # @param [String] iri self に与える iri
82
+ #
83
+ # @return [Hash]
84
+ #
85
+ def schema(iri=nil)
86
+ ts = base_uri.sub(/When\/$/, 'ts#')
87
+ hash =
88
+ {'@context'=>{'ts' => ts},
89
+ '@graph' => Schema.keys.map {|id| {'@id'=>'ts:'+id, 'ts:reference'=>{'@id'=>DocRoot + Schema[id]}}}
90
+ }
91
+ bless(hash, iri || ts[0..-2])
92
+ end
93
+
94
+ # Hash に最低限のメソッドを追加する
95
+ #
96
+ # @param [Hash] hash メソッドを追加される Hash
97
+ # @param [String] iri hash に与える iri
98
+ #
99
+ # @return [Hash]
100
+ #
101
+ def bless(hash, iri)
102
+ hash.extend(MinimumLinkedDataAPI)
103
+ hash.send(:iri=, iri)
104
+ hash
105
+ end
106
+
107
+ # jsonld を表現する Hash を各種のRDF表現形式に変換する
108
+ #
109
+ # @param [Hash] jsonld_hash jsonld を表現する Hash
110
+ # @param [Symbol] writer RDF表現形式 (デフォルト :jsonld - 単に Hash を JSON化)
111
+ # @param [Hash] prefixes prefix から namespace を引く Hash
112
+ #
113
+ # @return [String] writer で指定されたRDF表現形式の文字列
114
+ #
115
+ def to_linked_data(jsonld_hash, writer=:jsonld, prefixes=nil)
116
+ if writer == :jsonld
117
+ JSON.generate(jsonld_hash)
118
+ else
119
+ array = JSON::LD::API.toRdf(jsonld_hash)
120
+ graph = ::RDF::Graph.new << array
121
+ args = [writer]
122
+ args << {:prefixes=>prefixes} if prefixes
123
+ graph.dump(*args)
124
+ end
125
+ end
126
+
127
+ # 指定の範囲のResourceオブジェクトのグラフの jsonld を表現する Hash を生成する
128
+ #
129
+ # @param [Range or Array] objects jsonld を表現する Hash を生成するResourceオブジェクトの範囲または配列
130
+ # @param [Hash] options 以下の通り
131
+ # @option options [Boolean] :include 自身が含むResourceオブジェクトをグラフに含める(デフォルト nil)
132
+ # @option options [Object] @... そのまま戻り値のHashに追加
133
+ # @option options [Symbol] その他 {When::TM::CalDate#to_jsonld_hash} などを参照
134
+ #
135
+ # @return [Hash] jsonld を表現する Hash
136
+ #
137
+ def rdf_graph(objects, options={})
138
+ jsonld_hash = {}
139
+ sub_options = {}
140
+ options.each_pair do |key, value|
141
+ (/^@/ =~ key.to_s ? jsonld_hash : sub_options)[key] = value
142
+ end
143
+ jsonld_hash['@graph'] ||= []
144
+ sub_options[:prefixes] ||= When::Parts::Resource.namespace_prefixes if options[:context]
145
+ objects.each do |object|
146
+ object.register_graph(jsonld_hash['@graph'], sub_options)
147
+ end
148
+ if options['@context'] && options[:context]
149
+ sub_options[:prefixes].each_pair do |key, value|
150
+ options['@context'][key] ||= value.last
151
+ end
152
+ end
153
+ jsonld_hash
154
+ end
155
+
156
+ # Linked Data 用 namespace URI の Array の Hash を生成する
157
+ #
158
+ # @param [Array<When::Parts::Resource or String>] resources namespace を抽出する resource の Array
159
+ #
160
+ # @return [Hash]
161
+ #
162
+ def namespace_prefixes(*resources)
163
+ base = base_uri.sub(/When\/$/, '')
164
+ resources.inject({
165
+ 'xsd' => [XSD],
166
+ 'rdf' => [RDF],
167
+ 'rdfs' => [RDFS],
168
+ 'owl' => ['http://www.w3.org/2002/07/owl#'],
169
+ 'dc' => ['http://purl.org/dc/elements/1.1/'],
170
+ 'dcq' => ['http://purl.org/dc/terms/'],
171
+ 'dct' => ['http://purl.org/dc/dcmitype/'],
172
+ # 'tp' => [base + 'tp/'],
173
+ 'ts' => [base + 'ts#']
174
+ }) {|namespace, resource|
175
+ resource = When.Resource(resource) if resource.kind_of?(String)
176
+ hash = resource.namespace_prefixes
177
+ hash.each_pair do |key, value|
178
+ namespace[key] = namespace[key] ? (namespace[key] + value).uniq.sort_by {|ns| -ns.length} : value
179
+ end
180
+ namespace
181
+ }
182
+ end
183
+
184
+ # URIのArrayの最後の要素を prefix に対応する namespace とみなして json-ld の @context に適合する形式に変換する
185
+ #
186
+ # @param [Hash<String=>Array<String>>] prefixes Linked Data 用 namespace URIのArrayのHash
187
+ #
188
+ # @return [Hash<String=>String>] prefix と namespace の1対1対応
189
+ #
190
+ def prefixs_to_context(prefixes)
191
+ Hash[*(prefixes.keys.map {|key| [key, prefixes[key].last]}.flatten)]
192
+ end
193
+
194
+ # json-ld の @context に適合する形式で記述された 1対1対応する prefix と namespace を Linked Data 用 namespace URIのArrayのHash化する
195
+ #
196
+ # @param [Hash<String=>String>] prefixes prefix と namespace の1対1対応
197
+ #
198
+ # @return [Hash<String=>Array<String>>] Linked Data 用 namespace URIのArrayのHash
199
+ #
200
+ def context_to_prefixs(prefixes)
201
+ hash = {}
202
+ prefixes.each_pair do |key, value|
203
+ hash[key] = [value]
204
+ end
205
+ hash
206
+ end
207
+ end
208
+
209
+ # Linked Data 用 namespace URI の Array の Hash を生成する
210
+ #
211
+ # @return [Hash]
212
+ #
213
+ def namespace_prefixes
214
+ prefixes = {}
215
+ child.each do |c|
216
+ next if c.iri =~ / /
217
+ iri = c.child ? c.iri : self.iri
218
+ prefixes[((c.kind_of?(When::BasicTypes::M17n) ? c : c.label) / 'en').split(/ +/).first] = [iri + '::']
219
+ end
220
+ prefixes
221
+ end
222
+
223
+ # 自身を root とするグラフの jsonld を表現する Hash を各種のRDF表現形式に変換する
224
+ #
225
+ # @param [Symbol] writer RDF表現形式 (デフォルト :jsonld - 単に Hash を JSON化)
226
+ # @param [Hash] options 内部で呼び出す #to_jsonld_hash にそのまま渡す
227
+ #
228
+ # @return [String] writer で指定されたRDF表現形式の文字列
229
+ #
230
+ def to_linked_data(writer=:jsonld, options={})
231
+ jsonld_hash = rdf_graph(options)
232
+ When::Parts::Resource.to_linked_data(jsonld_hash, writer, jsonld_hash['@context'])
233
+ end
234
+
235
+ # 自身を root とするグラフの jsonld を表現する Hash を生成する
236
+ #
237
+ # @param [Hash] options {When::Parts::Resource.rdf_graph} を参照
238
+ #
239
+ # @return [Hash] jsonld を表現する Hash
240
+ #
241
+ def rdf_graph(options={})
242
+ When::Parts::Resource.rdf_graph([self], options)
243
+ end
244
+
245
+ # Resourceオブジェクトの jsonld をグラフに追加する
246
+ #
247
+ # @param [Array<Hash>] graph 個別のResourceオブジェクトの jsonld hash の Array
248
+ # @param [Hash] options {When::Parts::Resource.rdf_graph} を参照
249
+ #
250
+ # @return [Array] jsonld hash の Array
251
+ #
252
+ def register_graph(graph, options={})
253
+ jsonld_hash = to_jsonld_hash(options)
254
+ graph << jsonld_hash
255
+ if options[:include] && child
256
+ included_opt = {:included=>jsonld_hash['@id']}.update(options)
257
+ child.each do |included|
258
+ included.register_graph(graph, included_opt)
259
+ end
260
+ end
261
+ end
262
+
263
+ # Resourceオブジェクトの jsonld を表現する Hash を生成する
264
+ #
265
+ # @param [Hash] options 以下の通り
266
+ # @option options [Hash] :prefixes Linked Data 用 namespace URI の Array の Hash ('@context'互換でも可)
267
+ # @option options [Boolean] :context true なら 可能な限り namespace を prefix に変換する
268
+ # @option options [String or Boolean] :prev ひとつ前のResourceオブジェクトのIRI
269
+ # @option options [String or Boolean] :succ ひとつ後のResourceオブジェクトのIRI
270
+ # @option options [String or Boolean] :included 自身を含む親ResourceオブジェクトのIRI
271
+ # @option options [Object] @... そのまま戻り値のHashに反映
272
+ #
273
+ # @note :prev,:succ,:included が true のときは自身で当該IRIを計算する。
274
+ # nil,false のときは当該情報を戻り値のHashに追加しない。
275
+ #
276
+ # @return [Hash] jsonld を表現する Hash
277
+ #
278
+ def to_jsonld_hash(options={})
279
+ neighbor = {
280
+ :succ => options[:succ],
281
+ :prev => options[:prev],
282
+ :parent => options[:included]
283
+ }
284
+ neighbor.each_pair do |key, value|
285
+ neighbor[key] = send(key) if value == true
286
+ neighbor[key] = neighbor[key].iri if neighbor[key].kind_of?(When::Parts::Resource)
287
+ end
288
+ hash, context, base = hash_and_variables(options)
289
+ ts = base + 'ts#'
290
+ hash['@id'] = iri
291
+ hash[ts + 'succ'] = {'@id'=>neighbor[:succ]} if neighbor[:succ]
292
+ hash[ts + 'prev'] = {'@id'=>neighbor[:prev]} if neighbor[:prev]
293
+ hash['@reverse' ] = (hash['@reverse'] || {}).merge(
294
+ {RDFS + 'member'=>{'@id'=>neighbor[:parent]}}) if neighbor[:parent]
295
+ hash.update(hash_for_jsonld(ts, options))
296
+ compact_predicate(hash, context, options[:prefixes])
297
+ hash
298
+ end
299
+
300
+ private
301
+
302
+ #
303
+ # jsonld_hash と context, base を準備する
304
+ #
305
+ def hash_and_variables(options)
306
+ base = When::Parts::Resource.base_uri.sub(/When\/$/, '')
307
+ hash = {}
308
+ options.each_pair do |key, value|
309
+ hash[key] = value if /^@/ =~ key.to_s
310
+ end
311
+ hash[RDF + 'type'] = {'@id'=>base + 'ts/' + self.class.to_s.gsub(/::/, '/')}
312
+ if options[:context]
313
+ options[:prefixes] ||= When::Parts::Resource.namespace_prefixes
314
+ context = hash['@context'] || {}
315
+ end
316
+ [hash, context, base]
317
+ end
318
+
319
+ #
320
+ # jsonld_hash の個別部分
321
+ #
322
+ def hash_for_jsonld(ts, options)
323
+ tp = ts.sub('ts#', 'tp/')
324
+ hash = {}
325
+ to_h({:method=>:iri}.update(options)).each_pair do |key, value|
326
+ tskey = ts + key.to_s
327
+ case value
328
+ when Array ; hash[tskey] = value.map {|v|
329
+ case v
330
+ when When::TM::CalDate ; {'@id'=>tp + v.to_uri_escape}
331
+ when /:\/\// ; {'@id'=>v}
332
+ else ; nil
333
+ end
334
+ }.compact unless value.empty?
335
+ when Hash ;
336
+ when /:\/\// ; hash[tskey] = {'@id'=>value}
337
+ when When::TM::JulianDate ; hash[tskey] = value.precision <= When::DAY ? value.to_i : value.to_f
338
+ when When::Coordinates::Pair ; hash[tskey] = value.to_s
339
+ when Numeric ; hash[tskey] = value
340
+ else ; hash[tskey] = value.to_s
341
+ end
342
+ end
343
+ hash
344
+ end
345
+
346
+ #
347
+ # 述語をコンパクト化する
348
+ #
349
+ def compact_predicate(hash, context, prefixes)
350
+ [hash, hash['@reverse']].each do |h|
351
+ h.keys.each do |key|
352
+ id = compact_namespace_to_prefix(key, prefixes, context)
353
+ if context && id != key
354
+ prefix = id.split(':').first
355
+ context[prefix] = prefixes[prefix].last
356
+ end
357
+ h[id] = h.delete(key)
358
+ end if h
359
+ end
360
+ end
361
+
362
+ #
363
+ # namespace を prefix にコンパクト化する
364
+ #
365
+ def compact_namespace_to_prefix(source, prefixes, context=nil)
366
+ return source unless prefixes
367
+ prefixes.each_pair do |key, value|
368
+ Array(value).each do |prefix|
369
+ start = source.index(prefix)
370
+ body = source[prefix.length..-1]
371
+ return key + ':' + body if start == 0 && body !~ /:/
372
+ end
373
+ end
374
+ return source unless context
375
+ source =~ /\A((.+)([:#\/]))([^:#\/]+)\z/
376
+ namespace, item = $1.to_s, $4
377
+ if namespace =~ /^Ahttp:\/\/([^.]+)\.wikipedia\.org/
378
+ prefix = "wiki_#{$1}"
379
+ elsif namespace && namespace.index(When::Parts::Resource.base_uri) == 0
380
+ label = begin When.Resource(namespace.sub(/::\z/, '')) rescue return source end
381
+ label = label.label unless label.kind_of?(When::BasicTypes::M17n)
382
+ prefix = label.to_m17n / 'en'
383
+ return source unless prefix =~ /\A[-A-Z\d_]+\z/i
384
+ else
385
+ return source
386
+ end
387
+ prefixes[prefix] ||= []
388
+ prefixes[prefix] << namespace
389
+ prefixes[prefix] = prefixes[prefix].sort_by {|value| -value.length}
390
+ context[prefix] = prefixes[prefix].last
391
+ prefix + ':' + item
392
+ end
393
+ end
394
+
395
+ #
396
+ # When::BasicTypes::M17n への追加
397
+ #
398
+ class BasicTypes::M17n
399
+
400
+ private
401
+
402
+ #
403
+ # jsonld_hash の個別部分
404
+ #
405
+ def hash_for_jsonld(ts, options)
406
+ hash = {}
407
+ hash[RDFS + 'label'] = names.keys.map {|key| key=='' ? names[key] : {'@language'=>key, '@value'=>names[key]}}
408
+ hash[ts + 'label'] = label
409
+ hash[ts + 'reference'] = link.values.map {|ref| {'@id'=>ref}}
410
+ hash
411
+ end
412
+ end
413
+
414
+ #
415
+ # When::TM::Clock への追加
416
+ #
417
+ class TM::Clock
418
+
419
+ private
420
+
421
+ #
422
+ # jsonld_hash の個別部分
423
+ #
424
+ def hash_for_jsonld(ts, options)
425
+ hash = {}
426
+ self.class::HashProperty.each do |sym|
427
+ hash[ts + sym.to_s] = send(sym).to_s if send(sym)
428
+ end
429
+ hash
430
+ end
431
+ end
432
+
433
+ #
434
+ # When::TM::CalDate への追加
435
+ #
436
+ class TM::CalDate
437
+
438
+ # URI - linked data 用
439
+ #
440
+ # @overload to_uri_linkeddata()
441
+ #
442
+ # @return [String]
443
+ #
444
+ def to_uri_linkeddata(*args)
445
+ date, frame = _to_uri(to_s(*args)).split('^^', 2)
446
+ frame += '_' if frame =~ /\d\z/
447
+ date = "#{frame}(#{date})" if frame
448
+ When::Parts::Resource.base_uri.sub(/When\/$/, 'tp/') + date
449
+ end
450
+
451
+ # 自身を root とするグラフの jsonld を表現する Hash を各種のRDF表現形式に変換する
452
+ #
453
+ # @param [Symbol] writer RDF表現形式 (デフォルト :jsonld - 単に Hash を JSON化)
454
+ # @param [Hash] options 内部で呼び出す #to_jsonld_hash にそのまま渡す。ただし、
455
+ # @option options [Boolean] :include 自身が含む分解能が高いCalDateオブジェクトをグラフに含める(デフォルト true)
456
+ #
457
+ # @return [String] writer で指定されたRDF表現形式の文字列
458
+ #
459
+ def to_linked_data(writer=:jsonld, options={})
460
+ hash = rdf_graph({:include=>true}.update(options))
461
+ When::Parts::Resource.to_linked_data(hash, writer, hash['@context'])
462
+ end
463
+
464
+ # 自身を root とするグラフの jsonld を表現する Hash を生成する
465
+ #
466
+ # @param [Hash] options {When::Parts::Resource.rdf_graph} を参照
467
+ #
468
+ # @return [Hash] jsonld を表現する Hash
469
+ #
470
+ def rdf_graph(options={})
471
+ root = options[:include] && precision < When::YEAR ? floor(When::YEAR) : self
472
+ When::Parts::Resource.rdf_graph([root], options)
473
+ end
474
+
475
+ # CalDateオブジェクトの jsonld をグラフに追加する
476
+ #
477
+ # @param [Array<Hash>] graph 個別のCalDateオブジェクトの jsonld hash の Array
478
+ # @param [Hash] options {When::Parts::Resource.rdf_graph} を参照
479
+ #
480
+ # @return [Array] jsonld hash の Array
481
+ #
482
+ def register_graph(graph, options={})
483
+ jsonld_hash = to_jsonld_hash(options)
484
+ graph << jsonld_hash
485
+ if options[:include] && precision < When::DAY
486
+ included = floor(precision+1)
487
+ included_opt = {:included=>jsonld_hash['@id']}.update(options)
488
+ while include?(included) do
489
+ included.register_graph(graph, included_opt)
490
+ included = included.succ
491
+ end
492
+ end
493
+ end
494
+
495
+ # CalDateオブジェクトの jsonld を表現する Hash を生成する
496
+ #
497
+ # @param [Hash] options 以下の通り
498
+ # @option options [Hash] :prefixes Linked Data 用 namespace URI の Array の Hash ('@context'互換でも可)
499
+ # @option options [Boolean] :context true なら 可能な限り namespace を prefix に変換する
500
+ # @option options [String or Boolean] :prev ひとつ前のCalDateオブジェクトのIRI
501
+ # @option options [String or Boolean] :succ ひとつ後のCalDateオブジェクトのIRI
502
+ # @option options [String or Boolean] :included 自身を含む分解能が1低いCalDateオブジェクトのIRI
503
+ # @option options [Hash] :note 暦注計算のオプション {When::Parts::Resource#notes} を参照
504
+ # @option options [Object] @... そのまま戻り値のHashに反映
505
+ #
506
+ # @note :prev,:succ,:included が true のときは自身で当該IRIを計算する。
507
+ # nil,false のときは当該情報を戻り値のHashに追加しない。
508
+ #
509
+ # @return [Hash] jsonld を表現する Hash
510
+ #
511
+ def to_jsonld_hash(options={})
512
+ hash, context, base = hash_and_variables(options)
513
+ tp = base + 'tp/'
514
+ ts = base + 'ts#'
515
+ hash['@id'] ||= tp + to_uri_escape
516
+ hash[ts + 'sdn'] = precision <= When::DAY ? to_i : to_f
517
+ hash[ts + 'frame'] = {'@id'=>frame.iri(false)}
518
+ hash[ts + 'calendarEra'] = {'@id'=>calendar_era.iri(false)} if calendar_era
519
+ hash[ts + 'coordinate'] = self[precision].to_s
520
+ hash[ts + 'ruler'] = {'@id'=>query['name'].iri} if query && query['name'].kind_of?(When::BasicTypes::M17n)
521
+ hash[ts + 'succ'] = options[:succ].kind_of?(String) ?
522
+ options[:succ] : {'@id'=>tp + succ.to_uri_escape} if options[:succ]
523
+ hash[ts + 'prev'] = options[:prev].kind_of?(String) ?
524
+ options[:prev] : {'@id'=>tp + prev.to_uri_escape} if options[:prev]
525
+ hash['@reverse'] = (hash['@reverse'] || {}).merge(
526
+ {RDFS + 'member'=>
527
+ {'@id'=>options[:included].kind_of?(String) ?
528
+ options[:included] :
529
+ tp + floor(precision-1).to_uri_escape
530
+ }
531
+ }) if options[:included] && precision + frame.indices.size > 0
532
+ compact_predicate(hash, context, options[:prefixes])
533
+ note_options = {:indices=>precision, :notes=>:all}
534
+ note_options.update(options[:note]) if options[:note]
535
+ notes(note_options).first.each do |note|
536
+ next unless note[:note]
537
+ if note[:value].kind_of?(Array)
538
+ value = note[:value].flatten.reject {|v| v.kind_of?(Hash) || v =~ /-\z/ }.map {|v| _value_str(note[:note], v)}
539
+ value = value.first if value.size == 1
540
+ else
541
+ value =_value_str(note[:note], note[:value])
542
+ end
543
+ id = compact_namespace_to_prefix(value, options[:prefixes], context)
544
+ hash[compact_namespace_to_prefix(_note_str(note[:note]), options[:prefixes], context)] = (id == value && id !~ /:\/\//) ? id : {'@id'=>id}
545
+ end
546
+ hash
547
+ end
548
+
549
+ private
550
+
551
+ #
552
+ # できるだけ上位の IRI を note の IRI とする
553
+ #
554
+ def _note_str(note)
555
+ note = note.parent if note.equal?(note.parent.label)
556
+ note.iri
557
+ end
558
+
559
+ #
560
+ # できるだけ IRI を使用するようにしつつ value を JSON 可能な型に変換する
561
+ #
562
+ def _value_str(note, value)
563
+ case value
564
+ when Integer, Float ; value
565
+ when When::Parts::Resource
566
+ value.parent.equal?(note.parent) ? value.to_s :
567
+ !value.parent.kind_of?(When::BasicTypes::M17n) ? value.parent.iri :
568
+ value.registered? ? value.iri :
569
+ value.to_s
570
+ else ; value.to_s
571
+ end
572
+ end
573
+ end
574
+ end