module ActiveRecord::AttributeMethods::Dirty
Public Instance Methods
Returns the original value of an attribute before the last save. Behaves
similarly to attribute_was
. This method is useful in after
callbacks to get the original value of an attribute before the save that
just occurred
# File lib/active_record/attribute_methods/dirty.rb, line 166 def attribute_before_last_save(attr_name) mutations_before_last_save.original_value(attr_name) end
# File lib/active_record/attribute_methods/dirty.rb, line 220 def attribute_change(*) emit_warning_if_needed("attribute_change", "saved_change_to_attribute") super end
Alias for `attribute_change`
# File lib/active_record/attribute_methods/dirty.rb, line 186 def attribute_change_to_be_saved(attr_name) mutations_from_database.change_to_attribute(attr_name) end
# File lib/active_record/attribute_methods/dirty.rb, line 225 def attribute_changed?(*) emit_warning_if_needed("attribute_changed?", "saved_change_to_attribute?") super end
Alias for `attribute_was`
# File lib/active_record/attribute_methods/dirty.rb, line 191 def attribute_in_database(attr_name) mutations_from_database.original_value(attr_name) end
# File lib/active_record/attribute_methods/dirty.rb, line 215 def attribute_was(*) emit_warning_if_needed("attribute_was", "attribute_before_last_save") super end
Alias for `changed_attributes`
# File lib/active_record/attribute_methods/dirty.rb, line 211 def attributes_in_database changes_to_save.transform_values(&:first) end
# File lib/active_record/attribute_methods/dirty.rb, line 235 def changed(*) emit_warning_if_needed("changed", "saved_changes.keys") super end
# File lib/active_record/attribute_methods/dirty.rb, line 230 def changed?(*) emit_warning_if_needed("changed?", "saved_changes?") super end
Alias for `changed`
# File lib/active_record/attribute_methods/dirty.rb, line 206 def changed_attribute_names_to_save changes_to_save.keys end
Alias for `changes`
# File lib/active_record/attribute_methods/dirty.rb, line 201 def changes_to_save mutations_from_database.changes end
Alias for `changed?`
# File lib/active_record/attribute_methods/dirty.rb, line 196 def has_changes_to_save? mutations_from_database.any_changes? end
reload
the record and clears changed attributes.
# File lib/active_record/attribute_methods/dirty.rb, line 49 def reload(*) super.tap do @previous_mutation_tracker = nil clear_mutation_trackers @changed_attributes = ActiveSupport::HashWithIndifferentAccess.new end end
Attempts to save
the record and clears changed attributes if
successful.
# File lib/active_record/attribute_methods/dirty.rb, line 34 def save(*) if status = super changes_applied end status end
Attempts to save!
the record and clears changed attributes if
successful.
# File lib/active_record/attribute_methods/dirty.rb, line 42 def save!(*) super.tap do changes_applied end end
Returns the change to an attribute during the last save. If the attribute was changed, the result will be an array containing the original value and the saved value.
Behaves similarly to attribute_change
. This method is useful
in after callbacks, to see the change in an attribute that just occurred
This method can be invoked as `saved_change_to_name` in instead of `saved_change_to_attribute(“name”)`
# File lib/active_record/attribute_methods/dirty.rb, line 158 def saved_change_to_attribute(attr_name) mutations_before_last_save.change_to_attribute(attr_name) end
Did this attribute change when we last saved? This method can be invoked as
`saved_change_to_name?` instead of `saved_change_to_attribute?(“name”)`.
Behaves similarly to attribute_changed?
. This method is useful
in after callbacks to determine if the call to save changed a certain
attribute.
Options¶ ↑
from
When passed, this method will return false unless the
original value is equal to the given option
to
When passed, this method will return false unless the value
was changed to the given value
# File lib/active_record/attribute_methods/dirty.rb, line 145 def saved_change_to_attribute?(attr_name, **options) mutations_before_last_save.changed?(attr_name, **options) end
Returns a hash containing all the changes that were just saved.
# File lib/active_record/attribute_methods/dirty.rb, line 176 def saved_changes mutations_before_last_save.changes end
Did the last call to `save` have any changes to change?
# File lib/active_record/attribute_methods/dirty.rb, line 171 def saved_changes? mutations_before_last_save.any_changes? end
Alias for `attribute_changed?`
# File lib/active_record/attribute_methods/dirty.rb, line 181 def will_save_change_to_attribute?(attr_name, **options) mutations_from_database.changed?(attr_name, **options) end
Private Instance Methods
# File lib/active_record/attribute_methods/dirty.rb, line 296 def _create_record(*) partial_writes? ? super(keys_for_partial_write) : super end
# File lib/active_record/attribute_methods/dirty.rb, line 292 def _update_record(*) partial_writes? ? super(keys_for_partial_write) : super end
# File lib/active_record/attribute_methods/dirty.rb, line 277 def attribute_will_change!(attr_name) super if self.class.has_attribute?(attr_name) mutations_from_database.force_change(attr_name) else ActiveSupport::Deprecation.warn(<<-EOW.squish) #{attr_name} is not an attribute known to Active Record. This behavior is deprecated and will be removed in the next version of Rails. If you'd like #{attr_name} to be managed by Active Record, add `attribute :#{attr_name} to your class. EOW mutations_from_database.deprecated_force_change(attr_name) end end
# File lib/active_record/attribute_methods/dirty.rb, line 322 def cache_changed_attributes @cached_changed_attributes = changed_attributes yield ensure clear_changed_attributes_cache end
# File lib/active_record/attribute_methods/dirty.rb, line 268 def changes_include?(attr_name) super || mutation_tracker.changed?(attr_name) end
# File lib/active_record/attribute_methods/dirty.rb, line 272 def clear_attribute_change(attr_name) mutation_tracker.forget_change(attr_name) mutations_from_database.forget_change(attr_name) end
# File lib/active_record/attribute_methods/dirty.rb, line 329 def clear_changed_attributes_cache remove_instance_variable(:@cached_changed_attributes) if defined?(@cached_changed_attributes) end
# File lib/active_record/attribute_methods/dirty.rb, line 308 def clear_mutation_trackers @mutation_tracker = nil @mutations_from_database = nil @mutations_before_last_save = nil end
# File lib/active_record/attribute_methods/dirty.rb, line 249 def emit_warning_if_needed(method_name, new_method_name) unless mutation_tracker.equal?(mutations_from_database) ActiveSupport::Deprecation.warn(<<-EOW.squish) The behavior of `#{method_name}` inside of after callbacks will be changing in the next version of Rails. The new return value will reflect the behavior of calling the method after `save` returned (e.g. the opposite of what it returns now). To maintain the current behavior, use `#{new_method_name}` instead. EOW end end
# File lib/active_record/attribute_methods/dirty.rb, line 304 def forget_attribute_assignments @attributes = @attributes.map(&:forgetting_assignment) end
# File lib/active_record/attribute_methods/dirty.rb, line 300 def keys_for_partial_write changed_attribute_names_to_save & self.class.column_names end
# File lib/active_record/attribute_methods/dirty.rb, line 242 def mutation_tracker unless defined?(@mutation_tracker) @mutation_tracker = nil end @mutation_tracker ||= AttributeMutationTracker.new(@attributes) end
# File lib/active_record/attribute_methods/dirty.rb, line 318 def mutations_before_last_save @mutations_before_last_save ||= previous_mutation_tracker end
# File lib/active_record/attribute_methods/dirty.rb, line 261 def mutations_from_database unless defined?(@mutations_from_database) @mutations_from_database = nil end @mutations_from_database ||= mutation_tracker end
# File lib/active_record/attribute_methods/dirty.rb, line 314 def previous_mutation_tracker @previous_mutation_tracker ||= NullMutationTracker.instance end