Class: Bulkrax::ValkyrieObjectFactory

Inherits:
ObjectFactoryInterface show all
Includes:
FileFactory
Defined in:
app/factories/bulkrax/valkyrie_object_factory.rb

Overview

rubocop:disable Metrics/ClassLength

Defined Under Namespace

Classes: FileFactoryInnerWorkings

Instance Attribute Summary

Attributes inherited from ObjectFactoryInterface

#attributes, #importer_run_id, #klass, #object, #related_parents_parsed_mapping, #replace_files, #source_identifier_value, #update_files, #user, #work_identifier, #work_identifier_search_field

Class Method Interface collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods inherited from ObjectFactoryInterface

add_user_to_collection_permissions, #add_user_to_collection_permissions, #base_permitted_attributes, clean!, #create, default_admin_set_id, default_admin_set_or_nil, export_properties, #find, #find_or_create, find_or_nil, #initialize, #run, #search_by_identifier, #transformation_removes_blank_hash_values, #update

Methods included from Loggable

#log_created, #log_deleted_fs, #log_updated

Methods included from DynamicRecordLookup

#find_record

Constructor Details

This class inherits a constructor from Bulkrax::ObjectFactoryInterface

Class Method Details

.add_child_to_parent_work(parent:, child:) ⇒ Object

Note:

This does not save either object. We need to do that in another loop. Why? Because we might be adding many items to the parent.



68
69
70
71
72
73
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 68

def self.add_child_to_parent_work(parent:, child:)
  return true if parent.member_ids.include?(child.id)

  parent.member_ids << child.id
  parent.save
end

.add_resource_to_collection(collection:, resource:, user:) ⇒ Object



75
76
77
78
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 75

def self.add_resource_to_collection(collection:, resource:, user:)
  resource.member_of_collection_ids << collection.id
  save!(resource: resource, user: user)
end

.field_multi_value?(field:, model:) ⇒ Boolean

Returns:

  • (Boolean)


80
81
82
83
84
85
86
87
88
89
90
91
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 80

def self.field_multi_value?(field:, model:)
  return false unless field_supported?(field: field, model: model)

  if model.respond_to?(:schema)
    dry_type = model.schema.key(field.to_sym)
    return true if dry_type.respond_to?(:primitive) && dry_type.primitive == Array

    false
  else
    Bulkrax::ObjectFactory.field_multi_value?(field: field, model: model)
  end
end

.field_supported?(field:, model:) ⇒ Boolean

Returns:

  • (Boolean)


93
94
95
96
97
98
99
100
101
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 93

def self.field_supported?(field:, model:)
  if model.respond_to?(:schema)
    schema_properties(model).include?(field)
  else
    # We *might* have a Fedora object, so we need to consider that approach as
    # well.
    Bulkrax::ObjectFactory.field_supported?(field: field, model: model)
  end
end

.file_sets_for(resource:) ⇒ Object



103
104
105
106
107
108
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 103

def self.file_sets_for(resource:)
  return [] if resource.blank?
  return [resource] if resource.is_a?(Bulkrax.file_model_class)

  Hyrax.query_service.custom_queries.find_child_file_sets(resource: resource)
end

.find(id) ⇒ Object



110
111
112
113
114
115
116
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 110

def self.find(id)
  Hyrax.query_service.find_by(id: id)
  # Because Hyrax is not a hard dependency, we need to transform the Hyrax exception into a
  # common exception so that callers can handle a generalize exception.
rescue Hyrax::ObjectNotFoundError => e
  raise ObjectFactoryInterface::ObjectNotFoundError, e.message
end

.find_or_create_default_admin_setObject



118
119
120
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 118

def self.find_or_create_default_admin_set
  Hyrax::AdminSetCreateService.find_or_create_default_admin_set
end

.ordered_file_sets_for(object) ⇒ Object



201
202
203
204
205
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 201

def self.ordered_file_sets_for(object)
  return [] if object.blank?

  Hyrax.custom_queries.find_child_file_sets(resource: object)
end

.publish(event:, **kwargs) ⇒ Object



128
129
130
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 128

def self.publish(event:, **kwargs)
  Hyrax.publisher.publish(event, **kwargs)
end

.query(q, **kwargs) ⇒ Object

Raises:

  • (NotImplementedError)


