mods 2.4.0 → 3.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (45) hide show
  1. checksums.yaml +5 -5
  2. data/.github/workflows/ruby.yml +24 -0
  3. data/.gitignore +1 -0
  4. data/Gemfile +0 -4
  5. data/README.md +1 -3
  6. data/lib/mods/date.rb +51 -17
  7. data/lib/mods/marc_country_codes.rb +12 -10
  8. data/lib/mods/nom_terminology.rb +110 -849
  9. data/lib/mods/reader.rb +9 -39
  10. data/lib/mods/record.rb +13 -28
  11. data/lib/mods/version.rb +1 -1
  12. data/mods.gemspec +3 -3
  13. data/spec/fixture_data/hp566jq8781.xml +334 -0
  14. data/spec/integration/parker_spec.rb +217 -0
  15. data/spec/{date_spec.rb → lib/date_spec.rb} +8 -1
  16. data/spec/lib/language_spec.rb +123 -0
  17. data/spec/lib/location_spec.rb +175 -0
  18. data/spec/lib/name_spec.rb +368 -0
  19. data/spec/lib/origin_info_spec.rb +134 -0
  20. data/spec/lib/part_spec.rb +162 -0
  21. data/spec/lib/physical_description_spec.rb +72 -0
  22. data/spec/{reader_spec.rb → lib/reader_spec.rb} +1 -41
  23. data/spec/lib/record_info_spec.rb +114 -0
  24. data/spec/lib/record_spec.rb +287 -0
  25. data/spec/lib/related_item_spec.rb +124 -0
  26. data/spec/lib/subject_spec.rb +427 -0
  27. data/spec/lib/title_spec.rb +108 -0
  28. data/spec/lib/top_level_elmnts_simple_spec.rb +169 -0
  29. data/spec/spec_helper.rb +87 -6
  30. data/spec/support/fixtures.rb +9 -0
  31. metadata +61 -43
  32. data/.coveralls.yml +0 -1
  33. data/.travis.yml +0 -6
  34. data/spec/language_spec.rb +0 -118
  35. data/spec/location_spec.rb +0 -295
  36. data/spec/name_spec.rb +0 -759
  37. data/spec/origin_info_spec.rb +0 -447
  38. data/spec/part_spec.rb +0 -471
  39. data/spec/physical_description_spec.rb +0 -144
  40. data/spec/record_info_spec.rb +0 -493
  41. data/spec/record_spec.rb +0 -356
  42. data/spec/related_item_spec.rb +0 -305
  43. data/spec/subject_spec.rb +0 -809
  44. data/spec/title_spec.rb +0 -226
  45. data/spec/top_level_elmnts_simple_spec.rb +0 -369
@@ -3,10 +3,7 @@ module Mods
3
3
  # from: http://www.loc.gov/standards/mods/v3/mods-userguide-generalapp.html
4
4
 
5
5
  # Nokogiri 1.6.6 introduced lang as a built-in attribute
6
- LANG_ATTRIBS = (Nokogiri::VERSION < "1.6.6") ?
7
- ['script', 'transliteration', 'lang'] :
8
- ['script', 'transliteration']
9
-
6
+ LANG_ATTRIBS = ['script', 'transliteration']
10
7
  LINKING_ATTRIBS = ['xlink', 'ID']
11
8
 
12
9
  DATE_ATTRIBS = ['encoding', 'point', 'keyDate', 'qualifier']
@@ -19,6 +16,13 @@ module Mods
19
16
 
20
17
  class Record
21
18
 
19
+ def with_attributes(element, attributes = [], method_mappings: { 'type' => 'type_at', 'ID' => 'id_at' })
20
+ attributes.each do |attr_name|
21
+ attr_method = method_mappings.fetch(attr_name, attr_name)
22
+ element.send attr_method, path: "@#{attr_name}", accessor: lambda { |a| a.text }
23
+ end
24
+ end
25
+
22
26
  # set the NOM terminology; WITH namespaces
23
27
  # NOTES:
24
28
  # 1. certain words, such as 'type' 'name' 'description' are reserved words in jruby or nokogiri
@@ -30,80 +34,47 @@ module Mods
30
34
  def set_terminology_ns(mods_ng_xml)
31
35
  mods_ng_xml.set_terminology(:namespaces => { 'm' => Mods::MODS_NS }) do |t|
32
36
 
33
- # FIXME: may want to deal with camelcase vs. underscore in method_missing
34
-
35
37
  # ABSTRACT -------------------------------------------------------------------------------
36
38
  t.abstract :path => '/m:mods/m:abstract'
37
39
  t._abstract :path => '//m:abstract' do |n|
38
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
39
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
40
- Mods::LANG_ATTRIBS.each { |attr_name|
41
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
42
- }
40
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel type])
43
41
  end
44
42
 
45
43
  # ACCESS_CONDITION -----------------------------------------------------------------------
46
44
  t.accessCondition :path => '/m:mods/m:accessCondition'
47
45
  t._accessCondition :path => '//m:accessCondition' do |n|
48
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
49
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
50
- Mods::LANG_ATTRIBS.each { |attr_name|
51
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
52
- }
46
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel type])
53
47
  end
54
48
 
55
49
  # CLASSIFICATION -------------------------------------------------------------------------
56
50
  t.classification :path => '/m:mods/m:classification'
57
51
  t._classification :path => '//m:classification' do |n|
58
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
59
- n.edition :path => '@edition', :accessor => lambda { |a| a.text }
60
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
61
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
62
- }
63
- Mods::LANG_ATTRIBS.each { |attr_name|
64
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
65
- }
52
+ with_attributes(n, Mods::AUTHORITY_ATTRIBS | Mods::LANG_ATTRIBS | %w[displayLabel edition])
66
53
  end
67
54
 
68
55
  # EXTENSION ------------------------------------------------------------------------------
69
56
  t.extension :path => '/m:mods/m:extension'
70
57
  t._extension :path => '//m:extension' do |n|
71
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
58
+ with_attributes(n, %w[displayLabel])
72
59
  end
73
60
 
74
61
  # GENRE ----------------------------------------------------------------------------------
75
62
  t.genre :path => '/m:mods/m:genre'
76
63
  t._genre :path => '//m:genre' do |n|
77
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
78
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
79
- n.usage :path => '@usage', :accessor => lambda { |a| a.text }
80
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
81
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
82
- }
83
- Mods::LANG_ATTRIBS.each { |attr_name|
84
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
85
- }
64
+ with_attributes(n, Mods::AUTHORITY_ATTRIBS | Mods::LANG_ATTRIBS | %w[displayLabel type usage])
86
65
  end
