pennmarc 1.0.0 → 1.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (38) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +3 -0
  3. data/.rubocop_todo.yml +37 -21
  4. data/Gemfile.lock +3 -0
  5. data/README.md +12 -2
  6. data/lib/pennmarc/helpers/creator.rb +24 -20
  7. data/lib/pennmarc/helpers/edition.rb +15 -13
  8. data/lib/pennmarc/helpers/format.rb +3 -3
  9. data/lib/pennmarc/helpers/genre.rb +5 -4
  10. data/lib/pennmarc/helpers/helper.rb +1 -0
  11. data/lib/pennmarc/helpers/identifier.rb +32 -15
  12. data/lib/pennmarc/helpers/language.rb +3 -3
  13. data/lib/pennmarc/helpers/location.rb +10 -10
  14. data/lib/pennmarc/helpers/note.rb +0 -2
  15. data/lib/pennmarc/helpers/relation.rb +7 -7
  16. data/lib/pennmarc/helpers/series.rb +19 -31
  17. data/lib/pennmarc/helpers/subject.rb +11 -11
  18. data/lib/pennmarc/helpers/title.rb +1 -1
  19. data/lib/pennmarc/mappers.rb +31 -0
  20. data/lib/pennmarc/parser.rb +36 -62
  21. data/lib/pennmarc/util.rb +10 -11
  22. data/lib/pennmarc/version.rb +5 -0
  23. data/pennmarc.gemspec +5 -1
  24. data/spec/lib/pennmarc/helpers/creator_spec.rb +9 -9
  25. data/spec/lib/pennmarc/helpers/edition_spec.rb +3 -2
  26. data/spec/lib/pennmarc/helpers/format_spec.rb +1 -1
  27. data/spec/lib/pennmarc/helpers/genre_spec.rb +1 -1
  28. data/spec/lib/pennmarc/helpers/identifer_spec.rb +43 -14
  29. data/spec/lib/pennmarc/helpers/language_spec.rb +1 -1
  30. data/spec/lib/pennmarc/helpers/location_spec.rb +8 -8
  31. data/spec/lib/pennmarc/helpers/relation_spec.rb +2 -2
  32. data/spec/lib/pennmarc/helpers/series_spec.rb +6 -5
  33. data/spec/lib/pennmarc/helpers/subject_spec.rb +1 -1
  34. data/spec/lib/pennmarc/parser_spec.rb +22 -1
  35. metadata +7 -8
  36. data/legacy/indexer.rb +0 -568
  37. data/legacy/marc.rb +0 -2964
  38. data/legacy/test_file_output.json +0 -49
@@ -4,7 +4,6 @@ module PennMARC
4
4
  # Do Series and series-related field processing. Many of these fields are added entries that are justified by
5
5
  # corresponding series statements (usually 490). These fields provide information about the published series in which
6
6
  # a book, encoded finding aid, or other published work has appeared
7
- # @todo We may want to include 410 in the display tags, since it is included in references below.
8
7
  class Series < Helper
9
8
  class << self
10
9
  # 800 - Series Added Entry-Personal Name - https://www.loc.gov/marc/bibliographic/bd800.html
@@ -16,17 +15,17 @@ module PennMARC
16
15
  # 411 - Series Statement/Added Entry Meeting Name - https://www.loc.gov/marc/bibliographic/bd411.html
17
16
  # 440 - Series Statement/Added Entry-Title - https://www.loc.gov/marc/bibliographic/bd440.html
18
17
  # 490 - Series Statement - https://www.loc.gov/marc/bibliographic/bd490.html
19
- DISPLAY_TAGS = %w[800 810 811 830 400 411 440 490].freeze
18
+ DISPLAY_TAGS = %w[800 810 811 830 400 410 411 440 490].freeze
20
19
 
21
20
  # Fields for display that pertain to series information.
22
21
  # @param [MARC::Record] record
23
- # @param [Hash] relator_mapping
22
+ # @param [Hash] relator_map
24
23
  # @return [Array<String>] array of series information
25
- def show(record, relator_mapping = relator_map)
24
+ def show(record, relator_map: Mappers.relator)
26
25
  tags_present = DISPLAY_TAGS.select { |tag| record[tag].present? }
27
26
 
28
27
  values = if %w[800 810 811 400 410 411].member?(tags_present.first)
