module ActiveRecord::AttributeMethods::Dirty
def _create_record(attribute_names = attribute_names_for_partial_inserts)
def _create_record(attribute_names = attribute_names_for_partial_inserts) id = super changes_applied id end
def _touch_row(attribute_names, time)
def _touch_row(attribute_names, time) @_touch_attr_names = Set.new(attribute_names) affected_rows = super if @_skip_dirty_tracking ||= false clear_attribute_changes(@_touch_attr_names) return affected_rows end changes = {} @attributes.keys.each do |attr_name| next if @_touch_attr_names.include?(attr_name) if attribute_changed?(attr_name) changes[attr_name] = _read_attribute(attr_name) _write_attribute(attr_name, attribute_was(attr_name)) clear_attribute_change(attr_name) end end changes_applied changes.each { |attr_name, value| _write_attribute(attr_name, value) } affected_rows ensure @_touch_attr_names, @_skip_dirty_tracking = nil, nil end
def _update_record(attribute_names = attribute_names_for_partial_updates)
def _update_record(attribute_names = attribute_names_for_partial_updates) affected_rows = super changes_applied affected_rows end
def attribute_before_last_save(attr_name)
invoked as +name_before_last_save+ instead of
attribute before the save that triggered the callbacks to run. It can be
This method is useful in after callbacks to get the original value of an
Returns the original value of an attribute before the last save.
def attribute_before_last_save(attr_name) mutations_before_last_save.original_value(attr_name.to_s) end
def attribute_change_to_be_saved(attr_name)
If the attribute will change, the result will be an array containing the
attribute_change_to_be_saved("name").
be invoked as +name_change_to_be_saved+ instead of
change to an attribute that will occur when the record is saved. It can
This method is useful in validations and before callbacks, to see the
next save.
Returns the change to an attribute that will be persisted during the
def attribute_change_to_be_saved(attr_name) mutations_from_database.change_to_attribute(attr_name.to_s) end
def attribute_in_database(attr_name)
saved. It can be invoked as +name_in_database+ instead of
original value of an attribute prior to any changes about to be
This method is useful in validations and before callbacks, to see the
saved.
in-memory value that will be persisted the next time the record is
Returns the value of an attribute in the database, as opposed to the
def attribute_in_database(attr_name) mutations_from_database.original_value(attr_name.to_s) end
def attribute_names_for_partial_inserts
def attribute_names_for_partial_inserts if partial_inserts? changed_attribute_names_to_save else attribute_names.reject do |attr_name| if column_for_attribute(attr_name).default_function !attribute_changed?(attr_name) end end end end
def attribute_names_for_partial_updates
def attribute_names_for_partial_updates partial_updates? ? changed_attribute_names_to_save : attribute_names end
def attributes_in_database
original attribute values in the database (as opposed to the in-memory
The hash keys are the attribute names, and the hash values are the
next saved.
Returns a hash of the attributes that will change when the record is
def attributes_in_database mutations_from_database.changed_values end
def changed_attribute_names_to_save
Returns an array of the names of any attributes that will change when
def changed_attribute_names_to_save mutations_from_database.changed_attribute_names end
def changes_to_save
Returns a hash containing all the changes that will be persisted during
def changes_to_save mutations_from_database.changes end
def has_changes_to_save?
def has_changes_to_save? mutations_from_database.any_changes? end
def reload(*)
def reload(*) super.tap do @mutations_before_last_save = nil @mutations_from_database = nil end end
def saved_change_to_attribute(attr_name)
invoked as +saved_change_to_name+ instead of
attribute during the save that triggered the callbacks to run. It can be
This method is useful in after callbacks, to see the change in an
original value and the saved value.
attribute was changed, the result will be an array containing the
Returns the change to an attribute during the last save. If the
def saved_change_to_attribute(attr_name) mutations_before_last_save.change_to_attribute(attr_name.to_s) end
def saved_change_to_attribute?(attr_name, **options)
+to+ When passed, this method will return false unless the value was
value is equal to the given option
+from+ When passed, this method will return false unless the original
==== Options
saved_change_to_attribute?("name").
be invoked as +saved_change_to_name?+ instead of
was changed during the save that triggered the callbacks to run. It can
This method is useful in after callbacks to determine if an attribute
Did this attribute change when we last saved?
def saved_change_to_attribute?(attr_name, **options) mutations_before_last_save.changed?(attr_name.to_s, **options) end
def saved_changes
def saved_changes mutations_before_last_save.changes end
def saved_changes?
def saved_changes? mutations_before_last_save.any_changes? end
def will_save_change_to_attribute?(attr_name, **options)
+to+ When passed, this method will return false unless the value will be
value is equal to the given option
+from+ When passed, this method will return false unless the original
==== Options
will_save_change_to_attribute?("name").
invoked as +will_save_change_to_name?+ instead of
if the next call to +save+ will change a particular attribute. It can be
This method is useful in validations and before callbacks to determine
Will this attribute change the next time we save?
def will_save_change_to_attribute?(attr_name, **options) mutations_from_database.changed?(attr_name.to_s, **options) end