87
66
 
88
67
  # IDENTIIER ------------------------------------------------------------------------------
89
68
  t.identifier :path => '/m:mods/m:identifier'
90
69
  t._identifier :path => '//m:identifier' do |n|
91
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
92
- n.invalid :path => '@invalid', :accessor => lambda { |a| a.text }
93
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
94
- Mods::LANG_ATTRIBS.each { |attr_name|
95
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
96
- }
70
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel type invalid])
97
71
  end
98
72
 
99
73
  # LANGUAGE -------------------------------------------------------------------------------
100
74
  t.language :path => '/m:mods/m:language'
101
75
  t._language :path => '//m:language' do |n|
102
76
  # attributes
103
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
104
- Mods::LANG_ATTRIBS.each { |attr_name|
105
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
106
- }
77
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel])
107
78
  # child elements
108
79
  n.languageTerm :path => 'm:languageTerm'
109
80
  n.code_term :path => 'm:languageTerm[@type="code"]'
@@ -111,102 +82,97 @@ module Mods
111
82
  n.scriptTerm :path => 'm:scriptTerm'
112
83
  end
113
84
  t._languageTerm :path => '//m:languageTerm' do |lt|
114
- lt.type_at :path => '@type', :accessor => lambda { |a| a.text }
115
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
116
- lt.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
117
- }
85
+ with_attributes(lt, Mods::AUTHORITY_ATTRIBS | %w[type])
118
86
  end # t.language
119
87
 
120
88
  # LOCATION -------------------------------------------------------------------------------
121
89
  t.location :path => '/m:mods/m:location'
122
90
  t._location :path => '//m:location' do |n|
123
91
  # attributes
124
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
125
- Mods::LANG_ATTRIBS.each { |attr_name|
126
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
127
- }
92
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel])
128
93
  # child elements
129
94
  n.physicalLocation :path => 'm:physicalLocation' do |e|
130
- e.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
131
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
132
- e.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
133
- }
95
+ with_attributes(e, Mods::AUTHORITY_ATTRIBS | %w[displayLabel type])
134
96
  end
135
97
  n.shelfLocator :path => 'm:shelfLocator'
136
98
  n.url :path => 'm:url' do |e|
137
- e.dateLastAccessed :path => '@dateLastAccessed', :accessor => lambda { |a| a.text }
138
- e.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
139
- e.note :path => '@note', :accessor => lambda { |a| a.text }
140
- e.access :path => '@access', :accessor => lambda { |a| a.text }
141
- e.usage :path => '@usage', :accessor => lambda { |a| a.text }
99
+ with_attributes(e, %w[dateLastAccessed displayLabel note access usage])
100
+ end
101
+ n.holdingSimple :path => 'm:holdingSimple' do |h|
102
+ h.copyInformation path: 'm:copyInformation' do |c|
103
+ c.form path: 'm:form' do |f|
104
+ with_attributes(f, Mods::LANG_ATTRIBS | %w[type])
105
+ end
106
+ c.sub_location path: 'm:subLocation' do |s|
107
+ with_attributes(s, Mods::LANG_ATTRIBS)
108
+ end
109
+
110
+ c.shelf_locator path: 'm:shelfLocator' do |s|
111
+ with_attributes(s, Mods::LANG_ATTRIBS)
112
+ end
113
+ c.electronic_locator path: 'm:electronicLocator'
114
+ c.note path: 'm:note' do |note|
115
+ with_attributes(note, Mods::LANG_ATTRIBS | %w[displayLabel type])
116
+ end
117
+ c.enumeration_and_chronology path: 'm:enumerationAndChronology' do |e|
118
+ with_attributes(e, Mods::LANG_ATTRIBS | %w[unitType])
119
+ end
120
+ c.item_identifier path: 'm:itemIdentifier' do |i|
121
+ with_attributes(i, %w[type])
122
+ end
123
+ end
142
124
  end
143
- n.holdingSimple :path => 'm:holdingSimple'
144
125
  n.holdingExternal :path => 'm:holdingExternal'
145
126
  end # t.location
146
127
 
147
128
  # NAME ------------------------------------------------------------------------------------
148
129
  t.plain_name :path => '/m:mods/m:name'
149
- t._plain_name :path => '//m:name' do |n|
150
- Mods::Name::ATTRIBUTES.each { |attr_name|
151
- if attr_name != 'type'
152
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
153
- else
154
- n.type_at :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
155
- end
156
- }
130
+ t._plain_name :path => '(//m:name|//m:alternativeName)' do |n|
131
+ with_attributes(n, Mods::Name::ATTRIBUTES)
157
132
  # elements
158
133
  n.namePart :path => 'm:namePart' do |np|
159
- np.type_at :path => '@type', :accessor => lambda { |a| a.text }
134
+ with_attributes(np, %w[type])
160
135
  end
161
136
  n.family_name :path => 'm:namePart[@type="family"]'
162
137
  n.given_name :path => 'm:namePart[@type="given"]'
163
138
  n.termsOfAddress :path => 'm:namePart[@type="termsOfAddress"]'
164
139
  n.date :path => 'm:namePart[@type="date"]'
165
140
 
141
+ n.alternative_name :path => 'm:alternativeName' do |alt|
142
+ with_attributes(alt, %w[altType])
143
+ end
166
144
  n.displayForm :path => 'm:displayForm'
167
145
  n.affiliation :path => 'm:affiliation'
168
146
  n.description_el :path => 'm:description' # description is used by Nokogiri
169
147
  n.role :path => 'm:role' do |r|
170
148
  r.roleTerm :path => 'm:roleTerm' do |rt|
171
- rt.type_at :path => "@type", :accessor => lambda { |a| a.text }
172
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
173
- rt.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
174
- }
149
+ with_attributes(rt, Mods::AUTHORITY_ATTRIBS | %w[type])
150
+
151
+ rt.value path: '.', single: true, accessor: (lambda do |roleTerm|
152
+ text = roleTerm.text.strip
153
+
154
+ if roleTerm.type_at == 'code' && roleTerm.authority == 'marcrelator'
155
+ MARC_RELATOR.fetch(text, text)
156
+ else
157
+ text
158
+ end
159
+ end)
175
160
  end
161
+
176
162
  # role convenience method
177
163
  r.authority :path => '.', :accessor => lambda { |role_node|
178
- a = nil
179
- role_node.roleTerm.each { |role_t|
180
- # role_t.authority will be [] if it is missing from an earlier roleTerm
181
- if role_t.authority && (!a || a.size == 0)
182
- a = role_t.authority
183
- end
184
- }
185
- a
164
+ role_node.roleTerm.authority.first
186
165
  }