132
133
134
135
136
137
138
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 132

def self.query(q, **kwargs)
  # Someone could choose ActiveFedora::SolrService.  But I think we're
  # assuming Valkyrie is specifcally working for Hyrax.  Someone could make
  # another object factory.
  raise NotImplementedError, "#{self}.#{__method__}" unless defined?(Hyrax)
  Hyrax::SolrService.query(q, **kwargs)
end

.save!(resource:, user:) ⇒ Object



140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 140

def self.save!(resource:, user:)
  if resource.respond_to?(:save!)
    resource.save!
  else
    result = Hyrax.persister.save(resource: resource)
    raise Valkyrie::Persistence::ObjectNotFoundError unless result
    Hyrax.index_adapter.save(resource: result)
    if result.collection?
      publish('collection.metadata.updated', collection: result, user: user)
    else
      publish('object.metadata.updated', object: result, user: user)
    end
    resource
  end
end

.schema_properties(klass) ⇒ Array<String>

Retrieve properties from M3 model

Parameters:

  • klass

    the model

Returns:

  • (Array<String>)


192
193
194
195
196
197
198
199
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 192

def self.schema_properties(klass)
  @schema_properties_map ||= {}

  klass_key = klass.name
  @schema_properties_map[klass_key] = klass.schema.map { |k| k.name.to_s } unless @schema_properties_map.key?(klass_key)

  @schema_properties_map[klass_key]
end

.search_by_property(value:, klass:, field: nil, name_field: nil) ⇒ NilClass, Valkyrie::Resource

rubocop:disable Metrics/ParameterLists

Parameters:

  • value (String)
  • klass (Class, #where)
  • field (String, Symbol) (defaults to: nil)

    A convenience parameter where we pass the same value to search_field and name_field.

  • name_field (String) (defaults to: nil)

    the ActiveFedora::Base property name (e.g. “title”)

Returns:

  • (NilClass)

    when no object is found.

  • (Valkyrie::Resource)

    when a match is found, an instance of given :klass



178
179
180
181
182
183
184
185
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 178

def self.search_by_property(value:, klass:, field: nil, name_field: nil, **)
  name_field ||= field
  raise "Expected named_field or field got nil" if name_field.blank?
  return if value.blank?

  # Return nil or a single object.
  Hyrax.query_service.custom_query.find_by_model_and_property_value(model: klass, property: name_field, value: value)
end

.solr_name(field_name) ⇒ Object

Raises:

  • (NotImplementedError)


122
123
124
125
126
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 122

def self.solr_name(field_name)
  # It's a bit unclear what this should be if we can't rely on Hyrax.
  raise NotImplementedError, "#{self}.#{__method__}" unless defined?(Hyrax)
  Hyrax.config.index_field_mapper.solr_name(field_name)
end

.transactionsObject

Note:

Within Bulkrax::ValkyrieObjectFactory there are several calls to transactions; so you’ll need your container to register those transactions.

When you want a different set of transactions you can change the container.



54
55
56
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 54

def self.transactions
  @transactions || Hyrax::Transactions::Container
end

.update_index(resources:) ⇒ Object



156
157
158
159
160
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 156

def self.update_index(resources:)
  Array(resources).each do |resource|
    Hyrax.index_adapter.save(resource: resource)
  end
end

.update_index_for_file_sets_of(resource:) ⇒ Object



162
163
164
165
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 162

def self.update_index_for_file_sets_of(resource:)
  file_sets = Hyrax.query_service.custom_queries.find_child_file_sets(resource: resource)
  update_index(resources: file_sets)
end

Instance Method Details

#delete(user) ⇒ Object



207
208
209
210
211
212
213
214
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 207

def delete(user)
  obj = find
  return false unless obj

  Hyrax.persister.delete(resource: obj)
  Hyrax.index_adapter.delete(resource: obj)
  self.class.publish(event: 'object.deleted', object: obj, user: user)
end

#run!Object



216
217
218
219
220
221
222
223
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 216

def run!
  run
  # reload the object
  object = find
  return object if object&.persisted?

  raise(ObjectFactoryInterface::RecordInvalid, object)
end

#transactionsObject



58
59
60
# File 'app/factories/bulkrax/valkyrie_object_factory.rb', line 58

def transactions
  self.class.transactions
end