# frozen_string_literal: true module Upgrow # Mixin that implements Repository methods with an Active Record Base. When # included in a Repository class, it sets the default base to be a class # ending with `Record`. module ActiveRecordAdapter # Fetches all Records and returns them as an Array of Models. # # @return [Array] a collection of Models representing all persisted # Records. def all base.all.map { |record| to_model(record.attributes) } end # Persists a new Record with the given input, and materializes the newly # created Record as the returned Model instance. # # @param input [Input] the Input with the attributes for the new Record. # # @return [Model] the Model with the attributes of the newly created # Record. def create(input) record = base.create!(input.attributes) to_model(record.attributes) end # Retrieves the Record with the given ID, representing its data as a Model. # # @param id [Integer] the ID of the Record to be fetched. # # @return [Model] the Model with the attributes of the Record with the given # ID. def find(id) record = base.find(id) to_model(record.attributes) end # Updates the Record with the given ID with the given Input attributes. # # @param id [Integer] the ID of the Record to be updated. # @param input [Input] the Input with the attributes to be set in the # Record. # # @return [Model] the Model instance with the updated data of the Record. def update(id, input) record = base.update(id, input.attributes) to_model(record.attributes) end # Deletes the Record that has the given ID. # # @param id [Integer] the ID of the Record to be deleted. def delete(id) base.destroy(id) end # Callback method used by Basic Repository to set a default Repository base # when one is not explicitly provided at the Repository initialization. # # It attempts to find a constant based on the Repository name, with the # `Record` suffix as a convention. For example, a `UserRepository` would # have the `UserRecord` as its base. That is the naming convention for # Active Record classes under this architecture. # # @return [Class] the Active Record Base class to be used as the Repository # base according to the architecture's naming convention. def default_base base_name = self.class.name[/\A(.+)Repository\z/, 1] + 'Record' Object.const_get(base_name) end end end