29
- author_show_entries(record, tags_present.first, relator_mapping)
28
+ author_show_entries(record, tags_present.first, relator_map)
30
29
  elsif %w[830 440 490].member?(tags_present.first)
31
30
  title_show_entries(record, tags_present.first)
32
31
  end || []
@@ -37,14 +36,14 @@ module PennMARC
37
36
 
38
37
  # Values from series fields for display.
39
38
  # @param [MARC::Record] record
40
- # @param [Hash] relator_mapping
39
+ # @param [Hash] relator_map
41
40
  # @return [Array<String>] array of series values
42
- def values(record, relator_mapping = relator_map)
41
+ def values(record, relator_map: Mappers.relator)
43
42
  series_8x = record.fields(%w[800 810 811 830]).first
44
- return Array.wrap(series_8xx_field(series_8x, relator_mapping)) if series_8x
43
+ return Array.wrap(series_field(series_8x, relator_map)) if series_8x
45
44
 
46
45
  series_4x = record.fields(%w[400 410 411 440 490]).first
47
- return Array.wrap(series_4xx_field(series_4x, relator_mapping)) if series_4x
46
+ Array.wrap(series_field(series_4x, relator_map)) if series_4x
48
47
  end
49
48
 
50
49
  # Series fields for search.
@@ -111,8 +110,9 @@ module PennMARC
111
110
  def author_show_entries(record, first_tag, relator_mapping)
112
111
  record.fields(first_tag).map do |field|
113
112
  series = join_subfields(field, &subfield_not_in?(%w[0 5 6 8 e t w v n]))
113
+ author_show_subfields = %w[e w v n t]
114
114
  pairs = field.map do |sf|
115
- if %w[e w v n t].member?(sf.code)
115
+ if author_show_subfields.member?(sf.code)
116
116
  [' ', sf.value]
117
117
  elsif sf.code == '4'
118
118
  [', ', translate_relator(sf.value, relator_mapping)]
@@ -164,31 +164,19 @@ module PennMARC
164
164
  end || []
165
165
  end
166
166
 
167
- # Assemble a formatted string of a given 8xx field.
168
- # @note added 2017/04/10: filter out 0 (authority record numbers) added by Alma
169
- # @param [String] field
170
- # @param [Hash] relator_mapping
171
- # @return [String] series 8xx field
172
- def series_8xx_field(field, relator_mapping)
173
- s = field.filter_map { |sf|
174
- if %w[0 4 5 6 8].exclude?(sf.code)
175
- " #{sf.value}"
176
- elsif sf.code == '4'
177
- ", #{translate_relator(sf.value, relator_mapping)}"
178
- end
179
- }.join
180
- s2 = s + (%w[. -].exclude?(s[-1]) ? '.' : '')
181
- s2.squish
182
- end
183
-
184
- # Assemble a formatted string of a given 4xx field.
167
+ # Assemble a formatted string of a given field.
185
168
  # @note added 2017/04/10: filter out 0 (authority record numbers) added by Alma
186
- # @param [String] field
169
+ # @param [MARC::Field] field
187
170
  # @param [Hash] relator_mapping
188
171
  # @return [String] series 4xx field
189
- def series_4xx_field(field, relator_mapping)
172
+ def series_field(field, relator_mapping)
173
+ subfields = if field.tag.start_with? '4'
174
+ %w[0 4 6 8]
175
+ else
176
+ %w[0 4 5 6 8]
177
+ end
190
178
  s = field.filter_map { |sf|
191
- if %w[0 4 6 8].exclude?(sf.code)
179
+ if subfields.exclude?(sf.code)
192
180
  " #{sf.value}"
193
181
  elsif sf.code == '4'
194
182
  ", #{translate_relator(sf.value, relator_mapping)}"
@@ -26,14 +26,14 @@ module PennMARC
26
26
  # Local subject heading tags
27
27
  LOCAL_TAGS = %w[690 691 697].freeze
28
28
 
29
- # All Subjects for searching. This includes most subfield content from any field contained in {SEARCH_TAGS} or 69X,
30
- # including any linked 880 fields. Fields must have an indicator2 value in {SEARCH_SOURCE_INDICATORS}.
29
+ # All Subjects for searching. This includes most subfield content from any field contained in {SEARCH_TAGS} or
30
+ # 69X, including any linked 880 fields. Fields must have an indicator2 value in {SEARCH_SOURCE_INDICATORS}.
31
31
  # @todo this includes subfields that may not be desired like 1 (uri) and 2 (source code) but this might be OK for
32
32
  # a search (non-display) field?
33
- # @param [Hash] relator_mapping
33
+ # @param [Hash] relator_map
34
34
  # @param [MARC::Record] record
35
35
  # @return [Array] array of all subject values for search
36
- def search(record, relator_mapping = relator_map)
36
+ def search(record, relator_map: Mappers.relator)
37
37
  subject_fields(record, type: :search).filter_map do |field|
38
38
  subj_parts = field.filter_map do |subfield|
39
39
  # TODO: use term hash here? pro/chr would be rejected...
@@ -45,10 +45,9 @@ module PennMARC
45
45
  # remove any ? at the end
46
46
  subfield.value.gsub(/^%?(PRO|CHR)/, '').gsub(/\?$/, '').strip
47
47
  when '4'
48
- # TODO: use relation mapping method from Title helper? for potential URI support?
49
48
  # sf 4 should contain a 3-letter code or URI "that specifies the relationship from the entity described
50
49
  # in the record to the entity referenced in the field"
51
- "#{subfield.value} #{relator_mapping[subfield.value.to_sym]}".strip
50
+ "#{subfield.value} #{translate_relator(subfield.value.to_sym, relator_map)}".strip
52
51
  else
53
52
  subfield.value
54
53
  end
@@ -169,7 +168,8 @@ module PennMARC
169
168
  def format_term(type:, term:)
170
169
  return unless type.in? %i[facet display]
171
170
 
172
- normalize_single_subfield(term[:parts].first) if term[:count] == 1
171
+ # attempt to handle poorly coded record
172
+ normalize_single_subfield(term[:parts].first) if term[:count] == 1 && term[:parts].first.present?
173
173
 
174
174
  case type.to_sym
175
175
  when :facet
@@ -183,7 +183,7 @@ module PennMARC
183
183
  # @param [MARC::DataField] field
184
184
  # @return [Boolean] whether a MARC field is intended for display under general "Subjects"
185
185
  def subject_general_display_field?(field)
186
- return false unless field.tag.in? DISPLAY_TAGS + LOCAL_TAGS
186
+ return false unless field.tag.in?(DISPLAY_TAGS + LOCAL_TAGS) && field.respond_to?(:indicator2)
187
187
 
188
188
  return false if field.indicator2 == '7' && !valid_subject_genre_source_code?(field)
189
189
 
@@ -200,7 +200,7 @@ module PennMARC
200
200
  # @param [Hash] options include :tags and :indicator2 values
201
201
  # @return [Boolean] whether a MARC field should be considered for display
202
202
  def subject_display_field?(field, options)
203
- return false if field.blank?
203
+ return false unless field.respond_to?(:indicator2)
204
204
 
205
205
  return true if field.tag.in?(options[:tags]) && field.indicator2.in?(options[:indicator2])
206
206
 
@@ -210,7 +210,7 @@ module PennMARC
210
210
  # @param [MARC::DataField] field
211
211
  # @return [Boolean]
212
212
  def subject_facet_field?(field)
213
- return false if field.blank?
213
+ return false unless field.respond_to?(:indicator2)
214
214
 
215
215
  return true if field.tag.in?(DISPLAY_TAGS) && field.indicator2.in?(%w[0 2 4])
216
216
 
@@ -269,7 +269,7 @@ module PennMARC
269
269
  # @param [MARC::DataField] field
270
270
  # @return [Boolean]
271
271
  def subject_search_field?(field)
272
- return false if field.blank? || SEARCH_SOURCE_INDICATORS.exclude?(field.indicator2)
272
+ return false unless field.respond_to?(:indicator2) && SEARCH_SOURCE_INDICATORS.include?(field.indicator2)
273
273
 
274
274
  tag = if field.tag == '880'
275
275
  subfield_values(field, '6').first
@@ -89,7 +89,7 @@ module PennMARC
89
89
  end
90
90
  raw_title = join_subfields(title_field, &subfield_in?(['a'])) # get title from subfield a
91
91
  value = if offset.between?(1, 9)
92
- { prefix: raw_title[0..offset - 1].strip, filing: raw_title[offset..].strip }
92
+ { prefix: raw_title[0..offset - 1]&.strip, filing: raw_title[offset..]&.strip }
93
93
  elsif raw_title.present?
94
94
  handle_bracket_prefix raw_title
95
95
  else
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+
3
+ module PennMARC
4
+ # reusable static mappers
5
+ class Mappers
6
+ class << self
7
+ # @return [Hash]
8
+ def language
9
+ @language ||= load_map('language.yml')
10
+ end
11
+
12
+ # @return [Hash]
13
+ def location
14
+ @location ||= load_map('locations.yml')
15
+ end
16
+
17
+ # @return [Hash]
18
+ def relator
19
+ @relator ||= load_map('relator.yml')
20
+ end
21
+
22
+ # @param [String] filename of mapping file in config directory, with file extension
23
+ # @return [Hash] mapping as hash
24
+ def load_map(filename)
25
+ puts { "Loading #{filename}" }
26
+ YAML.safe_load(File.read(File.join(File.expand_path(__dir__), 'mappings', filename)),
27
+ symbolize_names: true)
28
+ end
29
+ end
30
+ end
31
+ end
@@ -2,79 +2,53 @@
2
2
 
3
3
  require 'active_support/all'
4
4
  require_relative 'helpers/helper'
5
- require_relative 'helpers/creator'
6
- require_relative 'helpers/database'
7
- require_relative 'helpers/date'
8
- require_relative 'helpers/format'
9
- require_relative 'helpers/genre'
10
- require_relative 'helpers/identifier'
11
- require_relative 'helpers/language'
12
- require_relative 'helpers/link'
13
- require_relative 'helpers/location'
14
- require_relative 'helpers/subject'
15
- require_relative 'helpers/title'
16
- require_relative 'helpers/citation'
17
- require_relative 'helpers/relation'
18
- require_relative 'helpers/production'
19
- require_relative 'helpers/edition'
20
- require_relative 'helpers/note'
21
- require_relative 'helpers/series'
5
+
6
+ # Require all files in helpers directory
7
+ # TODO: this double-requires Helper, but that needs to be required before other helpers...
8
+ Dir[File.join(__dir__, 'helpers', '*.rb')].each { |file| require file }
22
9
 
23
10
  # Top level gem namespace
24
11
  module PennMARC
25
- attr_accessor :mappings
26
-
27
- DEFINED_HELPERS = %w[Creator Database Date Format Genre Language Link Location Subject Title Relation].freeze
28
-
29
- # Methods here should return values used in the indexer. The parsing logic should
30
- # NOT return values specific to any particular site/interface, but just general
31
- # MARC parsing logic for "title", "subject", "author", etc., as much as reasonably
32
- # possible. We'll see how it goes.
33
- #
34
- # Methods should, by default, take in a MARC::Record
12
+ # Access point for magic calls to helper methods
35
13
  class Parser
36
- def initialize(helpers: DEFINED_HELPERS)
37
- @mappings = {}
38
- @helpers = Array.wrap(helpers) # TODO: load helpers dynamically?
14
+ # Allow calls to `respond_to?` on parser instances to respond accurately by checking helper classes
15
+ # @param [String, Symbol] name
16
+ # @return [Boolean]
17
+ def respond_to_missing?(name, include_private = false)
18
+ helper, method_name = parse_call(name)
19
+ begin
20
+ "PennMARC::#{helper}".constantize.respond_to?(method_name)
21
+ rescue NameError
22
+ super # Helper is not defined, so check self
23
+ end
39
24
  end
40
25
 
41
- def respond_to_missing?(name)
42
- name.split('_').first.in? @helpers
43
- end
44
-
45
- # Call helper class methods, e.g.,
26
+ # Call helper class methods, passing along additional arguments as needed, e.g.:
46
27
  # #title_show -> PennMARC::Title.show
47
28
  # #subject_facet -> PennMARC::Subject.facet
48
- def method_missing(name, opts)
49
- call = name.to_s.split('_')
50
- helper = call.shift
51
- meth = call.join('_')
52
- "PennMARC::#{helper.titleize}".constantize.public_send(meth, opts)
29
+ # @param [Symbol] name
30
+ # @param [MARC::Record] record
31
+ # @param [Array] opts
32
+ def method_missing(name, record, *opts)
33
+ helper, method_name = parse_call(name)
34
+ raise NoMethodError unless helper && method_name
35
+
36
+ helper_klass = "PennMARC::#{helper.titleize}".constantize
37
+ if opts.any?
38
+ helper_klass.public_send(method_name, record, **opts.first)
39
+ else
40
+ helper_klass.public_send(method_name, record)
41
+ end
53
42
  end
54
43
 
55
- # Load language map from YAML and memoize in @mappings hash
56
- # @return [Hash]
57
- def language_map
58
- @mappings[:language] ||= load_map('language.yml')
59
- end
60
-
61
- # Load location map from YAML and memoize in @mappings hash
62
- # @return [Hash]
63
- def location_map
64
- @mappings[:location] ||= load_map('locations.yml')
65
- end
44
+ private
66
45
 
67
- # Load relator map from YAML and memoize in @mappings hash
68
- # @return [Hash]
69
- def relator_map
70
- @mappings[:relator] ||= load_map('relator.yml')
71
- end
72
-
73
- # @param [String] filename of mapping file in config directory, with file extension
74
- # @return [Hash] mapping as hash
75
- def load_map(filename)
76
- YAML.safe_load(File.read(File.join(File.expand_path(__dir__), 'mappings', filename)),
77
- symbolize_names: true)
46
+ # Parse out a method call name in the way method_missing is configured to handle
47
+ # @param [String, Symbol] name
48
+ # @return [Array]
49
+ def parse_call(name)
50
+ call = name.to_s.split('_')
51
+ [call.shift&.titleize, call.join('_').to_sym]
78
52
  end
79
53
  end
80
54
  end
data/lib/pennmarc/util.rb CHANGED
@@ -9,8 +9,10 @@ module PennMARC
9
9
  # @param [MARC::DataField] field
10
10
  # @param [Proc] selector
11
11
  # @return [String]
12
- def join_subfields(field, &)
13
- field.select(&).filter_map { |sf|
12
+ def join_subfields(field, &selector)
13
+ return '' unless field
14
+
15
+ field.select(&selector).filter_map { |sf|
14
16
  value = sf.value&.strip
15
17
  next if value.blank?
16
18
 
@@ -26,7 +28,7 @@ module PennMARC
26
28
  # @param [Regexp] regex
27
29
  # @return [TrueClass, FalseClass]
28
30
  def subfield_value?(field, subfield, regex)
29
- field.any? { |sf| sf.code == subfield.to_s && sf.value =~ regex }
31
+ field&.any? { |sf| sf.code == subfield.to_s && sf.value =~ regex }
30
32
  end
31
33
 
32
34
  # returns true if a given field has a given subfield value in a given array
@@ -49,7 +51,6 @@ module PennMARC
49
51
  end
50
52
 
51
53
  # returns a lambda checking if passed-in subfield's code is a member of array
52
- # TODO: include lambda returning methods in their own module?
53
54
  # @param [Array] array
54
55
  # @return [Proc]
55
56
  def subfield_in?(array)
@@ -57,7 +58,6 @@ module PennMARC
57
58
  end
58
59
 
59
60
  # returns a lambda checking if passed-in subfield's code is NOT a member of array
60
- # TODO: include lambda returning methods in their own module?
61
61
  # @param [Array] array
62
62
  # @return [Proc]
63
63
  def subfield_not_in?(array)
@@ -124,16 +124,15 @@ module PennMARC
124
124
  # See: https://www.loc.gov/marc/bibliographic/bd880.html
125
125
  # @param [MARC::Record] record
126
126
  # @param [String|Array] subfield6_value either a string to look for in sub6 or an array of them
127
- # @param selector [Proc] takes a subfield as argument, returns a boolean
127
+ # @param [Proc] selector takes a subfield as argument, returns a boolean
128
128
  # @return [Array] array of linked alternates
129
- def linked_alternate(record, subfield6_value, &)
129
+ def linked_alternate(record, subfield6_value, &selector)
130
130
  record.fields('880').filter_map do |field|
131
131
  next unless subfield_value?(field, '6', /^#{Array.wrap(subfield6_value).join('|')}/)
132
132
 
133
- field.select(&).map(&:value).join(' ')
133
+ field.select(&selector).map(&:value).join(' ')
134
134
  end
135
135
  end
136
- alias get_880 linked_alternate
137
136
 
138
137
  # Common case of wanting to extract all the subfields besides 6 or 8,
139
138
  # from 880 datafield that has a particular subfield 6 value. We exclude 6 because
@@ -142,8 +141,9 @@ module PennMARC
142
141
  # @param [String|Array] subfield6_value either a string to look for in sub6 or an array of them
143
142
  # @return [Array] array of linked alternates without 8 or 6 values
144
143
  def linked_alternate_not_6_or_8(record, subfield6_value)
144
+ excluded_subfields = %w[6 8]
145
145
  linked_alternate(record, subfield6_value) do |sf|
146
- %w[6 8].exclude?(sf.code)
146
+ excluded_subfields.exclude?(sf.code)
147
147
  end
148
148
  end
149
149
 
@@ -179,7 +179,6 @@ module PennMARC
179
179
  def join_and_squish(array)
180
180
  array.join(' ').squish
181
181
  end
182
- alias join_and_trim_whitespace join_and_squish
183
182
 
184
183
  # If there's a subfield i, extract its value, and if there's something
185
184
  # in parentheses in that value, extract that.
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ module PennMARC
4
+ VERSION = '1.0.2'
5
+ end
data/pennmarc.gemspec CHANGED
@@ -1,8 +1,12 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ lib = File.expand_path('lib', __dir__)
4
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
5
+ require 'pennmarc/version'
6
+
3
7
  Gem::Specification.new do |s|
4
8
  s.name = 'pennmarc'
5
- s.version = '1.0.0'
9
+ s.version = PennMARC::VERSION
6
10
  s.summary = 'Penn Libraries Catalog MARC parsing wisdom for cross-project usage'
7
11
  s.description = 'This gem provides methods for parsing a Penn Libraries MARCXML record into string, array and date
8
12
  objects for use in discovery or preservation applications.'
@@ -17,9 +17,9 @@ describe 'PennMARC::Creator' do
17
17
  end
18
18
 
19
19
  it 'contains the expected search field values for a single author work' do
20
- expect(helper.search(record, mapping)).to eq ['Name Surname http://cool.uri/12345 author 1900-2000.',
21
- 'Surname, Name http://cool.uri/12345 author 1900-2000.',
22
- 'Alternative Surname']
20
+ expect(helper.search(record, relator_map: mapping)).to eq ['Name Surname http://cool.uri/12345 author 1900-2000.',
21
+ 'Surname, Name http://cool.uri/12345 author 1900-2000.',
22
+ 'Alternative Surname']
23
23
  end
24
24
  end
25
25
 
@@ -30,8 +30,8 @@ describe 'PennMARC::Creator' do
30
30
  end
31
31
 
32
32
  it 'contains the expected search field values for a corporate author work' do
33
- expect(helper.search(record, mapping)).to eq ['Group of People Annual Meeting Author.',
34
- 'Alt. Group Name Alt. Annual Meeting']
33
+ expect(helper.search(record, relator_map: mapping)).to eq ['Group of People Annual Meeting Author.',
34
+ 'Alt. Group Name Alt. Annual Meeting']
35
35
  end
36
36
  end
37
37
  end
@@ -46,7 +46,7 @@ describe 'PennMARC::Creator' do
46
46
  end
47
47
 
48
48
  it 'returns values for the author, including mapped relator code from ǂ4' do
49
- values = helper.values(record, mapping)
49
+ values = helper.values(record, relator_map: mapping)
50
50
  expect(values).to contain_exactly 'Author Fancy active 24th century AD, Author.'
51
51
  expect(values.join.downcase).not_to include 'alt'
52
52
  end
@@ -58,7 +58,7 @@ describe 'PennMARC::Creator' do
58
58
  end
59
59
 
60
60
  it 'returns values for the corporate author, including mapped relator code from ǂ4' do
61
- expect(helper.values(record, mapping)).to contain_exactly 'Annual Report Leader author, Author.'
61
+ expect(helper.values(record, relator_map: mapping)).to contain_exactly 'Annual Report Leader author, Author.'
62
62
  end
63
63
  end
64
64
  end
@@ -160,7 +160,7 @@ describe 'PennMARC::Creator' do
160
160
  end
161
161
 
162
162
  it 'returns conference name information for display, ignoring any linked 880 fields' do
163
- expect(helper.conference_show(record, mapping)).to eq ['MARC History Symposium, Author.']
163
+ expect(helper.conference_show(record, relator_map: mapping)).to eq ['MARC History Symposium, Author.']
164
164
  end
165
165
  end
166
166
 
@@ -204,7 +204,7 @@ describe 'PennMARC::Creator' do
204
204
  end
205
205
 
206
206
  it 'returns expected contributor values' do
207
- expect(helper.contributor_show(record, mapping)).to contain_exactly(
207
+ expect(helper.contributor_show(record, relator_map: mapping)).to contain_exactly(
208
208
  'Name I laureate 1968 pseud Fuller Name author affiliation materials, Author',
209
209
  'Corporation A division Office 1968 author affiliation materials, Author',
210
210
  'Alt Name Alt num Alt title Alt date Alt qualifier Alt Fuller Name Alt relator Alt affiliation Alt materials',
@@ -28,8 +28,9 @@ describe 'PennMARC::Edition' do
28
28
 
29
29
  describe '.other_show' do
30
30
  it 'returns other edition values' do
31
- expect(helper.other_show(record, mapping)).to contain_exactly('Autre Editione',
32
- 'Other Edition: Author. (Cool Book)')
31
+ expect(helper.other_show(record, relator_map: mapping)).to(
32
+ contain_exactly('Autre Editione', 'Other Edition: Author. (Cool Book)')
33
+ )
33
34
  end
34
35
  end
35
36
  end
@@ -7,7 +7,7 @@ describe 'PennMARC::Format' do
7
7
 
8
8
  describe '.facet' do
9
9
  let(:map) { location_map }
10
- let(:formats) { helper.facet(record, map) }
10
+ let(:formats) { helper.facet(record, location_map: map) }
11
11
 
12
12
  context 'with an "Archive"' do
13
13
  let(:map) do
@@ -43,7 +43,7 @@ describe 'PennMARC::Genre' do
43
43
  end
44
44
 
45
45
  describe '.facet' do
46
- let(:values) { helper.facet(record, location_map) }
46
+ let(:values) { helper.facet(record, location_map: location_map) }
47
47
  let(:location_map) do
48
48
  { manu: { specific_location: 'Secure Manuscripts Storage' },
49
49
  vanp: { specific_location: 'Van Pelt' } }
@@ -16,13 +16,14 @@ describe 'PennMARC::Identifier' do
16
16
  describe '.isxn_search' do
17
17
  let(:record) do
18
18
  marc_record fields: [
19
- marc_field(tag: '020', subfields: { a: '9781594205071', z: '1594205078' }),
20
- marc_field(tag: '022', subfields: { a: '0008-6533', l: '0300-7162', z: '0008-6533' })
19
+ marc_field(tag: '020', subfields: { a: '9781594205071', z: '1555975275' }),
20
+ marc_field(tag: '022', subfields: { a: '0008-6533', l: '0300-7162', z: '0799-5946 ' })
21
21
  ]
22
22
  end
23
23
 
24
24
  it 'returns expected search values' do
25
- expect(helper.isxn_search(record)).to contain_exactly('9781594205071', '1594205078', '0300-7162', '0008-6533')
25
+ expect(helper.isxn_search(record)).to contain_exactly('9781594205071', '1555975275', '9781555975272',
26
+ '1594205078', '0300-7162', '0008-6533', '0799-5946 ')
26
27
  end
27
28
 
28
29
  it 'converts ISBN10 values to ISBN13' do
@@ -40,9 +41,9 @@ describe 'PennMARC::Identifier' do
40
41
  ]
41
42
  end
42
43
 
43
- it 'returns expected show values' do
44
- expect(helper.isbn_show(record)).to contain_exactly('9781594205071 1594205078', '0805073698 9780735222786',
45
- '0735222789 9780805073690')
44
+ it 'returns expected ǂa values' do
45
+ expect(helper.isbn_show(record)).to contain_exactly('9781594205071', '0805073698',
46
+ '0735222789')
46
47
  end
47
48
  end
48
49
 
@@ -55,9 +56,9 @@ describe 'PennMARC::Identifier' do
55
56
  ]
56
57
  end
57
58
 
58
- it 'returns expected show values' do
59
- expect(helper.issn_show(record)).to contain_exactly('0008-6533 0008-6533', '2470-6302 1534-6714',
60
- '1080-6512 2213-4360')
59
+ it 'returns ǂa values' do
60
+ expect(helper.issn_show(record)).to contain_exactly('0008-6533', '2470-6302',
61
+ '1080-6512')
61
62
  end
62
63
  end
63
64
 
@@ -79,9 +80,11 @@ describe 'PennMARC::Identifier' do
79
80
  let(:record) do
80
81
  marc_record fields: [
81
82
  marc_field(tag: '024', subfields: { a: '602537854325', '6': '880-01' }),
83
+ marc_field(tag: '024', subfields: { a: '10.18574/9781479842865', '2': 'doi' }),
82
84
  marc_field(tag: '028', subfields: { a: 'B002086600', b: 'Island Def Jam Music Group', '6': '880-01' }),
83
85
  marc_field(tag: '880', subfields: { a: '523458735206', '6': '024' }),
84
- marc_field(tag: '880', subfields: { a: '006680200B', b: 'Island', '6': '028' })
86
+ marc_field(tag: '880', subfields: { a: '006680200B', b: 'Island', '6': '028' }),
87
+ marc_field(tag: '880', subfields: { a: '006680200B', b: 'Island', '6': '021' })
85
88
  ]
86
89
  end
87
90
 
@@ -90,18 +93,26 @@ describe 'PennMARC::Identifier' do
90
93
  'B002086600 Island Def Jam Music Group',
91
94
  '523458735206', '006680200B Island')
92
95
  end
96
+
97
+ it 'does not return DOI values' do
98
+ expect(helper.publisher_number_show(record)).not_to include('10.18574/9781479842865')
99
+ expect(helper.publisher_number_show(record)).not_to include('doi')
100
+
101
+ end
93
102
  end
94
103
 
95
104
  describe '.publisher_number_search' do
96
105
  let(:record) do
97
106
  marc_record fields: [
98
- marc_field(tag: '024', subfields: { a: '602537854325' }),
107
+ marc_field(tag: '024', subfields: { a: '602537854325', b: 'exclude' }),
108
+ marc_field(tag: '024', subfields: { a: '10.18574/9781479842865', '2': 'doi' }),
99
109
  marc_field(tag: '028', subfields: { a: 'B002086600', b: 'Island Def Jam Music Group' })
100
110
  ]
101
111
  end
102
112
 
103
- it 'returns expected search values' do
104
- expect(helper.publisher_number_search(record)).to contain_exactly('602537854325', 'B002086600')
113
+ it 'returns publisher numbers from 024/028 ǂa and DOI values in 024 ǂ2' do
114
+ expect(helper.publisher_number_search(record)).to contain_exactly('10.18574/9781479842865', '602537854325',
115
+ 'B002086600')
105
116
  end
106
117
  end
107
118
 
@@ -117,4 +128,22 @@ describe 'PennMARC::Identifier' do
117
128
  expect(helper.fingerprint_show(record)).to contain_exactly('dete nkck vess lodo Anno Domini MDCXXXVI 3')
118
129
  end
119
130
  end
120
- end
131
+
132
+ describe '.doi_show' do
133
+ let(:record) do
134
+ marc_record fields: [
135
+ marc_field(tag: '024', indicator1: '7', subfields: { a: '10.1038/sdata.2016.18 ', '2': 'doi' }),
136
+ marc_field(tag: '024', indicator1: '7', subfields: { a: '10.18574/9781479842865', '2': 'doi' }),
137
+ marc_field(tag: '024', indicator1: '7',
138
+ subfields: { a: '10.1016.12.31/nature.S0735-1097(98)2000/12?/31/34:7-7', '2': 'doi' }),
139
+ marc_field(tag: '024', indicator1: '7', subfields: { a: 'excluded', '2': 'non doi' }),
140
+ marc_field(tag: '024', indicator1: '0', subfields: { a: 'excluded', '2': 'doi' })
141
+ ]
142
+ end
143
+
144
+ it 'returns valid DOI values' do
145
+ expect(helper.doi_show(record)).to contain_exactly('10.1016.12.31/nature.S0735-1097(98)2000/12?/31/34:7-7',
146
+ '10.1038/sdata.2016.18', '10.18574/9781479842865')
147
+ end
148
+ end
149
+ end
@@ -18,7 +18,7 @@ describe 'PennMARC::Language' do
18
18
 
19
19
  describe '.search' do
20
20
  it 'returns the expected display value' do
21
- expect(helper.search(record, mapping)).to eq 'English'
21
+ expect(helper.search(record, language_map: mapping)).to eq 'English'
22
22
  end
23
23
  end
24
24