1+ # frozen_string_literal: true
12require 'csv'
23
34## Adds a service to generate a sample CSV file showing how fields are split
2627# type: "text/csv"
2728# end
2829# end
30+
31+ # rubocop:disable Metrics/ClassLength
2932module Bulkrax
3033 class SampleCsvService
3134 ADDED_BULKRAX_PROPERTIES = [
@@ -40,7 +43,7 @@ class SampleCsvService
4043
4144 SPECIAL_PROPERTIES = [
4245 { 'model OR work_type' => 'Default if not present' } ,
43- { 'source_identifier' => 'Alternative to id' }
46+ { 'source_identifier' => 'Required unique alternative to id' }
4447 ] . freeze
4548
4649 ## Initialize with optional model_name to customize mappings
@@ -51,20 +54,20 @@ class SampleCsvService
5154 # @return [Bulkrax::SampleCsvService] the service instance
5255 def initialize ( model_name : nil )
5356 # don't include generated metadata fields, except rights_statement
54- @mappings = Bulkrax . field_mappings [ "Bulkrax::CsvParser" ] . reject do |key , value |
57+ @mappings = Bulkrax . field_mappings [ "Bulkrax::CsvParser" ] . reject do |key , value |
5558 value [ "generated" ] == true && key != 'rights_statement'
5659 end
5760 # load models if 'all' is specified for model_name
5861 @model_name = model_name
5962 @all_models = begin
60- if model_name == 'all' && defined? ( ::Hyrax )
61- Hyrax . config . curation_concerns + [ Bulkrax . collection_model_class , Bulkrax . file_model_class ]
62- else
63- [ Bulkrax . default_work_type , Bulkrax . collection_model_class , Bulkrax . file_model_class ]
64- end
65- rescue
66- [ ]
67- end
63+ if model_name == 'all' && defined? ( ::Hyrax )
64+ Hyrax . config . curation_concerns + [ Bulkrax . collection_model_class , Bulkrax . file_model_class ]
65+ else
66+ [ Bulkrax . default_work_type , Bulkrax . collection_model_class , Bulkrax . file_model_class ]
67+ end
68+ rescue
69+ [ ]
70+ end
6871 end
6972
7073 ## Generate the CSV file or string
@@ -77,7 +80,6 @@ def self.call(model_name: nil, output: 'file', **args)
7780 new ( model_name : model_name ) . send ( "to_#{ output } " , **args )
7881 end
7982
80-
8183 ## create a CSV file on disk
8284 # @TODO: determine appropriate file path
8385 def to_file ( file_path : nil )
@@ -108,72 +110,75 @@ def csv_rows
108110
109111 # @TODO: ensure that bulkrax mappings include all properties for the model
110112 # even if not mapped in Bulkrax settings
113+ # rubocop:disable Metrics/MethodLength
111114 def breakdown_mappings
112115 # start with the required Bulkrax properties, then
113116 # add the bulkrax_mapped properties
117+ mv_split = Bulkrax . multi_value_element_split_on . source
118+
114119 all_mappings = ADDED_BULKRAX_PROPERTIES +
115- @mappings . map do |_ , value |
120+ @mappings . map do |_ , value |
116121 split = value [ "split" ]
117- split =
118- if split . nil?
119- "does not split"
120- elsif split == true
121- mv_split = Bulkrax . multi_value_element_split_on . source
122- if ( match = mv_split . match ( /\[ ([^\] ]+)\] / ) )
123- "split on #{ match [ 1 ] } "
124- elsif ( single = mv_split . match ( /\\ (.)/ ) )
125- "split on #{ single [ 1 ] } "
126- else
127- "split on #{ mv_split } "
128- end
129- elsif split . is_a? ( String )
130- if ( match = split . match ( /\[ ([^\] ]+)\] / ) )
131- "split on #{ match [ 1 ] } "
132- elsif ( single = split . match ( /\\ (.)/ ) )
133- "split on #{ single [ 1 ] } "
134- else
135- "split on #{ split } "
136- end
137- else
138- split
139- end
140-
141- { value [ "from" ] . join ( ' OR ' ) => split }
122+ split_text = if split . nil? # term doesn't split
123+ "does not split"
124+ elsif split == true # use global setting
125+ if ( match = mv_split . match ( /\[ ([^\] ]+)\] / ) )
126+ "split on #{ match [ 1 ] } "
127+ elsif ( single = mv_split . match ( /\\ (.)/ ) )
128+ "split on #{ single [ 1 ] } "
129+ else
130+ "split on #{ mv_split } "
131+ end
132+ elsif split . is_a? ( String ) # use custom setting
133+ if ( match = split . match ( /\[ ([^\] ]+)\] / ) )
134+ "split on #{ match [ 1 ] } "
135+ elsif ( single = split . match ( /\\ (.)/ ) )
136+ "split on #{ single [ 1 ] } "
137+ else
138+ "split on #{ split } "
139+ end
140+ else # does not match identified patterns
141+ split
142+ end
143+
144+ { value [ "from" ] . join ( ' OR ' ) => split_text }
142145 end
143146 # add in special properties
144147 SPECIAL_PROPERTIES + all_mappings
145148 end
149+ # rubocop:enable Metrics/MethodLength
146150
147151 # Generate rows for the specified model or all models
148152 def model_rows
149- rows = case @model_name
150- when 'all'
151- @all_models . map { |m | model_breakdown ( m . name ) }
152- when String
153- [ model_breakdown ( @model_name ) ]
154- else
155- [ ]
156- end
153+ case @model_name
154+ when 'all'
155+ @all_models . map { |m | model_breakdown ( m . name ) }
156+ when String
157+ [ model_breakdown ( @model_name ) ]
158+ else
159+ [ ]
160+ end
157161 end
158162
159163 def model_breakdown ( model_name )
164+ # rubocop:disable Metrics/MethodLength
160165 model_row = [ ]
161166 klass = determine_klass_for ( model_name )
162167 return model_row if klass . nil?
163168
164169 field_list = if klass . respond_to? ( :schema )
165- Bulkrax ::ValkyrieObjectFactory . schema_properties ( klass ) . map ( &:to_sym )
166- else
167- klass . properties . keys . map ( &:to_sym )
168- end
170+ Bulkrax ::ValkyrieObjectFactory . schema_properties ( klass ) . map ( &:to_sym )
171+ else
172+ klass . properties . keys . map ( &:to_sym )
173+ end
169174 load_required_terms_for ( klass : klass )
170175
171176 @header_row . each do |column_heading |
172177 # Load a value into each column based on the heading
173178 value = if field_list . include? ( column_heading . to_sym )
174179 mark_property ( field : column_heading . to_sym )
175180 elsif column_heading == 'model' || column_heading == 'work_type' || column_heading == 'model OR work_type'
176- " #{ model_name } "
181+ model_name . to_s
177182 elsif column_heading . in? ( ADDED_BULKRAX_PROPERTIES . map ( &:keys ) . flatten )
178183 'Optional'
179184 elsif column_heading == 'source_identifier'
@@ -189,6 +194,7 @@ def model_breakdown(model_name)
189194 end
190195 model_row
191196 end
197+ # rubocop:enable Metrics/MethodLength
192198
193199 # Determine if the property is required or optional for the given class
194200 def mark_property ( field :)
@@ -199,15 +205,15 @@ def mark_property(field:)
199205
200206 def load_required_terms_for ( klass :)
201207 @required_terms = begin
202- if klass . respond_to? ( :schema )
203- schema = klass . new . singleton_class . schema || klass . schema
204- get_required_types ( schema )
205- else
206- [ ]
207- end
208- rescue
209- [ ]
210- end
208+ if klass . respond_to? ( :schema )
209+ schema = klass . new . singleton_class . schema || klass . schema
210+ get_required_types ( schema )
211+ else
212+ [ ]
213+ end
214+ rescue
215+ [ ]
216+ end
211217 end
212218
213219 def get_required_types ( schema )
@@ -227,3 +233,4 @@ def determine_klass_for(model_name)
227233 end
228234 end
229235end
236+ # rubocop:enable Metrics/ClassLength
0 commit comments