166
+
187
167
  # role convenience method
188
168
  r.code :path => '.', :accessor => lambda { |role_node|
189
- c = nil
190
- role_node.roleTerm.each { |role_t|
191
- if role_t.type_at == 'code'
192
- c ||= role_t.text
193
- end
194
- }
195
- c
169
+ role_node.roleTerm.select { |role_t| role_t.type_at == 'code' }.first&.text
196
170
  }
171
+
197
172
  # role convenience method
198
173
  r.value :path => '.', :accessor => lambda { |role_node|
199
- val = nil
200
- role_node.roleTerm.each { |role_t|
201
- if role_t.type_at == 'text'
202
- val ||= role_t.text
203
- end
204
- }
205
- # FIXME: this is broken if there are multiple role codes and some of them are not marcrelator
206
- if !val && role_node.code && role_node.authority.first =~ /marcrelator/
207
- val = MARC_RELATOR[role_node.code.first]
208
- end
209
- val
174
+ val = role_node.roleTerm.select { |role_t| role_t.type_at == 'text' }.first&.text
175
+ val || role_node.roleTerm.select { |role_t| role_t.type_at == 'code' && role_t.authority.match?(/marcrelator/) }.first&.value
210
176
  }
211
177
  end # role node
212
178
 
@@ -274,12 +240,7 @@ module Mods
274
240
  # NOTE ---------------------------------------------------------------------------------
275
241
  t.note :path => '/m:mods/m:note'
276
242
  t._note :path => '//m:note' do |n|
277
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
278
- n.id_at :path => '@ID', :accessor => lambda { |a| a.text }
279
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
280
- Mods::LANG_ATTRIBS.each { |attr_name|
281
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
282
- }
243
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[ID displayLabel type])
283
244
  end
284
245
 
285
246
  # ORIGIN_INFO --------------------------------------------------------------------------
@@ -287,38 +248,27 @@ module Mods
287
248
  t._origin_info :path => '//m:originInfo' do |n|
288
249
  n.as_object :path => '.', :accessor => lambda { |a| Mods::OriginInfo.new(a) }
289
250
  # attributes
290
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
291
- Mods::LANG_ATTRIBS.each { |attr_name|
292
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
293
- }
251
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel])
294
252
  # child elements
295
253
  n.place :path => 'm:place' do |e|
296
254
  e.placeTerm :path => 'm:placeTerm' do |ee|
297
- ee.type_at :path => '@type', :accessor => lambda { |a| a.text }
298
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
299
- ee.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
300
- }
255
+ with_attributes(ee, Mods::AUTHORITY_ATTRIBS | %w[type])
301
256
  end
302
257
  end
303
258
  n.publisher :path => 'm:publisher'
304
259
  Mods::OriginInfo::DATE_ELEMENTS.each { |date_el|
305
260
  n.send date_el, :path => "m:#{date_el}" do |d|
306
- d.as_object :path => '.', :accessor => lambda { |a| Mods::Date.from_element(a) }
261
+ d.as_object :path => '.', :single => true, :accessor => lambda { |a| Mods::Date.from_element(a) }
307
262
 
308
- Mods::DATE_ATTRIBS.each { |attr_name|
309
- d.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
310
- }
311
- if date_el == 'dateOther'
312
- d.type_at :path => '@type', :accessor => lambda { |a| a.text }
313
- end
263
+ with_attributes(d, Mods::DATE_ATTRIBS)
264
+
265
+ with_attributes(d, %w[type]) if date_el == 'dateOther'
314
266
  end
315
267
  }
316
268
  n.edition :path => 'm:edition'
317
269
  n.issuance :path => 'm:issuance'
318
270
  n.frequency :path => 'm:frequency' do |f|
319
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
320
- f.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
321
- }
271
+ with_attributes(f, Mods::AUTHORITY_ATTRIBS)
322
272
  end
323
273
  end # t.origin_info
324
274
 
@@ -326,18 +276,11 @@ module Mods
326
276
  t.part :path => '/m:mods/m:part'
327
277
  t._part :path => '//m:part' do |n|
328
278
  # attributes
329
- n.id_at :path => '@ID', :accessor => lambda { |a| a.text }
330
- n.order :path => '@order', :accessor => lambda { |a| a.text }
331
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
332
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
333
- Mods::LANG_ATTRIBS.each { |attr_name|
334
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
335
- }
279
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[ID order type displayLabel])
336
280
  # child elements
337
281
  n.detail :path => 'm:detail' do |e|
338
282
  # attributes
339
- e.level :path => '@level', :accessor => lambda { |a| a.text }
340
- e.type_at :path => '@type', :accessor => lambda { |a| a.text }
283
+ with_attributes(e, %w[level type])
341
284
  # elements
342
285
  e.number :path => 'm:number'
343
286
  e.caption :path => 'm:caption'
@@ -345,7 +288,7 @@ module Mods
345
288
  end
346
289
  n.extent :path => 'm:extent' do |e| # TODO: extent is ordered in xml schema
347
290
  # attributes
348
- e.unit :path => '@unit', :accessor => lambda { |a| a.text }
291
+ with_attributes(e, %w[unit])
349
292
  # elements
350
293
  e.start :path => 'm:start'
351
294
  e.end :path => 'm:end'
@@ -353,13 +296,10 @@ module Mods
353
296
  e.list :path => 'm:list'
354
297
  end
355
298
  n.date :path => 'm:date' do |e|
356
- Mods::DATE_ATTRIBS.reject { |a| a == 'keyDate' }.each { |attr_name|
357
- e.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
358
- }
299
+ with_attributes(e, Mods::DATE_ATTRIBS - ['keyDate'])
359
300
  end
360
301
  n.text_el :path => 'm:text' do |e|
361
- e.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
362
- e.type_at :path => '@type', :accessor => lambda { |a| a.text }
302
+ with_attributes(e, %w[displayLabel type])
363
303
  end
364
304
  end # t._part
365
305
 
@@ -367,23 +307,16 @@ module Mods
367
307
  t.physical_description :path => '/m:mods/m:physicalDescription'
368
308
  t._physical_description :path => '//m:physicalDescription' do |n|
369
309
  # attributes
370
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
371
- Mods::LANG_ATTRIBS.each { |attr_name|
372
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
373
- }
310
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel])
374
311
  # child elements
375
312
  n.digitalOrigin :path => 'm:digitalOrigin'
376
313
  n.extent :path => 'm:extent'
377
314
  n.form :path => 'm:form' do |f|
