Module: ActsAsReplaceable::InstanceMethods

Defined in:
lib/acts_as_replaceable/acts_as_replaceable.rb

Instance Method Summary collapse

Instance Method Details

#_create_record(*args) ⇒ Object

Override the create or update method so we can run callbacks, but opt not to save if we don’t need to



152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
# File 'lib/acts_as_replaceable/acts_as_replaceable.rb', line 152

def _create_record(*args)
  ActsAsReplaceable::HelperMethods.lock_if(ActsAsReplaceable.concurrency, self) do
    find_and_replace
    if @has_not_changed
      logger.info "(acts_as_replaceable) Found unchanged #{self.class.to_s} ##{id} #{"- Name: #{name}" if respond_to?('name')}"
    elsif @has_been_replaced
      _update_record(*args)
      logger.info "(acts_as_replaceable) Updated existing #{self.class.to_s} ##{id} #{"- Name: #{name}" if respond_to?('name')}"
    else
      super
      logger.info "(acts_as_replaceable) Created #{self.class.to_s} ##{id} #{"- Name: #{name}" if respond_to?('name')}"
    end
  end

  return true
end

#find_and_replaceObject

Replaces self with an existing copy from the database if available, raises an exception if more than one copy exists in the database



170
171
172
173
174
175
176
177
178
# File 'lib/acts_as_replaceable/acts_as_replaceable.rb', line 170

def find_and_replace
  existing = ActsAsReplaceable::HelperMethods.find_existing(self)

  if existing.length > 1
    raise RecordNotUnique, "#{existing.length} duplicate #{self.class.model_name.human.pluralize} present in database"
  end

  replace_with(existing.first) if existing.first
end

#replace_with(existing) ⇒ Object



180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
# File 'lib/acts_as_replaceable/acts_as_replaceable.rb', line 180

def replace_with(existing)
  # Inherit target's attributes for those in acts_as_replaceable_options[:inherit]
  ActsAsReplaceable::HelperMethods.copy_attributes(acts_as_replaceable_options[:inherit], existing, self)

  # Rails 5 introduced AR::Dirty and started using `mutations_from_database` to
  # lookup `id_in_database` which is required for the `_update_record` call
  #
  # This chunk of code is copied from https://api.rubyonrails.org/classes/ActiveRecord/Persistence.html#method-i-becomes
  if existing.respond_to?(:mutations_from_database, true)
    instance_variable_set("@mutations_from_database", existing.send(:mutations_from_database) || nil)
  end

  @new_record        = false
  @has_been_replaced = true
  @has_not_changed   = !ActsAsReplaceable::HelperMethods.mark_changes(self, existing)
end