relaton-bib 1.4.1 → 1.5.pre

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: 82478564be12002c51d6f7f81ea3c54ca36c5bc82ca545936f4736db3ddc738e
4
- data.tar.gz: 93d029e955c664c2f6a0c0e2e9828f957b6e28658df37336a4e3a1dcf2b8e64c
3
+ metadata.gz: 718bae79646e15f68243d997e053ed614d8309dafad8cbb8e9d0189d49198171
4
+ data.tar.gz: e54d51485d37662aa2507d074f859b896277d13fe298158ce84faf9570e037bc
5
5
  SHA512:
6
- metadata.gz: ae4783978cf446d07b669de15c00f7e9018736347dfb5999ca7b5c11890a3448bb723dce967f5ef7d83199eaca6c01cf2750b557816ea8ed3633743b36bb2405
7
- data.tar.gz: da5f68cd7839e4436adedfbdfbc82923c3416cec188b411cf4cb9d288ba8d0722cf15d39f909daef7afadb2792affc21e7c83c88ce4ecc71de0fb2cd7338e81b
6
+ metadata.gz: 630aee8ec416f891616c5efcdd068994422bfca2415f57a9e211fec53bece058c51af62220301dd7dc547c5fcde34852f5fc970256d6a845040fd58745ab5ca7
7
+ data.tar.gz: 7dfc99a09a5e896a76c27fed1c0dcc8ff02b126d51c019831532849626a972a28f2f1593f1d5e59b3a8ced5b97264a6d2abdb876f2874b2a3aad037017aa2757
@@ -1,3 +1,4 @@
1
+ require "forwardable"
1
2
  require "relaton_bib/version"
2
3
  require "relaton_bib/deep_dup"
3
4
  require "relaton_bib/bibliographic_item"
@@ -1,4 +1,31 @@
1
1
  module RelatonBib
2
+ class BiblioNoteCollection
3
+ extend Forwardable
4
+
5
+ def_delegators :@array, :[], :first, :last, :empty?, :any?, :size,
6
+ :each, :map, :detect, :length
7
+
8
+ def initialize(notes)
9
+ @array = notes
10
+ end
11
+
12
+ # @param bibnote [RelatonBib::BiblioNote]
13
+ # @return [self]
14
+ def <<(bibnote)
15
+ @array << bibnote
16
+ self
17
+ end
18
+
19
+ # @param opts [Hash]
20
+ # @option opts [Nokogiri::XML::Builder] XML builder
21
+ # @option opts [String] :lang language
22
+ def to_xml(**opts)
23
+ bnc = @array.select { |bn| bn.language&.include? opts[:lang] }
24
+ bnc = @array unless bnc.any?
25
+ bnc.each { |bn| bn.to_xml opts[:builder] }
26
+ end
27
+ end
28
+
2
29
  class BiblioNote < FormattedString
3
30
  # @return [String, NilClass]
4
31
  attr_reader :type
@@ -45,7 +45,7 @@ module RelatonBib
45
45
  attr_reader :id, :type, :docnumber, :edition, :doctype
46
46
 
47
47
  # @!attribute [r] title
48
- # @return [Array<RelatonBib::TypedTitleString>]
48
+ # @return [RelatonBib::TypedTitleStringCollection]
49
49
 
50
50
  # @return [Array<RelatonBib::TypedUri>]
51
51
  attr_reader :link
@@ -59,10 +59,10 @@ module RelatonBib
59
59
  # @return [Array<RelatonBib::ContributionInfo>]
60
60
  attr_reader :contributor
61
61
 
62
- # @return [RelatonBib::BibliongraphicItem::Version, NilClass]
62
+ # @return [RelatonBib::BibliographicItem::Version, NilClass]
63
63
  attr_reader :version
64
64
 
65
- # @return [Array<RelatonBib::BiblioNote>]
65
+ # @return [RelatonBib::BiblioNoteCollection]
66
66
  attr_reader :biblionote
67
67
 
68
68
  # @return [Array<String>] language Iso639 code
@@ -126,7 +126,8 @@ module RelatonBib
126
126
  # rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
127
127
 
128
128
  # @param id [String, NilClass]
129
- # @param title [Array<RelatonBib::TypedTitleString>]
129
+ # @param title [RelatonBib::TypedTitleStringCollection,
130
+ # Array<Hash, RelatonBib::TypedTitleString>]
130
131
  # @param formattedref [RelatonBib::FormattedRef, NilClass]
131
132
  # @param type [String, NilClass]
132
133
  # @param docid [Array<RelatonBib::DocumentIdentifier>]
@@ -136,7 +137,7 @@ module RelatonBib
136
137
  # @param docstatus [RelatonBib::DocumentStatus, NilClass]
137
138
  # @param edition [String, NilClass]
138
139
  # @param version [RelatonBib::BibliographicItem::Version, NilClass]
139
- # @param biblionote [Array<RelatonBib::BiblioNote>]
140
+ # @param biblionote [RelatonBib::BiblioNoteCollection]
140
141
  # @param series [Array<RelatonBib::Series>]
141
142
  # @param medium [RelatonBib::Medium, NilClas]
142
143
  # @param place [Array<String, RelatonBib::Place>]
@@ -193,9 +194,7 @@ module RelatonBib
193
194
  warn %{[relaton-bib] document type "#{args[:type]}" is invalid.}
194
195
  end
195
196
 
