mods_display 0.10.0 → 1.0.0.alpha3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (91) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +2 -1
  3. data/.rubocop_todo.yml +433 -35
  4. data/README.md +0 -95
  5. data/app/components/mods_display/field_component.html.erb +13 -0
  6. data/app/components/mods_display/field_component.rb +27 -0
  7. data/app/components/mods_display/list_field_component.html.erb +11 -0
  8. data/app/components/mods_display/list_field_component.rb +10 -0
  9. data/app/components/mods_display/record_component.html.erb +5 -0
  10. data/app/components/mods_display/record_component.rb +39 -0
  11. data/app/helpers/mods_display/record_helper.rb +106 -0
  12. data/app/models/mods_display/record.rb +26 -0
  13. data/config/locales/en.yml +1 -1
  14. data/config.ru +9 -0
  15. data/lib/mods_display/engine.rb +13 -0
  16. data/lib/mods_display/fields/access_condition.rb +4 -0
  17. data/lib/mods_display/fields/contents.rb +14 -15
  18. data/lib/mods_display/fields/field.rb +13 -149
  19. data/lib/mods_display/fields/genre.rb +4 -0
  20. data/lib/mods_display/fields/imprint.rb +52 -3
  21. data/lib/mods_display/fields/name.rb +11 -20
  22. data/lib/mods_display/fields/nested_related_item.rb +11 -20
  23. data/lib/mods_display/fields/note.rb +4 -0
  24. data/lib/mods_display/fields/related_item.rb +4 -0
  25. data/lib/mods_display/fields/resource_type.rb +1 -1
  26. data/lib/mods_display/fields/sub_title.rb +3 -3
  27. data/lib/mods_display/fields/subject.rb +13 -39
  28. data/lib/mods_display/fields/title.rb +4 -0
  29. data/lib/mods_display/fields/values.rb +4 -4
  30. data/lib/mods_display/html.rb +55 -106
  31. data/lib/mods_display/version.rb +1 -1
  32. data/lib/mods_display.rb +2 -17
  33. data/mods_display.gemspec +15 -9
  34. metadata +45 -105
  35. data/.github/workflows/ruby.yml +0 -24
  36. data/.gitignore +0 -21
  37. data/lib/mods_display/configuration/access_condition.rb +0 -21
  38. data/lib/mods_display/configuration/base.rb +0 -34
  39. data/lib/mods_display/configuration/genre.rb +0 -9
  40. data/lib/mods_display/configuration/imprint.rb +0 -13
  41. data/lib/mods_display/configuration/name.rb +0 -9
  42. data/lib/mods_display/configuration/note.rb +0 -9
  43. data/lib/mods_display/configuration/related_item.rb +0 -9
  44. data/lib/mods_display/configuration/subject.rb +0 -13
  45. data/lib/mods_display/configuration/title.rb +0 -9
  46. data/lib/mods_display/configuration.rb +0 -93
  47. data/lib/mods_display/controller_extension.rb +0 -32
  48. data/lib/mods_display/helpers/record_helper.rb +0 -131
  49. data/lib/mods_display/model_extension.rb +0 -22
  50. data/lib/mods_display/railtie.rb +0 -10
  51. data/spec/configuration/access_condition_spec.rb +0 -10
  52. data/spec/configuration/base_spec.rb +0 -39
  53. data/spec/fake_app.rb +0 -18
  54. data/spec/fields/abstract_spec.rb +0 -39
  55. data/spec/fields/access_condition_spec.rb +0 -107
  56. data/spec/fields/audience_spec.rb +0 -24
  57. data/spec/fields/cartographics_spec.rb +0 -38
  58. data/spec/fields/collection_spec.rb +0 -77
  59. data/spec/fields/contact_spec.rb +0 -23
  60. data/spec/fields/contents_spec.rb +0 -39
  61. data/spec/fields/description_spec.rb +0 -55
  62. data/spec/fields/extent_spec.rb +0 -31
  63. data/spec/fields/form_spec.rb +0 -49
  64. data/spec/fields/genre_spec.rb +0 -34
  65. data/spec/fields/geo_spec.rb +0 -40
  66. data/spec/fields/identifier_spec.rb +0 -61
  67. data/spec/fields/imprint_spec.rb +0 -289
  68. data/spec/fields/language_spec.rb +0 -51
  69. data/spec/fields/location_spec.rb +0 -81
  70. data/spec/fields/name_spec.rb +0 -166
  71. data/spec/fields/nested_related_item_spec.rb +0 -89
  72. data/spec/fields/note_spec.rb +0 -72
  73. data/spec/fields/related_item_spec.rb +0 -72
  74. data/spec/fields/resource_type_spec.rb +0 -34
  75. data/spec/fields/sub_title_spec.rb +0 -20
  76. data/spec/fields/subject_spec.rb +0 -113
  77. data/spec/fields/title_spec.rb +0 -82
  78. data/spec/fixtures/access_condition_fixtures.rb +0 -58
  79. data/spec/fixtures/cartographics_fixtures.rb +0 -52
  80. data/spec/fixtures/imprint_fixtures.rb +0 -349
  81. data/spec/fixtures/name_fixtures.rb +0 -398
  82. data/spec/fixtures/nested_realted_items_fixtures.rb +0 -64
  83. data/spec/fixtures/related_item_fixtures.rb +0 -107
  84. data/spec/fixtures/subjects_fixtures.rb +0 -115
  85. data/spec/fixtures/title_fixtures.rb +0 -115
  86. data/spec/helpers/record_helper_spec.rb +0 -241
  87. data/spec/integration/configuration_spec.rb +0 -57
  88. data/spec/integration/html_spec.rb +0 -87
  89. data/spec/integration/installation_spec.rb +0 -26
  90. data/spec/spec_helper.rb +0 -46
  91. data/spec/test_fr.yml +0 -3