378
- f.type_at :path => '@type', :accessor => lambda { |a| a.text }
379
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
380
- f.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
381
- }
315
+ with_attributes(f, Mods::AUTHORITY_ATTRIBS | %w[type])
382
316
  end
383
317
  n.internetMediaType :path => 'm:internetMediaType'
384
318
  n.note :path => 'm:note' do |nn|
385
- nn.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
386
- nn.type_at :path => '@type', :accessor => lambda { |a| a.text }
319
+ with_attributes(nn, %w[displayLabel type])
387
320
  end
388
321
  n.reformattingQuality :path => 'm:reformattingQuality'
389
322
  end
@@ -392,52 +325,37 @@ module Mods
392
325
  t.record_info :path => '/m:mods/m:recordInfo'
393
326
  t._record_info :path => '//m:recordInfo' do |n|
394
327
  # attributes
395
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
396
- Mods::LANG_ATTRIBS.each { |attr_name|
397
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
398
- }
328
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel])
399
329
  # child elements
400
330
  n.recordContentSource :path => 'm:recordContentSource' do |r|
401
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
402
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
403
- }
331
+ with_attributes(r, Mods::AUTHORITY_ATTRIBS)
404
332
  end
405
333
  n.recordCreationDate :path => 'm:recordCreationDate' do |r|
406
- Mods::DATE_ATTRIBS.each { |attr_name|
407
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
408
- }
334
+ with_attributes(r, Mods::DATE_ATTRIBS)
409
335
  end
410
336
  n.recordChangeDate :path => 'm:recordChangeDate' do |r|
411
- Mods::DATE_ATTRIBS.each { |attr_name|
412
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
413
- }
337
+ with_attributes(r, Mods::DATE_ATTRIBS)
414
338
  end
415
339
  n.recordIdentifier :path => 'm:recordIdentifier' do |r|
416
- r.source :path => '@source', :accessor => lambda { |a| a.text }
340
+ with_attributes(r, ['source'])
417
341
  end
418
342
  n.recordOrigin :path => 'm:recordOrigin'
419
343
  n.languageOfCataloging :path => 'm:languageOfCataloging' do |r|
420
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
421
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
422
- }
344
+ with_attributes(r, Mods::AUTHORITY_ATTRIBS)
423
345
  r.languageTerm :path => 'm:languageTerm'
424
346
  r.scriptTerm :path => 'm:scriptTerm'
425
347
  end
426
348
  n.descriptionStandard :path => 'm:descriptionStandard' do |r|
427
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
428
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
429
- }
349
+ with_attributes(r, Mods::AUTHORITY_ATTRIBS)
430
350
  end
431
351
  end # t._record_info
432
352
 
433
353
  # RELATED_ITEM-------------------------------------------------------------------------
434
354
  t.related_item :path => '/m:mods/m:relatedItem' do |n|
435
355
  # attributes
436
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
437
- n.id_at :path => '@ID', :accessor => lambda { |a| a.text }
438
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
356
+ with_attributes(n, %w[ID displayLabel type])
439
357
  # elements
440
- n.abstract :path => 'abstract'
358
+ n.abstract :path => 'm:abstract'
441
359
  n.accessCondition :path => 'm:accessCondition'
442
360
  n.classification :path => 'm:classification'
443
361
  n.extension :path => 'm:extension'
@@ -465,13 +383,7 @@ module Mods
465
383
  t.subject :path => '/m:mods/m:subject'
466
384
  t._subject :path => '//m:subject' do |n|
467
385
  # attributes
468
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
469
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
470
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
471
- }
472
- Mods::LANG_ATTRIBS.each { |attr_name|
473
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
474
- }
386
+ with_attributes(n, Mods::AUTHORITY_ATTRIBS | Mods::LANG_ATTRIBS | %w[displayLabel])
475
387
  # child elements
476
388
  n.cartographics :path => 'm:cartographics' do |n1|
477
389
  n1.scale :path => 'm:scale'
@@ -482,19 +394,13 @@ module Mods
482
394
  }
483
395
  end
484
396
  n.genre :path => 'm:genre' do |n1|
485
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
486
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
487
- }
397
+ with_attributes(n1, Mods::AUTHORITY_ATTRIBS)
488
398
  end
489
399
  n.geographic :path => 'm:geographic' do |n1|
490
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
491
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
492
- }
400
+ with_attributes(n1, Mods::AUTHORITY_ATTRIBS)
493
401
  end
494
402
  n.geographicCode :path => 'm:geographicCode' do |gc|
495
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
496
- gc.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
497
- }
403
+ with_attributes(gc, Mods::AUTHORITY_ATTRIBS)
498
404
  # convenience method
499
405
  gc.translated_value :path => '.', :accessor => lambda { |gc_node|
500
406
  code_val ||= gc_node.text
@@ -514,78 +420,45 @@ module Mods
514
420
  Mods::Subject::HIER_GEO_CHILD_ELEMENTS.each { |elname|
515
421
  n1.send elname, :path => "m:#{elname}"
516
422
  }
517
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
518
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
519
- }
423
+ with_attributes(n1, Mods::AUTHORITY_ATTRIBS)
520
424
  end
521
425
  # Note: 'name' is used by Nokogiri
522
426
  n.name_el :path => 'm:name' do |t1|
523
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
524
- t1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
525
- }
427
+ with_attributes(t1, Mods::AUTHORITY_ATTRIBS)
526
428
  end
527
429
  n.personal_name :path => 'm:name[@type="personal"]'
528
430
  n.corporate_name :path => 'm:name[@type="corporate"]'
529
431
  n.conference_name :path => 'm:name[@type="conference"]'
530
432
  n.occupation :path => 'm:occupation' do |n1|
531
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
532
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
533
- }
433
+ with_attributes(n1, Mods::AUTHORITY_ATTRIBS)
534
434
  end
535
435
  n.temporal :path => 'm:temporal' do |n1|
536
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
537
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
538
- }
539
- # date attributes as attributes
540
- Mods::DATE_ATTRIBS.each { |attr_name|
541
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
542
- }
436
+ with_attributes(n1, Mods::AUTHORITY_ATTRIBS | Mods::DATE_ATTRIBS)
543
437
  end
544
438
  n.titleInfo :path => 'm:titleInfo' do |t1|
545
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
546
- t1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
547
- }
439
+ with_attributes(t1, Mods::AUTHORITY_ATTRIBS)
548
440
  end
549
441
  n.topic :path => 'm:topic' do |n1|
550
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
551
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
552
- }
442
+ with_attributes(n1, Mods::AUTHORITY_ATTRIBS)
553
443
  end
554
444
  end # t.subject
555
445
 
556
446
  # TABLE_OF_CONTENTS ---------------------------------------------------------------------
557
447
  t.tableOfContents :path => '/m:mods/m:tableOfContents'
558
448
  t._tableOfContents :path => '//m:tableOfContents' do |n|
559
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
560
- n.shareable :path => '@shareable', :accessor => lambda { |a| a.text }
561
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
562
- Mods::LANG_ATTRIBS.each { |attr_name|
563
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
564
- }
449
+ with_attributes(n, Mods::LANG_ATTRIBS | %w[displayLabel shareable type])
565
450
  end
566
451
 
567
452
  # TARGET_AUDIENCE -----------------------------------------------------------------------
568
453
  t.targetAudience :path => '/m:mods/m:targetAudience'
569
454
  t._targetAudience :path => '//m:targetAudience' do |n|
570
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
571
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
572
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
573
- }
574
- Mods::LANG_ATTRIBS.each { |attr_name|
575
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
576
- }
455
+ with_attributes(n, Mods::AUTHORITY_ATTRIBS | Mods::LANG_ATTRIBS | %w[displayLabel])
577
456
  end
578
457
 
579
458
  # TITLE_INFO ----------------------------------------------------------------------------
580
459
  t.title_info :path => '/m:mods/m:titleInfo'
581
460
  t._title_info :path => '//m:titleInfo' do |n|
582
- Mods::TitleInfo::ATTRIBUTES.each { |attr_name|
583
- if attr_name != 'type'
584
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
585
- else
586
- n.type_at :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
587
- end
588
- }
461
+ with_attributes(n, Mods::TitleInfo::ATTRIBUTES)
589
462
  n.title :path => 'm:title'
590
463
  n.subTitle :path => 'm:subTitle'
591
464
  n.nonSort :path => 'm:nonSort'
@@ -623,624 +496,12 @@ module Mods
623
496
  # TYPE_OF_RESOURCE --------------------------------------------------------------------
624
497
  t.typeOfResource :path => '/m:mods/m:typeOfResource'
625
498
  t._typeOfResource :path => '//m:typeOfResource' do |n|
626
- n.collection :path => '@collection', :accessor => lambda { |a| a.text }
627
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
628
- n.manuscript :path => '@manuscript', :accessor => lambda { |a| a.text }
629
- n.usage :path => '@usage', :accessor => lambda { |a| a.text }
499
+ with_attributes(n, %w[collection displayLabel manuscript usage])
630
500
  end
631
-
632
- end # terminology
501
+ end
633
502
 
634
503
  mods_ng_xml.nom!
635
504
  mods_ng_xml
636
- end # set_terminology_ns
637
-
638
- # set the NOM terminology; do NOT use namespaces
639
- # NOTES:
640
- # 1. certain words, such as 'type' 'name' 'description' are reserved words in jruby or nokogiri
641
- # when the terminology would use these words, a suffix of '_at' is added if it is an attribute,
642
- # (e.g. 'type_at' for @type) and a suffix of '_el' is added if it is an element.
643
- # 2. the underscore prefix variant terms are a way of making subterms for a node available
644
- # to any instance of said node and are not intended to be used externally
645
- # @param mods_ng_xml a Nokogiri::Xml::Document object containing MODS (without namespaces)
646
- def set_terminology_no_ns(mods_ng_xml)
647
- mods_ng_xml.set_terminology() do |t|
648
-
649
- # FIXME: may want to deal with camelcase vs. underscore in method_missing
650
-
651
- # ABSTRACT -------------------------------------------------------------------------------
652
- t.abstract :path => '/mods/abstract'
653
- t._abstract :path => '//abstract' do |n|
654
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
655
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
656
- Mods::LANG_ATTRIBS.each { |attr_name|
657
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
658
- }
659
- end
660
-
661
- # ACCESS_CONDITION -----------------------------------------------------------------------
662
- t.accessCondition :path => '/mods/accessCondition'
663
- t._accessCondition :path => '//accessCondition' do |n|
664
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
665
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
666
- Mods::LANG_ATTRIBS.each { |attr_name|
667
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
668
- }
669
- end
670
-
671
- # CLASSIFICATION -------------------------------------------------------------------------
672
- t.classification :path => '/mods/classification'
673
- t._classification :path => '//classification' do |n|
674
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
675
- n.edition :path => '@edition', :accessor => lambda { |a| a.text }
676
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
677
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
678
- }
679
- Mods::LANG_ATTRIBS.each { |attr_name|
680
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
681
- }
682
- end
683
-
684
- # EXTENSION ------------------------------------------------------------------------------
685
- t.extension :path => '/mods/extension'
686
- t._extension :path => '//extension' do |n|
687
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
688
- end
689
-
690
- # GENRE ----------------------------------------------------------------------------------
691
- t.genre :path => '/mods/genre'
692
- t._genre :path => '//genre' do |n|
693
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
694
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
695
- n.usage :path => '@usage', :accessor => lambda { |a| a.text }
696
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
697
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
698
- }
699
- Mods::LANG_ATTRIBS.each { |attr_name|
700
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
701
- }
702
- end
703
-
704
- # IDENTIIER ------------------------------------------------------------------------------
705
- t.identifier :path => '/mods/identifier'
706
- t._identifier :path => '//identifier' do |n|
707
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
708
- n.invalid :path => '@invalid', :accessor => lambda { |a| a.text }
709
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
710
- Mods::LANG_ATTRIBS.each { |attr_name|
711
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
712
- }
713
- end
714
-
715
- # LANGUAGE -------------------------------------------------------------------------------
716
- t.language :path => '/mods/language'
717
- t._language :path => '//language' do |n|
718
- # attributes
719
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
720
- Mods::LANG_ATTRIBS.each { |attr_name|
721
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
722
- }
723
- # child elements
724
- n.languageTerm :path => 'languageTerm'
725
- n.code_term :path => 'languageTerm[@type="code"]'
726
- n.text_term :path => 'languageTerm[@type="text"]'
727
- n.scriptTerm :path => 'scriptTerm'
728
- end
729
- t._languageTerm :path => '//languageTerm' do |lt|
730
- lt.type_at :path => '@type', :accessor => lambda { |a| a.text }
731
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
732
- lt.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
733
- }
734
- end # t.language
735
-
736
- # LOCATION -------------------------------------------------------------------------------
737
- t.location :path => '/mods/location'
738
- t._location :path => '//location' do |n|
739
- # attributes
740
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
741
- Mods::LANG_ATTRIBS.each { |attr_name|
742
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
743
- }
744
- # child elements
745
- n.physicalLocation :path => 'physicalLocation' do |e|
746
- e.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
747
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
748
- e.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
749
- }
750
- end
751
- n.shelfLocator :path => 'shelfLocator'
752
- n.url :path => 'url' do |e|
753
- e.dateLastAccessed :path => '@dateLastAccessed', :accessor => lambda { |a| a.text }
754
- e.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
755
- e.note :path => '@note', :accessor => lambda { |a| a.text }
756
- e.access :path => '@access', :accessor => lambda { |a| a.text }
757
- e.usage :path => '@usage', :accessor => lambda { |a| a.text }
758
- end
759
- n.holdingSimple :path => 'holdingSimple'
760
- n.holdingExternal :path => 'holdingExternal'
761
- end # t.location
762
-
763
- # NAME ------------------------------------------------------------------------------------
764
- t.plain_name :path => '/mods/name'
765
- t._plain_name :path => '//name' do |n|
766
- Mods::Name::ATTRIBUTES.each { |attr_name|
767
- if attr_name != 'type'
768
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
769
- else
770
- n.type_at :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
771
- end
772
- }
773
- # elements
774
- n.namePart :path => 'namePart' do |np|
775
- np.type_at :path => '@type', :accessor => lambda { |a| a.text }
776
- end
777
- n.family_name :path => 'namePart[@type="family"]'
778
- n.given_name :path => 'namePart[@type="given"]'
779
- n.termsOfAddress :path => 'namePart[@type="termsOfAddress"]'
780
- n.date :path => 'namePart[@type="date"]'
781
-
782
- n.displayForm :path => 'displayForm'
783
- n.affiliation :path => 'affiliation'
784
- n.description_el :path => 'description' # description is used by Nokogiri
785
- n.role :path => 'role' do |r|
786
- r.roleTerm :path => 'roleTerm' do |rt|
787
- rt.type_at :path => "@type", :accessor => lambda { |a| a.text }
788
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
789
- rt.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
790
- }
791
- end
792
- # convenience method
793
- r.authority :path => '.', :accessor => lambda { |role_node|
794
- a = nil
795
- role_node.roleTerm.each { |role_t|
796
- # role_t.authority will be [] if it is missing from an earlier roleTerm
797
- if role_t.authority && (!a || a.size == 0)
798
- a = role_t.authority
799
- end
800
- }
801
- a
802
- }
803
- # convenience method
804
- r.code :path => '.', :accessor => lambda { |role_node|
805
- c = nil
806
- role_node.roleTerm.each { |role_t|
807
- if role_t.type_at == 'code'
808
- c ||= role_t.text
809
- end
810
- }
811
- c
812
- }
813
- # convenience method
814
- r.value :path => '.', :accessor => lambda { |role_node|
815
- val = nil
816
- role_node.roleTerm.each { |role_t|
817
- if role_t.type_at == 'text'
818
- val ||= role_t.text
819
- end
820
- }
821
- # FIXME: this is broken if there are multiple role codes and some of them are not marcrelator
822
- if !val && role_node.code && role_node.authority.first =~ /marcrelator/
823
- val = MARC_RELATOR[role_node.code.first]
824
- end
825
- val
826
- }
827
- end # role node
828
-
829
- # name convenience method
830
- # uses the displayForm of a name if present
831
- # if no displayForm, try to make a string from family, given and terms of address
832
- # otherwise, return all non-date nameParts concatenated together
833
- n.display_value :path => '.', :single => true, :accessor => lambda {|name_node|
834
- dv = ''
835
- if name_node.displayForm && name_node.displayForm.text.size > 0
836
- dv = name_node.displayForm.text
837
- end
838
- if dv.empty?
839
- if name_node.type_at == 'personal'
840
- if name_node.family_name.size > 0
841
- dv = name_node.given_name.size > 0 ? "#{name_node.family_name.text}, #{name_node.given_name.text}" : name_node.family_name.text
842
- elsif name_node.given_name.size > 0
843
- dv = name_node.given_name.text
844
- end
845
- if !dv.empty?
846
- first = true
847
- name_node.namePart.each { |np|
848
- if np.type_at == 'termsOfAddress' && !np.text.empty?
849
- if first
850
- dv = dv + " " + np.text
851
- first = false
852
- else
853
- dv = dv + ", " + np.text
854
- end
855
- end
856
- }
857
- else # no family or given name
858
- dv = name_node.namePart.select {|np| np.type_at != 'date' && !np.text.empty?}.join(" ")
859
- end
860
- else # not a personal name
861
- dv = name_node.namePart.select {|np| np.type_at != 'date' && !np.text.empty?}.join(" ")
862
- end
863
- end
864
- dv.strip.empty? ? nil : dv.strip
865
- }
866
-
867
- # name convenience method
868
- n.display_value_w_date :path => '.', :single => true, :accessor => lambda {|name_node|
869
- dv = '' + name_node.display_value
870
- name_node.namePart.each { |np|
871
- if np.type_at == 'date' && !np.text.empty? && !dv.end_with?(np.text)
872
- dv = dv + ", #{np.text}"
873
- end
874
- }
875
- if dv.start_with?(', ')
876
- dv.sub(', ', '')
877
- end
878
- dv.strip.empty? ? nil : dv.strip
879
- }
880
- end # t._plain_name
881
-
882
- t.personal_name :path => '/mods/name[@type="personal"]'
883
- t._personal_name :path => '//name[@type="personal"]'
884
- t.corporate_name :path => '/mods/name[@type="corporate"]'
885
- t._corporate_name :path => '//name[@type="corporate"]'
886
- t.conference_name :path => '/mods/name[@type="conference"]'
887
- t._conference_name :path => '//name[@type="conference"]'
888
-
889
- # NOTE ---------------------------------------------------------------------------------
890
- t.note :path => '/mods/note'
891
- t._note :path => '//note' do |n|
892
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
893
- n.id_at :path => '@ID', :accessor => lambda { |a| a.text }
894
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
895
- Mods::LANG_ATTRIBS.each { |attr_name|
896
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
897
- }
898
- end
899
-
900
- # ORIGIN_INFO --------------------------------------------------------------------------
901
- t.origin_info :path => '/mods/originInfo'
902
- t._origin_info :path => '//originInfo' do |n|
903
- # attributes
904
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
905
- Mods::LANG_ATTRIBS.each { |attr_name|
906
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
907
- }
908
- # child elements
909
- n.place :path => 'place' do |e|
910
- e.placeTerm :path => 'placeTerm' do |ee|
911
- ee.type_at :path => '@type', :accessor => lambda { |a| a.text }
912
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
913
- ee.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
914
- }
915
- end
916
- end
917
- n.publisher :path => 'publisher'
918
- Mods::OriginInfo::DATE_ELEMENTS.each { |date_el|
919
- n.send date_el, :path => "#{date_el}" do |d|
920
- Mods::DATE_ATTRIBS.each { |attr_name|
921
- d.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
922
- }
923
- if date_el == 'dateOther'
924
- d.type_at :path => '@type', :accessor => lambda { |a| a.text }
925
- end
926
- end
927
- }
928
- n.edition :path => 'edition'
929
- n.issuance :path => 'issuance'
930
- n.frequency :path => 'frequency' do |f|
931
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
932
- f.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
933
- }
934
- end
935
- end # t.origin_info
936
-
937
- # PART -----------------------------------------------------------------------------------
938
- t.part :path => '/mods/part'
939
- t._part :path => '//part' do |n|
940
- # attributes
941
- n.id_at :path => '@ID', :accessor => lambda { |a| a.text }
942
- n.order :path => '@order', :accessor => lambda { |a| a.text }
943
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
944
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
945
- Mods::LANG_ATTRIBS.each { |attr_name|
946
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
947
- }
948
- # child elements
949
- n.detail :path => 'detail' do |e|
950
- # attributes
951
- e.level :path => '@level', :accessor => lambda { |a| a.text }
952
- e.type_at :path => '@type', :accessor => lambda { |a| a.text }
953
- # elements
954
- e.number :path => 'number'
955
- e.caption :path => 'caption'
956
- e.title :path => 'title'
957
- end
958
- n.extent :path => 'extent' do |e| # TODO: extent is ordered in xml schema
959
- # attributes
960
- e.unit :path => '@unit', :accessor => lambda { |a| a.text }
961
- # elements
962
- e.start :path => 'start'
963
- e.end :path => 'end'
964
- e.total :path => 'total'
965
- e.list :path => 'list'
966
- end
967
- n.date :path => 'date' do |e|
968
- Mods::DATE_ATTRIBS.reject { |a| a == 'keyDate' }.each { |attr_name|
969
- e.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
970
- }
971
- end
972
- n.text_el :path => 'text' do |e|
973
- e.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
974
- e.type_at :path => '@type', :accessor => lambda { |a| a.text }
975
- end
976
- end # t._part
977
-
978
- # PHYSICAL_DESCRIPTION -------------------------------------------------------------------
979
- t.physical_description :path => '/mods/physicalDescription'
980
- t._physical_description :path => '//physicalDescription' do |n|
981
- # attributes
982
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
983
- Mods::LANG_ATTRIBS.each { |attr_name|
984
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
985
- }
986
- # child elements
987
- n.digitalOrigin :path => 'digitalOrigin'
988
- n.extent :path => 'extent'
989
- n.form :path => 'form' do |f|
990
- f.type_at :path => '@type', :accessor => lambda { |a| a.text }
991
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
992
- f.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
993
- }
994
- end
995
- n.internetMediaType :path => 'internetMediaType'
996
- n.note :path => 'note' do |nn|
997
- nn.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
998
- nn.type_at :path => '@type', :accessor => lambda { |a| a.text }
999
- end
1000
- n.reformattingQuality :path => 'reformattingQuality'
1001
- end
1002
-
1003
- # RECORD_INFO --------------------------------------------------------------------------
1004
- t.record_info :path => '/mods/recordInfo'
1005
- t._record_info :path => '//recordInfo' do |n|
1006
- # attributes
1007
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
1008
- Mods::LANG_ATTRIBS.each { |attr_name|
1009
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1010
- }
1011
- # child elements
1012
- n.recordContentSource :path => 'recordContentSource' do |r|
1013
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1014
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1015
- }
1016
- end
1017
- n.recordCreationDate :path => 'recordCreationDate' do |r|
1018
- Mods::DATE_ATTRIBS.each { |attr_name|
1019
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1020
- }
1021
- end
1022
- n.recordChangeDate :path => 'recordChangeDate' do |r|
1023
- Mods::DATE_ATTRIBS.each { |attr_name|
1024
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1025
- }
1026
- end
1027
- n.recordIdentifier :path => 'recordIdentifier' do |r|
1028
- r.source :path => '@source', :accessor => lambda { |a| a.text }
1029
- end
1030
- n.recordOrigin :path => 'recordOrigin'
1031
- n.languageOfCataloging :path => 'languageOfCataloging' do |r|
1032
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1033
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1034
- }
1035
- r.languageTerm :path => 'languageTerm'
1036
- r.scriptTerm :path => 'scriptTerm'
1037
- end
1038
- n.descriptionStandard :path => 'descriptionStandard' do |r|
1039
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1040
- r.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1041
- }
1042
- end
1043
- end # t._record_info
1044
-
1045
- # RELATED_ITEM-------------------------------------------------------------------------
1046
- t.related_item :path => '/mods/relatedItem' do |n|
1047
- # attributes
1048
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
1049
- n.id_at :path => '@ID', :accessor => lambda { |a| a.text }
1050
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
1051
- # elements
1052
- n.abstract :path => 'abstract'
1053
- n.accessCondition :path => 'accessCondition'
1054
- n.classification :path => 'classification'
1055
- n.extension :path => 'extension'
1056
- n.genre :path => 'genre'
1057
- n.identifier :path => 'identifier'
1058
- n.language :path => 'language'
1059
- n.location :path => 'location'
1060
- n.name_el :path => 'name' # Note: 'name' is used by Nokogiri
1061
- n.personal_name :path => 'name[@type="personal"]'
1062
- n.corporate_name :path => 'name[@type="corporate"]'
1063
- n.conference_name :path => 'name[@type="conference"]'
1064
- n.note :path => 'note'
1065
- n.originInfo :path => 'originInfo'
1066
- n.part :path => 'part'
1067
- n.physicalDescription :path => 'physicalDescription'
1068
- n.recordInfo :path => 'recordInfo'
1069
- n.subject :path => 'subject'
1070
- n.tableOfContents :path => 'tableOfContents'
1071
- n.targetAudience :path => 'targetAudience'
1072
- n.titleInfo :path => 'titleInfo'
1073
- n.typeOfResource :path => 'typeOfResource'
1074
- end
1075
-
1076
- # SUBJECT -----------------------------------------------------------------------------
1077
- t.subject :path => '/mods/subject'
1078
- t._subject :path => '//subject' do |n|
1079
- # attributes
1080
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
1081
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1082
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1083
- }
1084
- Mods::LANG_ATTRIBS.each { |attr_name|
1085
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1086
- }
1087
- # child elements
1088
- n.cartographics :path => 'cartographics' do |n1|
1089
- n1.scale :path => 'scale'
1090
- n1.projection :path => 'projection'
1091
- n1.coordinates :path => 'coordinates'
1092
- Mods::Subject::CARTOGRAPHICS_CHILD_ELEMENTS.each { |elname|
1093
- n1.send elname, :path => "#{elname}"
1094
- }
1095
- end
1096
- n.geographic :path => 'geographic' do |n1|
1097
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1098
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1099
- }
1100
- end
1101
- n.genre :path => 'genre' do |n1|
1102
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1103
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1104
- }
1105
- end
1106
- n.geographicCode :path => 'geographicCode' do |gc|
1107
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1108
- gc.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1109
- }
1110
- # convenience method
1111
- gc.translated_value :path => '.', :accessor => lambda { |gc_node|
1112
- code_val ||= gc_node.text
1113
- xval = nil
1114
- if code_val
1115
- case gc_node.authority
1116
- when 'marcgac'
1117
- xval = MARC_GEOGRAPHIC_AREA[code_val]
1118
- when 'marccountry'
1119
- xval = MARC_COUNTRY[code_val]
1120
- end
1121
- end
1122
- xval
1123
- }
1124
- end
1125
- n.hierarchicalGeographic :path => 'hierarchicalGeographic' do |n1|
1126
- Mods::Subject::HIER_GEO_CHILD_ELEMENTS.each { |elname|
1127
- n1.send elname, :path => "#{elname}"
1128
- }
1129
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1130
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1131
- }
1132
- end
1133
- # Note: 'name' is used by Nokogiri
1134
- n.name_el :path => 'name' do |t1|
1135
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1136
- t1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1137
- }
1138
- end
1139
- n.personal_name :path => 'name[@type="personal"]'
1140
- n.corporate_name :path => 'name[@type="corporate"]'
1141
- n.conference_name :path => 'name[@type="conference"]'
1142
- n.occupation :path => 'occupation' do |n1|
1143
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1144
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1145
- }
1146
- end
1147
- n.temporal :path => 'temporal' do |n1|
1148
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1149
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1150
- }
1151
- # date attributes as attributes
1152
- Mods::DATE_ATTRIBS.each { |attr_name|
1153
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1154
- }
1155
- end
1156
- n.titleInfo :path => 'titleInfo' do |t1|
1157
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1158
- t1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1159
- }
1160
- end
1161
- n.topic :path => 'topic' do |n1|
1162
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1163
- n1.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1164
- }
1165
- end
1166
- end # t.subject
1167
-
1168
- # TABLE_OF_CONTENTS ---------------------------------------------------------------------
1169
- t.tableOfContents :path => '/mods/tableOfContents'
1170
- t._tableOfContents :path => '//tableOfContents' do |n|
1171
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
1172
- n.shareable :path => '@shareable', :accessor => lambda { |a| a.text }
1173
- n.type_at :path => '@type', :accessor => lambda { |a| a.text }
1174
- Mods::LANG_ATTRIBS.each { |attr_name|
1175
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1176
- }
1177
- end
1178
-
1179
- # TARGET_AUDIENCE -----------------------------------------------------------------------
1180
- t.targetAudience :path => '/mods/targetAudience'
1181
- t._targetAudience :path => '//targetAudience' do |n|
1182
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
1183
- Mods::AUTHORITY_ATTRIBS.each { |attr_name|
1184
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1185
- }
1186
- Mods::LANG_ATTRIBS.each { |attr_name|
1187
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1188
- }
1189
- end
1190
-
1191
- # TITLE_INFO ----------------------------------------------------------------------------
1192
- t.title_info :path => '/mods/titleInfo'
1193
- t._title_info :path => '//titleInfo' do |n|
1194
- Mods::TitleInfo::ATTRIBUTES.each { |attr_name|
1195
- if attr_name != 'type'
1196
- n.send attr_name, :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1197
- else
1198
- n.type_at :path => "@#{attr_name}", :accessor => lambda { |a| a.text }
1199
- end
1200
- }
1201
- n.title :path => 'title'
1202
- n.subTitle :path => 'subTitle'
1203
- n.nonSort :path => 'nonSort'
1204
- n.partNumber :path => 'partNumber'
1205
- n.partName :path => 'partName'
1206
- n.sort_title :path => '.', :accessor => lambda { |node|
1207
- if node.type_at != "alternative" || (node.type_at == "alternative" && mods_ng_xml.xpath('/mods/titleInfo').size == 1)
1208
- node.title.text + (!node.subTitle.text.empty? ? "#{@title_delimiter}#{node.subTitle.text}" : "" )
1209
- end
1210
- }
1211
- n.full_title :path => '.', :accessor => lambda { |node|
1212
- (!node.nonSort.text.empty? ? "#{node.nonSort.text} " : "" ) +
1213
- node.title.text +
1214
- (!node.subTitle.text.empty? ? "#{@title_delimiter}#{node.subTitle.text}" : "" )
1215
- }
1216
- n.short_title :path => '.', :accessor => lambda { |node|
1217
- if node.type_at != "alternative"
1218
- (!node.nonSort.text.empty? ? "#{node.nonSort.text} " : "" ) +
1219
- node.title.text
1220
- end
1221
- }
1222
- n.alternative_title :path => '.', :accessor => lambda { |node|
1223
- if node.type_at == "alternative"
1224
- (!node.nonSort.text.empty? ? "#{node.nonSort.text} " : "" ) +
1225
- node.title.text
1226
- end
1227
- }
1228
- end # t._title_info
1229
-
1230
- # TYPE_OF_RESOURCE --------------------------------------------------------------------
1231
- t.typeOfResource :path => '/mods/typeOfResource'
1232
- t._typeOfResource :path => '//typeOfResource' do |n|
1233
- n.collection :path => '@collection', :accessor => lambda { |a| a.text }
1234
- n.displayLabel :path => '@displayLabel', :accessor => lambda { |a| a.text }
1235
- n.manuscript :path => '@manuscript', :accessor => lambda { |a| a.text }
1236
- n.usage :path => '@usage', :accessor => lambda { |a| a.text }
1237
- end
1238
-
1239
- end # terminology
1240
-
1241
- mods_ng_xml.nom!
1242
- mods_ng_xml
1243
- end # set_terminology_no_ns
1244
-
1245
- end # Record class
1246
- end # Mods module
505
+ end
506
+ end
507
+ end