196
- @title = (args[:title] || []).map do |t|
197
- t.is_a?(Hash) ? TypedTitleString.new(t) : t
198
- end
197
+ @title = TypedTitleStringCollection.new(args[:title])
199
198
 
200
199
  @date = (args[:date] || []).map do |d|
201
200
  d.is_a?(Hash) ? BibliographicDate.new(d) : d
@@ -224,7 +223,7 @@ module RelatonBib
224
223
  @docnumber = args[:docnumber]
225
224
  @edition = args[:edition]
226
225
  @version = args[:version]
227
- @biblionote = args.fetch :biblionote, []
226
+ @biblionote = args.fetch :biblionote, BiblioNoteCollection.new([])
228
227
  @language = args.fetch :language, []
229
228
  @script = args.fetch :script, []
230
229
  @status = args[:docstatus]
@@ -262,7 +261,7 @@ module RelatonBib
262
261
  # @return [RelatonBib::FormattedString, Array<RelatonBib::FormattedString>]
263
262
  def abstract(lang: nil)
264
263
  if lang
265
- @abstract.detect { |a| a.language.include? lang }
264
+ @abstract.detect { |a| a.language&.include? lang }
266
265
  else
267
266
  @abstract
268
267
  end
@@ -300,14 +299,18 @@ module RelatonBib
300
299
  "#{makeid(identifier, false)}#{year}"
301
300
  end
302
301
 
303
- # @param builder [Nokogiri::XML::Builder, NillClass] (nil)
304
- # @return [String]
305
- def to_xml(builder = nil, **opts, &block)
306
- if builder
307
- render_xml builder, **opts, &block
302
+ # @param opts [Hash]
303
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
304
+ # @option opts [Boolean] :bibdata
305
+ # @option opts [Symbol, NilClass] :date_format (:short), :full
306
+ # @option opts [String, Symbol] :lang language
307
+ # @return [String] XML
308
+ def to_xml(**opts, &block)
309
+ if opts[:builder]
310
+ render_xml **opts, &block
308
311
  else
309
312
  Nokogiri::XML::Builder.new(encoding: "UTF-8") do |xml|
310
- render_xml xml, **opts, &block
313
+ render_xml builder: xml, **opts, &block
311
314
  end.doc.root.to_xml
312
315
  end
313
316
  end
@@ -387,12 +390,10 @@ module RelatonBib
387
390
  bibtex.to_s
388
391
  end
389
392
 
390
- # @param lang [String] language code Iso639
391
- # @return [Array<RelatonIsoBib::TypedTitleString>]
393
+ # @param lang [String, nil] language code Iso639
394
+ # @return [RelatonIsoBib::TypedTitleStringCollection]
392
395
  def title(lang: nil)
393
- if lang then @title.select { |t| t.title.language&.include? lang }
394
- else @title
395
- end
396
+ @title.lang lang
396
397
  end
397
398
 
398
399
  # @param type [Symbol] type of url, can be :src/:obp/:rss
@@ -420,7 +421,7 @@ module RelatonBib
420
421
  me.disable_id_attribute
421
422
  me.relation << DocumentRelation.new(type: "instance", bibitem: self)
422
423
  me.language.each do |l|
423
- me.title.delete_if { |t| t.type == "title-part" }
424
+ me.title.delete_title_part!
424
425
  ttl = me.title.select do |t|
425
426
  t.type != "main" && t.title.language&.include?(l)
426
427
  end
@@ -665,13 +666,16 @@ module RelatonBib
665
666
  # rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
666
667
  # rubocop:disable Style/NestedParenthesizedCalls, Metrics/BlockLength
667
668
 
668
- # @param builder [Nokogiri::XML::Builder]
669
- # @return [String]
670
- def render_xml(builder, **opts)
669
+ # @param opts [Hash]
670
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
671
+ # @option opts [Boolean] bibdata
672
+ # @option opts [Symbol, NilClass] :date_format (:short), :full
673
+ # @option opts [String] :lang language
674
+ def render_xml(**opts)
671
675
  root = opts[:bibdata] ? :bibdata : :bibitem
672
- xml = builder.send(root) do
676
+ xml = opts[:builder].send(root) do |builder|
673
677
  builder.fetched fetched if fetched
674
- title.each { |t| builder.title { t.to_xml builder } }
678
+ title.to_xml **opts
675
679
  formattedref&.to_xml builder
676
680
  link.each { |s| s.to_xml builder }
677
681
  docidentifier.each { |di| di.to_xml builder }
@@ -679,21 +683,23 @@ module RelatonBib
679
683
  date.each { |d| d.to_xml builder, **opts }
680
684
  contributor.each do |c|
681
685
  builder.contributor do
682
- c.role.each { |r| r.to_xml builder }
683
- c.to_xml builder
686
+ c.role.each { |r| r.to_xml **opts }
687
+ c.to_xml **opts
684
688
  end
685
689
  end
686
690
  builder.edition edition if edition
687
691
  version&.to_xml builder
688
- biblionote.each { |n| n.to_xml builder }
692
+ biblionote.to_xml **opts
689
693
  opts[:note]&.each do |n|
690
694
  builder.note(n[:text], format: "text/plain", type: n[:type])
691
695
  end
692
696
  language.each { |l| builder.language l }
693
697
  script.each { |s| builder.script s }
694
- abstract.each { |a| builder.abstract { a.to_xml(builder) } }
698
+ abstr = abstract.select { |ab| ab.language&.include? opts[:lang] }
699
+ abstr = abstract unless abstr.any?
700
+ abstr.each { |a| builder.abstract { a.to_xml(builder) } }
695
701
  status&.to_xml builder