@@ -0,0 +1,27 @@
1
+ module ModsDisplay
2
+ class FieldComponent < ViewComponent::Base
3
+ with_collection_parameter :field
4
+
5
+ def initialize(field:, delimiter: nil, label_html_attributes: {}, value_html_attributes: {}, value_transformer: nil)
6
+ super
7
+
8
+ @field = field
9
+ @delimiter = delimiter
10
+ @value_transformer = value_transformer
11
+ @label_html_attributes = label_html_attributes
12
+ @value_html_attributes = value_html_attributes
13
+ end
14
+
15
+ def render?
16
+ @field.values.any?(&:present?)
17
+ end
18
+
19
+ def format_value(value)
20
+ if @value_transformer
21
+ @value_transformer.call(value)
22
+ else
23
+ helpers.link_urls_and_email(value)
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,11 @@
1
+ <% if @field.label %>
2
+ <%= tag.dt @field.label.sub(/:$/, ''), **@label_html_attributes %>
3
+ <% end %>
4
+
5
+ <%= tag.dd **@value_html_attributes do %>
6
+ <%= tag.ul **@list_html_attributes do %>
7
+ <% @field.values.select(&:present?).each do |value| %>
8
+ <%= tag.li format_value(value), **@list_item_html_attributes %>
9
+ <% end %>
10
+ <% end %>
11
+ <% end %>
@@ -0,0 +1,10 @@
1
+ module ModsDisplay
2
+ class ListFieldComponent < ModsDisplay::FieldComponent
3
+ def initialize(field:, list_html_attributes: {}, list_item_html_attributes: {}, **args)
4
+ super(field: field, **args)
5
+
6
+ @list_html_attributes = list_html_attributes
7
+ @list_item_html_attributes = list_item_html_attributes
8
+ end
9
+ end
10
+ end
@@ -0,0 +1,5 @@
1
+ <%= tag.dl **@html_attributes do %>
2
+ <% @fields.each do |field| %>
3
+ <%= render @record.mods_field(field) %>
4
+ <% end %>
5
+ <% end %>
@@ -0,0 +1,39 @@
1
+ module ModsDisplay
2
+ class RecordComponent < ViewComponent::Base
3
+ DEFAULT_FIELDS = [
4
+ :subTitle,
5
+ :name,
6
+ :language,
7
+ :imprint,
8
+ :resourceType,
9
+ :genre,
10
+ :form,
11
+ :extent,
12
+ :geo,
13
+ :description,
14
+ :cartographics,
15
+ :abstract,
16
+ :contents,
17
+ :audience,
18
+ :note,
19
+ :contact,
20
+ :collection,
21
+ :nestedRelatedItem,
22
+ :relatedItem,
23
+ :subject,
24
+ :identifier,
25
+ :location
26
+ # :accessCondition
27
+ ].freeze
28
+
29
+ with_collection_parameter :record
30
+
31
+ def initialize(record:, fields: DEFAULT_FIELDS, html_attributes: {})
32
+ super
33
+
34
+ @record = record
35
+ @fields = fields
36
+ @html_attributes = html_attributes
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,106 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ModsDisplay
4
+ module RecordHelper
5
+ def mods_display_label(label)
6
+ content_tag(:dt, label.delete(':')) + "\n".html_safe
7
+ end
8
+
9
+ # @private
10
+ def mods_display_content(values, delimiter = nil)
11
+ mods_record_field ModsDisplay::Values.new(values: Array(values)), delimiter
12
+ end
13
+
14
+ def mods_record_field(field, delimiter = nil, component: ModsDisplay::FieldComponent, &block)
15
+ render component.new(field: field, delimiter: delimiter, value_transformer: block)
16
+ end
17
+
18
+ def mods_name_field(field, &block)
19
+ mods_record_field(field) do |name|
20
+ block_given? ? capture { yield(name.name) } : name.name
21
+ end
22
+ end
23
+
24
+ def mods_display_name(values, &block)
25
+ mods_name_field(ModsDisplay::Values.new(values: Array(values)), &block)
26
+ end
27
+
28
+ # We need this to remove the ending ":" from the role labels only in data from
29
+ # mods_display
30
+ # @private (but currently used in searchworks)
31
+ def sanitize_mods_name_label(label)
32
+ label.sub(/:$/, '')
33
+ end
34
+
35
+ def mods_subject_field(field, &block)
36
+ mods_record_field(field) do |subject_line|
37
+ safe_join(link_mods_subjects(subject_line, &block), ' > ')
38
+ end
39
+ end
40
+
41
+ def mods_genre_field(field, &block)
42
+ mods_record_field(field) do |genre_line|
43
+ link_to_mods_subject(genre_line, &block)
44
+ end
45
+ end
46
+
47
+ # @private
48
+ def link_mods_genres(genre, &block)
49
+ link_buffer = []
50
+ link_to_mods_subject(genre, link_buffer, &block)
51
+ end
52
+
53
+ # @private
54
+ def link_mods_subjects(subjects, &block)
55
+ link_buffer = []
56
+ linked_subjects = []
57
+ subjects.each do |subject|
58
+ if subject.present?
59
+ linked_subjects << link_to_mods_subject(subject, link_buffer, &block)
60
+ end
61
+ end
62
+ linked_subjects
63
+ end
64
+
65
+ # @private
66
+ def link_to_mods_subject(subject, buffer = [], &block)
67
+ subject_text = subject.respond_to?(:name) ? subject.name : subject
68
+ link = block_given? ? capture { yield(subject_text, buffer) } : subject_text
69
+ buffer << subject_text.strip
70
+ link << " (#{subject.roles.join(', ')})" if subject.respond_to?(:roles) && subject.roles.present?
71
+ link
72
+ end
73
+
74
+ # rubocop:disable Layout/LineLength
75
+ # @private, but used in PURL currently
76
+ def link_urls_and_email(val, tags: %w[a dl dd dt i b em strong])
77
+ val = val.gsub(%r{<[^/> ]+}) do |possible_tag|
78
+ # Allow potentially valid HTML tags through to the sanitizer step, and HTML escape the rest
79
+ if tags.include? possible_tag[1..]
80
+ possible_tag
81
+ else
82
+ "&lt;#{possible_tag[1..]}"
83
+ end
84
+ end
85
+
86
+ # http://daringfireball.net/2010/07/improved_regex_for_matching_urls
87
+ url = %r{(?i)\b(?:https?://|www\d{0,3}[.]|[a-z0-9.\-]+[.][a-z]{2,4}/)(?:[^\s()<>]+|\([^\s()<>]+|\([^\s()<>]+\)*\))+(?:\([^\s()<>]+|\([^\s()<>]+\)*\)|[^\s`!()\[\]{};:'".,<>?«»“”‘’])}i
88
+ # http://www.regular-expressions.info/email.html
89
+ email = %r{[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+(?:[A-Z]{2}|com|org|net|edu|gov|mil|biz|info|mobi|name|aero|asia|jobs|museum)\b}i
90
+ matches = [val.scan(url), val.scan(email)].flatten.uniq
91
+ unless val =~ /<a/ # we'll assume that linking has alraedy occured and we don't want to double link
92
+ matches.each do |match|
93
+ if match =~ email
94
+ val.gsub!(match, "<a href='mailto:#{match}'>#{match}</a>")
95
+ else
96
+ val.gsub!(match, "<a href='#{match}'>#{match}</a>")
97
+ end
98
+ end
99
+ end
100
+
101
+ sanitize val, tags: tags, attributes: %w[href]
102
+ end
103
+ # rubocop:enable Layout/LineLength
104
+
105
+ end
106
+ end
@@ -0,0 +1,26 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'stanford-mods'
4
+
5
+ ##
6
+ # A convenience object for parsing and rendering MODS
7
+ module ModsDisplay
8
+ class Record
9
+ attr_reader :xml
10
+
11
+ def initialize(xml)
12
+ @xml = xml
13
+ end
14
+
15
+ def mods_record
16
+ return if xml.nil?
17
+ @mods_record ||= Stanford::Mods::Record.new.tap { |mods| mods.from_str(xml, false) }
18
+ end
19
+
20
+ def mods_display_html
21
+ return unless mods_record
22
+
23
+ ModsDisplay::HTML.new(mods_record)
24
+ end
25
+ end
26
+ end
@@ -42,7 +42,7 @@ en:
42
42
  license: "License:"
43
43
  location: "Location:"
44
44
  map_data: "Map data:"
45
- matrix_number: "Matric number:"
45
+ matrix_number: "Matrix number:"
46
46
  music_plate: "Music plate:"
47
47
  music_publisher: "Music publisher:"
48
48
  note: "Note:"
data/config.ru ADDED
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "rubygems"
4
+ require "bundler"
5
+
6
+ Bundler.require :default, :development
7
+
8
+ Combustion.initialize! :all
9
+ run Combustion::Application
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'view_component'
4
+
5
+ module ModsDisplay
6
+ class Engine < ::Rails::Engine
7
+ initializer 'mods_display.helpers' do
8
+ config.after_initialize do
9
+ ActionView::Base.include ModsDisplay::RecordHelper
10
+ end
11
+ end
12
+ end
13
+ end
@@ -60,6 +60,10 @@ module ModsDisplay
60
60
 
61
61
  private
62
62
 
63
+ def delimiter
64
+ '<br />'
65
+ end
66
+
63
67
  def process_access_statement(element)
64
68
  case normalize_type(element)
65
69
  when 'copyright'
@@ -1,21 +1,20 @@
1
1
  module ModsDisplay
2
2
  class Contents < Field
3
- def to_html
4
- return nil if fields.empty? || @config.ignore?
5
- output = ''
6
- fields.each do |field|
7
- next unless field.values.any? { |f| f && !f.empty? }
8
- output << "<dt#{label_class} #{sanitized_field_title(field.label)}>#{field.label}</dt>"
9
- output << "<dd#{value_class}>"
10
- output << '<ul><li>'
11
- # compress all values into a "--"-delimited string then split them up
12
- output << field.values.join('--').split('--').map(&:strip).map do |val|
13
- @config.link ? link_to_value(val.to_s) : link_urls_and_email(val.to_s)
14
- end.join('</li><li>')
15
- output << '</li></ul>'
16
- output << '</dd>'
3
+ def to_html(view_context = ApplicationController.renderer)
4
+ f = fields.map do |field|
5
+ ModsDisplay::Values.new(label: field.label, values: [field.values.join("\n\n")])
17
6
  end
18
- output
7
+
8
+ helpers = view_context.respond_to?(:simple_format) ? view_context : ApplicationController.new.view_context
9
+
10
+ value_transformer = lambda do |value|
11
+ text = ERB::Util.h(value.gsub('&#10;', "\n"))
12
+ helpers.simple_format(text, {}, sanitize: false)
13
+ end
14
+
15
+ component = ModsDisplay::FieldComponent.with_collection(f, value_transformer: value_transformer)
16
+
17
+ view_context.render component, layout: false
19
18
  end
20
19
 
21
20
  private
@@ -1,10 +1,8 @@
1
1
  # encoding: utf-8
2
2
  module ModsDisplay
3
3
  class Field
4
- def initialize(values, config, klass)
4
+ def initialize(values)
5
5
  @values = values
6
- @config = config
7
- @klass = klass
8
6
  end
9
7
 
10
8
  def fields
@@ -22,83 +20,18 @@ module ModsDisplay
22
20
  displayLabel(@values.first)
23
21
  end
24
22
 
25
- def to_html
26
- return nil if fields.empty? || @config.ignore?
27
- output = ''
28
- fields.each do |field|
29
- next unless field.values.any? { |f| f && !f.empty? }
30
- output << "<dt#{label_class} #{sanitized_field_title(field.label)}>#{field.label}</dt>"
31
- output << "<dd#{value_class}>"
32
- output << field.values.map do |val|
33
- @config.link ? link_to_value(val.to_s) : link_urls_and_email(val.to_s)
34
- end.join(@config.delimiter)
35
- output << '</dd>'
36
- end
37
- output
23
+ def to_html(view_context = ApplicationController.renderer)
24
+ view_context.render ModsDisplay::FieldComponent.with_collection(fields, delimiter: delimiter), layout: false
38
25
  end
39
26
 
40
- private
41
-
42
- def compact_and_join_with_delimiter(values, delimiter)
43
- compact_values = values.compact.reject { |v| v.strip.empty? }
44
- return compact_values.join(delimiter) if compact_values.length == 1 ||
45
- !ends_in_terminating_punctuation?(delimiter)
46
- compact_values.each_with_index.map do |value, i|
47
- if (compact_values.length - 1) == i || # last item?
48
- ends_in_terminating_punctuation?(value)
49
- value << ' '
50
- else
51
- value << delimiter
52
- end
53
- end.join.strip
27
+ def render_in(view_context)
28
+ to_html(view_context)
54
29
  end
55
30
 
56
- def process_bc_ad_dates(date_fields)
57
- date_fields.map do |date_field|
58
- case
59
- when date_is_bc_edtf?(date_field)
60
- year = date_field.text.strip.gsub(/^-0*/, '').to_i + 1
61
- date_field.content = "#{year} B.C."
62
- when date_is_ad?(date_field)
63
- date_field.content = "#{date_field.text.strip.gsub(/^0*/, '')} A.D."
64
- end
65
- date_field
66
- end
67
- end
68
-
69
- def date_is_bc_edtf?(date_field)
70
- date_field.text.strip.start_with?('-') && date_is_edtf?(date_field)
71
- end
72
-
73
- def date_is_ad?(date_field)
74
- date_field.text.strip.gsub(/^0*/, '').length < 4
75
- end
76
-
77
- def date_is_edtf?(date_field)
78
- field_is_encoded?(date_field, 'edtf')
79
- end
80
-
81
- def field_is_encoded?(field, encoding)
82
- field.attributes['encoding'] &&
83
- field.attributes['encoding'].respond_to?(:value) &&
84
- field.attributes['encoding'].value.downcase == encoding
85
- end
86
-
87
- def ends_in_terminating_punctuation?(value)
88
- value.strip.end_with?('.', ',', ':', ';')
89
- end
90
-
91
- def label_class
92
- " class='#{@config.label_class}'" unless @config.label_class == ''
93
- end
94
-
95
- def value_class
96
- " class='#{@config.value_class}'" unless @config.value_class == ''
97
- end
31
+ private
98
32
 
99
- def link_to_value(link_text, link_href = nil)
100
- href_or_text = link_href || link_text
101
- "<a href='#{@klass.send(@config.link[0], replace_tokens(@config.link[1], href_or_text))}'>#{link_text}</a>"
33
+ def delimiter
34
+ nil
102
35
  end
103
36
 
104
37
  def displayForm(element)
@@ -113,83 +46,14 @@ module ModsDisplay
113
46
  "#{element.attributes['displayLabel'].value}:"
114
47
  end
115
48
 
116
- def sanitized_field_title(label)
117
- "title='#{label.gsub(/:$/, '').strip}'"
118
- end
119
-
120
- def replace_tokens(object, value)
121
- object = object.dup
122
- if object.is_a?(Hash)
123
- object.each do |k, v|
124
- object[k] = replace_token(v, value)
125
- end
126
- elsif object.is_a?(String)
127
- object = replace_token(object, value)
128
- end
129
- object
130
- end
131
-
132
- def replace_token(string, value)
133
- string = string.dup
134
- tokens.each do |token|
135
- string.gsub!(token, value)
136
- end
137
- string
138
- end
139
-
140
- def tokens
141
- ['%value%']
142
- end
49
+ def collapse_fields(display_fields)
50
+ return display_fields if display_fields.length == 1
143
51
 
144
- # rubocop:disable Metrics/LineLength
145
- # Disabling line length due to necessarily long regular expressions
146
- def link_urls_and_email(val)
147
- val = val.dup
148
- # http://daringfireball.net/2010/07/improved_regex_for_matching_urls
149
- url = %r{(?i)\b(?:https?://|www\d{0,3}[.]|[a-z0-9.\-]+[.][a-z]{2,4}\/)(?:[^\s()<>]+|\([^\s()<>]+|\([^\s()<>]+\)*\))+(?:\([^\s()<>]+|\([^\s()<>]+\)*\)|[^\s`!()\[\]{};:'".,<>?«»“”‘’])}i
150
- # http://www.regular-expressions.info/email.html
151
- email = /[A-Z0-9_\.%\+\-\']+@(?:[A-Z0-9\-]+\.)+(?:[A-Z]{2,4}|museum|travel)/i
152
- matches = [val.scan(url), val.scan(email)].flatten
153
- unless val =~ /<a/ # we'll assume that linking has alraedy occured and we don't want to double link
154
- matches.each do |match|
155
- if match =~ email
156
- val = val.gsub(match, "<a href='mailto:#{match}'>#{match}</a>")
157
- else
158
- val = val.gsub(match, "<a href='#{match}'>#{match}</a>")
159
- end
160
- end
161
- end
162
- val
163
- end
164
- # rubocop:enable Metrics/LineLength
52
+ display_fields.slice_when { |before, after| before.label != after.label }.map do |group|
53
+ next group.first if group.length == 1
165
54
 
166
- def collapse_fields(display_fields)
167
- return_values = []
168
- current_label = nil
169
- prev_label = nil
170
- buffer = []
171
- display_fields.each_with_index do |field, index|
172
- current_label = field.label
173
- current_values = field.values
174
- if display_fields.length == 1
175
- return_values << ModsDisplay::Values.new(label: current_label, values: current_values)
176
- elsif index == (display_fields.length - 1)
177
- # need to deal w/ when we have a last element but we have separate labels in the buffer.
178
- if current_label != prev_label
179
- return_values << ModsDisplay::Values.new(label: prev_label, values: buffer.flatten)
180
- return_values << ModsDisplay::Values.new(label: current_label, values: current_values)
181
- else
182
- buffer.concat(current_values)
183
- return_values << ModsDisplay::Values.new(label: current_label, values: buffer.flatten)
184
- end
185
- elsif prev_label && (current_label != prev_label)
186
- return_values << ModsDisplay::Values.new(label: prev_label, values: buffer.flatten)
187
- buffer = []
188
- end
189
- buffer.concat(current_values)
190
- prev_label = current_label
55
+ ModsDisplay::Values.new(label: group.first.label, values: group.map(&:values).flatten)
191
56
  end
192
- return_values
193
57
  end
194
58
  end
195
59
  end
@@ -9,6 +9,10 @@ module ModsDisplay
9
9
 
10
10
  private
11
11
 
12
+ def delimiter
13
+ '<br />'
14
+ end
15
+
12
16
  def displayLabel(element)
13
17
  super(element) || I18n.t('mods_display.genre')
14
18
  end
@@ -168,9 +168,9 @@ module ModsDisplay
168
168
  date_field = date_field.clone
169
169
  date_field.content = begin
170
170
  if date_field.text.strip =~ /^\d{4}-\d{2}-\d{2}$/
171
- Date.parse(date_field.text).strftime(@config.full_date_format)
171
+ Date.parse(date_field.text).strftime('%B %d, %Y')
172
172
  elsif date_field.text.strip =~ /^\d{4}-\d{2}$/
173
- Date.parse("#{date_field.text}-01").strftime(@config.short_date_format)
173
+ Date.parse("#{date_field.text}-01").strftime('%B %Y')
174
174
  else
175
175
  date_field.content
176
176
  end
@@ -183,7 +183,7 @@ module ModsDisplay
183
183
  def process_iso8601_date(date_field)
184
184
  date_field = date_field.clone
185
185
  date_field.content = begin
186
- Date.iso8601(date_field.text).strftime(@config.full_date_format)
186
+ Date.iso8601(date_field.text).strftime('%B %d, %Y')
187
187
  rescue
188
188
  date_field.content
189
189
  end
@@ -256,6 +256,55 @@ module ModsDisplay
256
256
 
257
257
  private
258
258
 
259
+ def compact_and_join_with_delimiter(values, delimiter)
260
+ compact_values = values.compact.reject { |v| v.strip.empty? }
261
+ return compact_values.join(delimiter) if compact_values.length == 1 ||
262
+ !ends_in_terminating_punctuation?(delimiter)
263
+ compact_values.each_with_index.map do |value, i|
264
+ if (compact_values.length - 1) == i || # last item?
265
+ ends_in_terminating_punctuation?(value)
266
+ value << ' '
267
+ else
268
+ value << delimiter
269
+ end
270
+ end.join.strip
271
+ end
272
+
273
+ def process_bc_ad_dates(date_fields)
274
+ date_fields.map do |date_field|
275
+ case
276
+ when date_is_bc_edtf?(date_field)
277
+ year = date_field.text.strip.gsub(/^-0*/, '').to_i + 1
278
+ date_field.content = "#{year} B.C."
279
+ when date_is_ad?(date_field)
280
+ date_field.content = "#{date_field.text.strip.gsub(/^0*/, '')} A.D."
281
+ end
282
+ date_field
283
+ end
284
+ end
285
+
286
+ def date_is_bc_edtf?(date_field)
287
+ date_field.text.strip.start_with?('-') && date_is_edtf?(date_field)
288
+ end
289
+
290
+ def date_is_ad?(date_field)
291
+ date_field.text.strip.gsub(/^0*/, '').length < 4
292
+ end
293
+
294
+ def date_is_edtf?(date_field)
295
+ field_is_encoded?(date_field, 'edtf')
296
+ end
297
+
298
+ def field_is_encoded?(field, encoding)
299
+ field.attributes['encoding'] &&
300
+ field.attributes['encoding'].respond_to?(:value) &&
301
+ field.attributes['encoding'].value.downcase == encoding
302
+ end
303
+
304
+ def ends_in_terminating_punctuation?(value)
305
+ value.strip.end_with?('.', ',', ':', ';')
306
+ end
307
+
259
308
  def edition_element(value)
260
309
  value.edition.reject do |e|
261
310
  e.text.strip.empty?
@@ -16,26 +16,18 @@ module ModsDisplay
16
16
  collapse_roles(collapse_fields(return_fields))
17
17
  end
18
18
 
19
- def to_html
20
- return nil if fields.empty? || @config.ignore?
21
- output = ''
22
- fields.each do |field|
23
- output << "<dt#{label_class} #{sanitized_field_title(field.label)}>#{field.label}</dt>"
24
- output << "<dd#{value_class}>"
25
- output << field.values.map do |val|
26
- if @config.link
27
- link_to_value(val.name)
28
- else
29
- val.to_s
30
- end
31
- end.join(@config.delimiter)
32
- output << '</dd>'
33
- end
34
- output
19
+ def to_html(view_context = ApplicationController.renderer)
20
+ component = ModsDisplay::FieldComponent.with_collection(fields, value_transformer: ->(value) { value.to_s })
21
+
22
+ view_context.render component, layout: false
35
23
  end
36
24
 
37
25
  private
38
26
 
27
+ def delimiter
28
+ '<br />'
29
+ end
30
+
39
31
  def collapse_roles(fields)
40
32
  return [] if fields.blank?
41
33
 
@@ -150,12 +142,11 @@ module ModsDisplay
150
142
  def rebuild_fields_with_new_labels(label_keys, results)
151
143
  # Build the new fields data, stripping out the roles within the Person classes
152
144
  label_keys.uniq.map do |k|
153
- mdv = ModsDisplay::Values.new({})
154
- mdv.label = k
155
- mdv.values = results[k].map do |person|
145
+ values = results[k].map do |person|
156
146
  ModsDisplay::Name::Person.new(name: person.name)
157
147
  end
158
- mdv
148
+
149
+ ModsDisplay::Values.new(label: k, values: values)
159
150
  end
160
151
  end
161
152