696
- copyright&.each { |c| c.to_xml builder }
702
+ copyright&.each { |c| c.to_xml **opts }
697
703
  relation.each { |r| r.to_xml builder, **opts }
698
704
  series.each { |s| s.to_xml builder }
699
705
  medium&.to_xml builder
@@ -702,7 +708,9 @@ module RelatonBib
702
708
  accesslocation.each { |al| builder.accesslocation al }
703
709
  license.each { |l| builder.license l }
704
710
  classification.each { |cls| cls.to_xml builder }
705
- keyword.each { |kw| builder.keyword { kw.to_xml(builder) } }
711
+ kwrd = keyword.select { |kw| kw.language&.include? opts[:lang] }
712
+ kwrd = keyword unless kwrd.any?
713
+ kwrd.each { |kw| builder.keyword { kw.to_xml(builder) } }
706
714
  validity&.to_xml builder
707
715
  if block_given? then yield builder
708
716
  elsif opts[:bibdata] && (doctype || editorialgroup || ics&.any? ||
@@ -6,7 +6,7 @@ module RelatonBib
6
6
  class << self
7
7
  # @param bibtex [String]
8
8
  # @return [Hash{String=>RelatonBib::BibliographicItem}]
9
- def from_bibtex(bibtex)
9
+ def from_bibtex(bibtex) # rubocop:disable Metrics/AbcSize,Metrics/MethodLength
10
10
  BibTeX.parse(bibtex).reduce({}) do |h, bt|
11
11
  h[bt.key] = BibliographicItem.new(
12
12
  id: bt.key,
@@ -35,7 +35,7 @@ module RelatonBib
35
35
 
36
36
  # @param bibtex [BibTeX::Entry]
37
37
  # @return [Array<RelatonBib::DocumentIdentifier>]
38
- def fetch_docid(bibtex)
38
+ def fetch_docid(bibtex) # rubocop:disable Metrics/AbcSize
39
39
  docid = []
40
40
  docid << DocumentIdentifier.new(id: bibtex.isbn.to_s, type: "isbn") if bibtex["isbn"]
41
41
  docid << DocumentIdentifier.new(id: bibtex.lccn.to_s, type: "lccn") if bibtex["lccn"]
@@ -67,17 +67,17 @@ module RelatonBib
67
67
  end
68
68
 
69
69
  # @param bibtex [BibTeX::Entry]
70
- # @return [Array<Hash>]
70
+ # @return [RelatonBib::TypedTitleStringCollection]
71
71
  def fetch_title(bibtex)
72
72
  title = []
73
73
  title << { type: "main", content: bibtex.title.to_s } if bibtex["title"]
74
74
  title << { type: "main", content: bibtex.subtitle.to_s } if bibtex["subtitle"]
75
- title
75
+ TypedTitleStringCollection.new title
76
76
  end
77
77
 
78
78
  # @param bibtex [BibTeX::Entry]
79
79
  # @return [Array<Hash>]
80
- def fetch_contributor(bibtex)
80
+ def fetch_contributor(bibtex) # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/MethodLength
81
81
  contributor = []
82
82
  fetch_person(bibtex["author"]).each do |entity|
83
83
  contributor << { entity: entity, role: [{ type: "author" }] }
@@ -94,7 +94,7 @@ module RelatonBib
94
94
  if bibtex["institution"]
95
95
  contributor << {
96
96
  entity: { name: bibtex.institution.to_s },
97
- role: [{ type: "distributor", description: ["sponsor"] }]
97
+ role: [{ type: "distributor", description: ["sponsor"] }],
98
98
  }
99
99
  end
100
100
 
@@ -145,11 +145,11 @@ module RelatonBib
145
145
  end
146
146
 
147
147
  # @param bibtex [BibTeX::Entry]
148
- # @return [Array<RelatonBib::BiblioNote>]
148
+ # @return [RelatonBib::BiblioNoteCollection]
149
149
  def fetch_note(bibtex)
150
150
  bibtex.select do |k, _v|
151
151
  %i[annote howpublished comment note content].include? k
152
- end.reduce([]) do |mem, note|
152
+ end.reduce(BiblioNoteCollection.new([])) do |mem, note|
153
153
  type = case note[0]
154
154
  when :note then nil
155
155
  when :content then "tableOfContents"
@@ -164,13 +164,14 @@ module RelatonBib
164
164
  def fetch_relation(bibtex)
165
165
  return [] unless bibtex["booktitle"]
166
166
 
167
- title = TypedTitleString.new(type: "main", content: bibtex.booktitle.to_s)
168
- [{ type: "partOf", bibitem: BibliographicItem.new(title: [title]) }]
167
+ ttl = TypedTitleString.new(type: "main", content: bibtex.booktitle.to_s)
168
+ title = TypedTitleStringCollection.new [ttl]
169
+ [{ type: "partOf", bibitem: BibliographicItem.new(title: title) }]
169
170
  end
170
171
 
171
172
  # @param bibtex [BibTeX::Entry]
172
173
  # @return [Array<RelatonBib::BibItemLocality>]
173
- def fetch_extent(bibtex)
174
+ def fetch_extent(bibtex) # rubocop:disable Metrics/MethodLength,Metrics/AbcSize
174
175
  bibtex.select do |k, _v|
175
176
  %i[chapter pages volume].include? k
176
177
  end.reduce([]) do |mem, loc|
@@ -188,13 +189,13 @@ module RelatonBib
188
189
 
189
190
  # @param bibtex [BibTeX::Entry]
190
191
  # @return [Array<RelatonBib::Series>]
191
- def fetch_series(bibtex)
192
+ def fetch_series(bibtex) # rubocop:disable Metrics/MethodLength
192
193
  series = []
193
194
  if bibtex["journal"]
194
195
  series << Series.new(
195
196
  type: "journal",
196
197
  title: TypedTitleString.new(content: bibtex.journal.to_s),
197
- number: bibtex["number"]&.to_s,
198
+ number: bibtex["number"]&.to_s
198
199
  )
199
200
  end
200
201
 
@@ -207,7 +208,7 @@ module RelatonBib
207
208
 
208
209
  # @param bibtex [BibTeX::Entry]
209
210
  # @return [Array<RelatonBib::TypedUri>]
210
- def fetch_link(bibtex)
211
+ def fetch_link(bibtex) # rubocop:disable Metrics/AbcSize
211
212
  link = []
212
213
  link << TypedUri.new(type: "src", content: bibtex.url.to_s) if bibtex["url"]
213
214
  link << TypedUri.new(type: "doi", content: bibtex.doi.to_s) if bibtex["doi"]
@@ -242,4 +243,4 @@ module RelatonBib
242
243
  end
243
244
  end
244
245
  end
245
- end
246
+ end
@@ -31,11 +31,15 @@ module RelatonBib
31
31
  end
32
32
  end
33
33
 
34
- # @param builder [Nokogiri::XML::Builder]
35
- def to_xml(builder)
36
- builder.role(type: type) do
37
- description.each do |d|
38
- builder.description { |desc| d.to_xml(desc) }
34
+ # @param opts [Hash]
35
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
36
+ # @option opts [String] :lang language
37
+ def to_xml(**opts) # rubocop:disable Metrics/AbcSize
38
+ opts[:builder].role(type: type) do |builder|
39
+ desc = description.select { |d| d.language&.include? opts[:lang] }
40
+ desc = description unless desc.any?
41
+ desc.each do |d|
42
+ builder.description { |b| d.to_xml(b) }
39
43
  end
40
44
  end
41
45
  end
@@ -83,9 +87,11 @@ module RelatonBib
83
87
  @role = role.map { |r| ContributorRole.new(**r) }
84
88
  end
85
89
 
86
- # @param builder [Nokogiri::XML::Builder]
87
- def to_xml(builder)
88
- entity.to_xml builder
90
+ # @param opts [Hash]
91
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
92
+ # @option opts [String, Symbol] :lang language
93
+ def to_xml(**opts)
94
+ entity.to_xml **opts
89
95
  end
90
96
 
91
97
  # @return [Hash]
@@ -129,12 +129,16 @@ module RelatonBib
129
129
  @description = description
130
130
  end
131
131
 
132
- # @params builder [Nokogiri::XML::Builder]
133
- def to_xml(builder)
134
- builder.affiliation do
132
+ # @param opts [Hash]
133
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
134
+ # @option opts [String] :lang language
135
+ def to_xml(**opts) # rubocop:disable Metrics/AbcSize
136
+ opts[:builder].affiliation do |builder|
135
137
  builder.name { name.to_xml builder } if name
136
- description.each { |d| builder.description { d.to_xml builder } }
137
- organization.to_xml builder
138
+ desc = description.select { |d| d.language&.include? opts[:lang] }
139
+ desc = description unless desc.any?
140
+ desc.each { |d| builder.description { d.to_xml builder } }
141
+ organization.to_xml **opts
138
142
  end
139
143
  end
140
144
 
@@ -151,7 +155,7 @@ module RelatonBib
151
155
  # @param prefix [String]
152
156
  # @param count [Integer]
153
157
  # @return [String]
154
- def to_asciibib(prefix = "", count = 1)
158
+ def to_asciibib(prefix = "", count = 1) # rubocop:disable Metrics/AbcSize
155
159
  pref = prefix.empty? ? prefix : prefix + "."
156
160
  out = count > 1 ? "#{pref}affiliation::\n" : ""
157
161
  out += name.to_asciibib "#{pref}affiliation.name" if name
@@ -38,19 +38,21 @@ module RelatonBib
38
38
  @scope = scope
39
39
  end
40
40
 
41
- # @param builder [Nokogiri::XML::Builder]
42
- def to_xml(builder)
43
- builder.copyright do
41
+ # @param opts [Hash]
42
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
43
+ # @option opts [String, Symbol] :lang language
44
+ def to_xml(**opts)
45
+ opts[:builder].copyright do |builder|
44
46
  builder.from from ? from.year : "unknown"
45
47
  builder.to to.year if to
46
- owner.each { |o| builder.owner { o.to_xml builder } }
48
+ owner.each { |o| builder.owner { o.to_xml **opts } }
47
49
  builder.scope scope if scope
48
50
  end
49
51
  end
50
52
  # rubocop:enable Metrics/AbcSize
51
53
 
52
54
  # @return [Hash]
53
- def to_hash
55
+ def to_hash # rubocop:disable Metrics/AbcSize
54
56
  owners = single_element_array(owner.map { |o| o.to_hash["organization"] })
55
57
  hash = {
56
58
  "owner" => owners,
@@ -63,7 +63,7 @@ module RelatonBib
63
63
  opts.delete :note
64
64
  builder.relation(type: type) do
65
65
  builder.description { description.to_xml builder } if description
66
- bibitem.to_xml(builder, **opts.merge(embedded: true))
66
+ bibitem.to_xml(**opts.merge(builder: builder, embedded: true))
67
67
  locality.each { |l| l.to_xml builder }
68
68
  source_locality.each { |l| l.to_xml builder }
69
69
  end
@@ -71,7 +71,7 @@ module RelatonBib
71
71
  # rubocop:enable Metrics/AbcSize
72
72
 
73
73
  # @return [Hash]
74
- def to_hash
74
+ def to_hash # rubocop:disable Metrics/AbcSize
75
75
  hash = { "type" => type, "bibitem" => bibitem.to_hash }
76
76
  hash["description"] = description.to_hash if description
77
77
  hash["locality"] = single_element_array(locality) if locality&.any?
@@ -1,7 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require "forwardable"
4
-
5
3
  module RelatonBib
6
4
  # Document relation collection
7
5
  class DocRelationCollection
@@ -58,7 +58,8 @@ module RelatonBib
58
58
  def title_hash_to_bib(ret)
59
59
  return unless ret[:title]
60
60
 
61
- ret[:title] = array(ret[:title]).reduce([]) do |m, t|
61
+ ret[:title] = array(ret[:title])
62
+ .reduce(TypedTitleStringCollection.new) do |m, t|
62
63
  if t.is_a?(Hash) then m << t
63
64
  else
64
65
  m + TypedTitleString.from_string(t)
@@ -139,20 +140,14 @@ module RelatonBib
139
140
  )
140
141
  end
141
142
 
142
- def biblionote_hash_to_bib(ret) # rubocop:disable Metrics/MethodLength
143
+ def biblionote_hash_to_bib(ret) # rubocop:disable Metrics/MethodLength,Metrics/AbcSize
143
144
  return unless ret[:biblionote]
144
145
 
145
146
  ret[:biblionote] = array(ret[:biblionote])
146
- (ret[:biblionote])&.each_with_index do |n, i|
147
- ret[:biblionote][i] = if n.is_a?(String)
148
- BiblioNote.new content: n
149
- else
150
- BiblioNote.new(
151
- content: n[:content], type: n[:type],
152
- language: n[:language], script: n[:script],
153
- format: n[:format]
154
- )
155
- end
147
+ .reduce(BiblioNoteCollection.new([])) do |mem, n|
148
+ mem << if n.is_a?(String) then BiblioNote.new content: n
149
+ else BiblioNote.new(n)
150
+ end
156
151
  end
157
152
  end
158
153
 
@@ -178,7 +173,7 @@ module RelatonBib
178
173
  DocumentStatus::Stage.new(**args)
179
174
  end
180
175
 
181
- def contributors_hash_to_bib(ret) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/MethodLength
176
+ def contributors_hash_to_bib(ret) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/MethodLength,Metrics/PerceivedComplexity
182
177
  return unless ret[:contributor]
183
178
 
184
179
  ret[:contributor] = array(ret[:contributor])
@@ -209,6 +204,9 @@ module RelatonBib
209
204
  org[:identifier] = array(org[:identifier])&.map do |a|
210
205
  OrgIdentifier.new(a[:type], a[:id])
211
206
  end
207
+ org[:subdivision] = array(org[:subdivision]).map do |sd|
208
+ LocalizedString.new sd
209
+ end
212
210
  org
213
211
  end
214
212
 
@@ -20,7 +20,7 @@ module RelatonBib
20
20
 
21
21
  # @return [String]
22
22
  def inspect
23
- "<#{self.class}:#{format('%#.14x', object_id << 1)} "\
23
+ "<#{self.class}:#{format('%<id>#.14x', id: object_id << 1)} "\
24
24
  "@text=\"#{@hit_collection&.text}\" "\
25
25
  "@fetched=\"#{!@fetch.nil?}\" "\
26
26
  "@fullIdentifier=\"#{@fetch&.shortref(nil)}\" "\
@@ -31,13 +31,17 @@ module RelatonBib
31
31
  raise "Not implemented"
32
32
  end
33
33
 
34
- # @param builder [Nokogiri::XML::Builder]
35
- def to_xml(builder = nil, **opts)
36
- if builder
37
- fetch.to_xml builder, **opts
34
+ # @param opts [Hash]
35
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
36
+ # @option opts [Boolean] :bibdata
37
+ # @option opts [String, Symbol] :lang language
38
+ # @return [String] XML
39
+ def to_xml(**opts)
40
+ if opts[:builder]
41
+ fetch.to_xml **opts
38
42
  else
39
43
  builder = Nokogiri::XML::Builder.new(encoding: "UTF-8") do |xml|
40
- fetch.to_xml xml, **opts
44
+ fetch.to_xml **opts.merge(builder: xml)
41
45
  end
42
46
  builder.doc.root.to_xml
43
47
  end
@@ -36,12 +36,17 @@ module RelatonBib
36
36
  self
37
37
  end
38
38
 
39
+ # @param opts [Hash]
40
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
41
+ # @option opts [Boolean] :bibdata
42
+ # @option opts [String, Symbol] :lang language
43
+ # @return [String] XML
39
44
  def to_xml(**opts)
40
45
  builder = Nokogiri::XML::Builder.new(encoding: "UTF-8") do |xml|
41
46
  xml.documents do
42
47
  @array.each do |hit|
43
48
  hit.fetch
44
- hit.to_xml xml, **opts
49
+ hit.to_xml **opts.merge(builder: xml)
45
50
  end
46
51
  end
47
52
  end
@@ -49,8 +54,8 @@ module RelatonBib
49
54
  end
50
55
 
51
56
  def select(&block)
52
- me = self.deep_dup
53
- array_dup = self.instance_variable_get(:@array).deep_dup
57
+ me = deep_dup
58
+ array_dup = instance_variable_get(:@array).deep_dup
54
59
  me.instance_variable_set(:@array, array_dup)
55
60
  array_dup.select!(&block)
56
61
  me
@@ -49,7 +49,7 @@ module RelatonBib
49
49
  end
50
50
 
51
51
  # @param builder [Nokogiri::XML::Builder]
52
- def to_xml(builder) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
52
+ def to_xml(builder) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity
53
53
  return unless content
54
54
 
55
55
  if content.is_a?(Array)
@@ -62,7 +62,7 @@ module RelatonBib
62
62
  end
63
63
 
64
64
  # @return [Hash]
65
- def to_hash # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
65
+ def to_hash # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity
66
66
  if content.is_a? String
67
67
  return content unless language || script
68
68
 
@@ -77,7 +77,7 @@ module RelatonBib
77
77
  # @param prefix [String]
78
78
  # @param count [Integer] number of elements
79
79
  # @return [String]
80
- def to_asciibib(prefix = "", count = 1) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
80
+ def to_asciibib(prefix = "", count = 1) # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity
81
81
  pref = prefix.empty? ? prefix : prefix + "."
82
82
  if content.is_a? String
83
83
  out = count > 1 ? "#{prefix}::\n" : ""
@@ -55,7 +55,7 @@ module RelatonBib
55
55
  # @return [RelatonBib::LocalizedString, NilClass]
56
56
  attr_reader :abbreviation
57
57
 
58
- # @return [RelatonBib::LocalizedString, NilClass]
58
+ # @return [Array<RelatonBib::LocalizedString>]
59
59
  attr_reader :subdivision
60
60
 
61
61
  # @return [Array<RelatonBib::OrgIdentifier>]
@@ -63,11 +63,11 @@ module RelatonBib
63
63
 
64
64
  # @param name [String, Hash, Array<String, Hash>]
65
65
  # @param abbreviation [RelatoBib::LocalizedString, String]
66
- # @param subdivision [RelatoBib::LocalizedString, String]
66
+ # @param subdivision [Array<RelatoBib::LocalizedString>]
67
67
  # @param url [String]
68
68
  # @param identifier [Array<RelatonBib::OrgIdentifier>]
69
69
  # @param contact [Array<RelatonBib::Address, RelatonBib::Contact>]
70
- def initialize(**args) # rubocop:disable Metrics/AbcSize
70
+ def initialize(**args) # rubocop:disable Metrics/AbcSize,Metrics/MethodLength
71
71
  raise ArgumentError, "missing keyword: name" unless args[:name]
72
72
 
73
73
  super(url: args[:url], contact: args.fetch(:contact, []))
@@ -79,17 +79,23 @@ module RelatonBib
79
79
  end
80
80
 
81
81
  @abbreviation = localized_string args[:abbreviation]
82
- @subdivision = localized_string args[:subdivision]
82
+ @subdivision = (args[:subdivision] || []).map do |sd|
83
+ localized_string sd
84
+ end
83
85
  @identifier = args.fetch(:identifier, [])
84
86
  end
85
87
 
86
- # @param builder [Nokogiri::XML::Builder]
87
- def to_xml(builder) # rubocop:disable Metrics/AbcSize
88
- builder.organization do
89
- name.each do |n|
90
- builder.name { |b| n.to_xml b }
91
- end
92
- builder.subdivision { |s| subdivision.to_xml s } if subdivision
88
+ # @param opts [Hash]
89
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
90
+ # @option opts [String] :lang language
91
+ def to_xml(**opts) # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity,Metrics/MethodLength
92
+ opts[:builder].organization do |builder|
93
+ nm = name.select { |n| n.language&.include? opts[:lang] }
94
+ nm = name unless nm.any?
95
+ nm.each { |n| builder.name { |b| n.to_xml b } }
96
+ sbdv = subdivision.select { |sd| sd.language&.include? opts[:lang] }
97
+ sbdv = subdivision unless sbdv.any?
98
+ sbdv.each { |sd| builder.subdivision { sd.to_xml builder } }
93
99
  builder.abbreviation { |a| abbreviation.to_xml a } if abbreviation
94
100
  builder.uri url if uri
95
101
  identifier.each { |identifier| identifier.to_xml builder }
@@ -98,23 +104,28 @@ module RelatonBib
98
104
  end
99
105
 
100
106
  # @return [Hash]
101
- def to_hash
107
+ def to_hash # rubocop:disable Metrics/AbcSize
102
108
  hash = { "name" => single_element_array(name) }
103
109
  hash["abbreviation"] = abbreviation.to_hash if abbreviation
104
110
  hash["identifier"] = single_element_array(identifier) if identifier&.any?
105
- hash["subdivision"] = subdivision.to_hash if subdivision
111
+ if subdivision&.any?
112
+ hash["subdivision"] = single_element_array(subdivision)
113
+ end
106
114
  { "organization" => hash.merge(super) }
107
115
  end
108
116
 
109
117
  # @param prefix [String]
110
118
  # @param count [Integer]
111
119
  # @return [String]
112
- def to_asciibib(prefix = "", count = 1) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
120
+ def to_asciibib(prefix = "", count = 1) # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/MethodLength
113
121
  pref = prefix.sub /\*$/, "organization"
114
122
  out = count > 1 ? "#{pref}::\m" : ""
115
123
  name.each { |n| out += n.to_asciibib "#{pref}.name", name.size }
116
124
  out += abbreviation.to_asciibib "#{pref}.abbreviation" if abbreviation
117
- out += subdivision.to_asciibib "#{pref}.subdivision" if subdivision
125
+ subdivision.each do |sd|
126
+ out += "#{pref}.subdivision::" if subdivision.size > 1
127
+ out += sd.to_asciibib "#{pref}.subdivision"
128
+ end
118
129
  identifier.each { |n| out += n.to_asciibib pref, identifier.size }
119
130
  out += super pref
120
131
  out
@@ -44,23 +44,33 @@ module RelatonBib
44
44
  @completename = args[:completename]
45
45
  end
46
46
 
47
- # @param builder [Nokogiri::XML::Builder]
48
- def to_xml(builder) # rubocop:disable Metrics/AbcSize, Metrics/MethodLength
49
- builder.name do
47
+ # @param opts [Hash]
48
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
49
+ # @option opts [String] :lang language
50
+ def to_xml(**opts) # rubocop:disable Metrics/AbcSize, Metrics/MethodLength,Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity
51
+ opts[:builder].name do |builder|
50
52
  if completename
51
53
  builder.completename { completename.to_xml builder }
52
54
  else
53
- prefix.each { |p| builder.prefix { p.to_xml builder } }
54
- forename.each { |f| builder.forename { f.to_xml builder } }
55
- initial.each { |i| builder.initial { i.to_xml builder } }
55
+ pref = prefix.select { |p| p.language&.include? opts[:lang] }
56
+ pref = prefix unless pref.any?
57
+ pref.each { |p| builder.prefix { p.to_xml builder } }
58
+ frnm = forename.select { |f| f.language&.include? opts[:lang] }
59
+ frnm = forename unless frnm.any?
60
+ frnm.each { |f| builder.forename { f.to_xml builder } }
61
+ init = initial.select { |i| i.language&.include? opts[:lang] }
62
+ init = initial unless init.any?
63
+ init.each { |i| builder.initial { i.to_xml builder } }
56
64
  builder.surname { surname.to_xml builder }
57
- addition.each { |a| builder.addition { a.to_xml builder } }
65
+ addn = addition.select { |a| a.language&.include? opts[:lang] }
66
+ addn = addition unless addn.any?
67
+ addn.each { |a| builder.addition { a.to_xml builder } }
58
68
  end
59
69
  end
60
70
  end
61
71
 
62
72
  # @return [Hash]
63
- def to_hash # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
73
+ def to_hash # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/PerceivedComplexity
64
74
  hash = {}
65
75
  hash["forename"] = single_element_array(forename) if forename&.any?
66
76
  hash["initial"] = single_element_array(initial) if initial&.any?
@@ -73,7 +83,7 @@ module RelatonBib
73
83
 
74
84
  # @param pref [String]
75
85
  # @return [String]
76
- def to_asciibib(pref) # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/MethodLength
86
+ def to_asciibib(pref) # rubocop:disable Metrics/AbcSize,Metrics/CyclomaticComplexity,Metrics/MethodLength,Metrics/PerceivedComplexity
77
87
  prf = pref.empty? ? pref : pref + "."
78
88
  prf += "name."
79
89
  out = forename.map do |fn|
@@ -170,11 +180,13 @@ module RelatonBib
170
180
  @identifier = identifier
171
181
  end
172
182
 
173
- # @param builder [Nokogiri::XML::Builder]
174
- def to_xml(builder)
175
- builder.person do
176
- name.to_xml builder
177
- affiliation.each { |a| a.to_xml builder }
183
+ # @param opts [Hash]
184
+ # @option opts [Nokogiri::XML::Builder] :builder XML builder
185
+ # @option opts [String, Symbol] :lang language
186
+ def to_xml(**opts)
187
+ opts[:builder].person do |builder|
188
+ name.to_xml **opts
189
+ affiliation.each { |a| a.to_xml **opts }
178
190
  identifier.each { |id| id.to_xml builder }
179
191
  contact.each { |contact| contact.to_xml builder }
180
192
  end
@@ -1,4 +1,70 @@
1
1
  module RelatonBib
2
+ class TypedTitleStringCollection
3
+ extend Forwardable
4
+
5
+ def_delegators :@array, :[], :first, :last, :empty?, :any?, :size,
6
+ :each, :detect, :map, :length
7
+
8
+ # @param title [Array<RelatonBib::TypedTitleString, Hash>]
9
+ def initialize(title = [])
10
+ @array = (title || []).map do |t|
11
+ t.is_a?(Hash) ? TypedTitleString.new(t) : t
12
+ end
13
+ end
14
+
15
+ # @param lang [String, nil] language code Iso639
16
+ # @return [RelatonIsoBib::TypedTitleStringCollection]
17
+ def lang(lang = nil)
18
+ if lang
19
+ TypedTitleStringCollection.new select_lang(lang)
20
+ else self
21
+ end
22
+ end
23
+
24
+ def delete_title_part!
25
+ titles.delete_if { |t| t.type == "title-part" }
26
+ end
27
+
28
+ # @return [RelatonBib::TypedTitleStringCollection]
29
+ def select
30
+ TypedTitleStringCollection.new(titles.select { |t| yield t })
31
+ end
32
+
33
+ # @param title [RelatonBib::TypedTitleString]
34
+ # @return [self]
35
+ def <<(title)
36
+ titles << title
37
+ self
38
+ end
39
+
40
+ # @param tcoll [RelatonBib::TypedTitleStringCollection]
41
+ # @return [RelatonBib::TypedTitleStringCollection]
42
+ def +(tcoll)
43
+ TypedTitleStringCollection.new titles + tcoll.titles
44
+ end
45
+
46
+ def titles
47
+ @array
48
+ end
49
+
50
+ # @param opts [Hash]
51
+ # @option opts [Nokogiri::XML::Builder] XML builder
52
+ # @option opts [String, Symbol] :lang language
53
+ def to_xml(**opts)
54
+ tl = select_lang(opts[:lang])
55
+ tl = titles unless tl.any?
56
+ tl.each { |t| opts[:builder].title { t.to_xml opts[:builder] } }
57
+ end
58
+
59
+ private
60
+
61
+ # @param lang [String]
62
+ # @return [Array<RelatonBib::TypedTitleString]
63
+ def select_lang(lang)
64
+ titles.select { |t| t.title.language&.include? lang }
65
+ end
66
+ end
67
+
2
68
  class TypedTitleString
3
69
  # @return [String]
4
70
  attr_reader :type
@@ -38,6 +104,7 @@ module RelatonBib
38
104
  end.compact
39
105
  tts << new(type: "main", content: ttls.compact.join(" - "),
40
106
  language: lang, script: script)
107
+ TypedTitleStringCollection.new tts
41
108
  end
42
109
 
43
110
  # @param title [String]
@@ -1,3 +1,3 @@
1
1
  module RelatonBib
2
- VERSION = "1.4.1".freeze
2
+ VERSION = "1.5.pre".freeze
3
3
  end
@@ -20,7 +20,7 @@ module RelatonBib
20
20
  # rubocop:disable Metrics/MethodLength, Metrics/AbcSize
21
21
 
22
22
  # @return [Hash]
23
- def item_data(bibitem) # rubocop:disable Metrics/CyclomaticComplexity
23
+ def item_data(bibitem) # rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
24
24
  ext = bibitem.at "//ext"
25
25
  {
26
26
  id: bibitem[:id]&.empty? ? nil : bibitem[:id],
@@ -75,7 +75,7 @@ module RelatonBib
75
75
  end
76
76
 
77
77
  def fetch_note(item)
78
- item.xpath("./note").map do |n|
78
+ bnotes = item.xpath("./note").map do |n|
79
79
  BiblioNote.new(
80
80
  content: n.text,
81
81
  type: n[:type],
@@ -84,6 +84,7 @@ module RelatonBib
84
84
  script: n[:script]
85
85
  )
86
86
  end
87
+ BiblioNoteCollection.new bnotes
87
88
  end
88
89
 
89
90
  def fetch_language(item)
@@ -98,7 +99,7 @@ module RelatonBib
98
99
  end
99
100
  end
100
101
 
101
- def fetch_series(item) # rubocop:disable Metrics/CyclomaticComplexity, Metrics/AbcSize, Metrics/MethodLength
102
+ def fetch_series(item) # rubocop:disable Metrics/CyclomaticComplexity,Metrics/AbcSize,Metrics/MethodLength,Metrics/PerceivedComplexity
102
103
  item.xpath("./series").reduce([]) do |mem, sr|
103
104
  abbr = sr.at "abbreviation"
104
105
  abbreviation = abbr &&
@@ -164,10 +165,15 @@ module RelatonBib
164
165
  end
165
166
  end
166
167
 
168
+ # @param item [Nokogiri::XML::Element]
169
+ # @return [RelatonBib::TypedTitleStringCollection]
167
170
  def fetch_titles(item)
168
- item.xpath("./title").map { |t| ttitle t }
171
+ ttl = item.xpath("./title").map { |t| ttitle t }
172
+ TypedTitleStringCollection.new ttl
169
173
  end
170
174
 
175
+ # @param title [Nokogiri::XML::Element]
176
+ # @return [RelatonBib::TypedTitleString]
171
177
  def ttitle(title)
172
178
  return unless title
173
179
 
@@ -224,9 +230,10 @@ module RelatonBib
224
230
  identifier = org.xpath("./identifier").map do |i|
225
231
  OrgIdentifier.new(i[:type], i.text)
226
232
  end
233
+ subdiv = org.xpath("subdivision").map &:text
227
234
  Organization.new(name: names,
228
235
  abbreviation: org.at("abbreviation")&.text,
229
- subdivision: org.at("subdivision")&.text,
236
+ subdivision: subdiv,
230
237
  url: org.at("uri")&.text,
231
238
  identifier: identifier)
232
239
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: relaton-bib
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.1
4
+ version: 1.5.pre
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ribose Inc.
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-09-20 00:00:00.000000000 Z
11
+ date: 2020-10-06 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: byebug
@@ -259,9 +259,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
259
259
  version: 2.4.0
260
260
  required_rubygems_version: !ruby/object:Gem::Requirement
261
261
  requirements:
262
- - - ">="
262
+ - - ">"
263
263
  - !ruby/object:Gem::Version
264
- version: '0'
264
+ version: 1.3.1
265
265
  requirements: []
266
266
  rubygems_version: 3.0.6
267
267
  signing_key: