Created
May 10, 2016 14:49
-
-
Save ideasasylum/e0be5ef7c3603f22e26aa0c4dd590385 to your computer and use it in GitHub Desktop.
Dirty state tracking for previous changes
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module PreviouslyDirty | |
extend ActiveSupport::Concern | |
include ActiveModel::AttributeMethods | |
included do | |
attribute_method_suffix '_previously_changed?', '_previously_was' | |
end | |
# Handle <tt>*_previously_changed?</tt> for +method_missing+. | |
def attribute_previously_changed?(attr, options = {}) #:nodoc: | |
result = previous_changes.include?(attr) | |
result &&= options[:to] == previous_changes[attr][1] if options.key?(:to) | |
result &&= options[:from] == previous_changes[attr][0] if options.key?(:from) | |
result | |
end | |
# Handle <tt>*_was</tt> for +method_missing+. | |
def attribute_previously_was(attr) # :nodoc: | |
attribute_previously_changed?(attr) ? previous_changes[attr][0] : __send__(attr) | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Rails has some great dirty state tracking methods but this information is cleared after the commit. This prevents you doing things like:
but all the changes from the last commit are stored in the
previous_changes
hash so this gist adds theattribute_previously_changed?
andattribute_previously_was
methods following the same pattern as the regular change methodsI find this very handy for conditional after_commit callbacks or, even better, for avoiding callbacks altogether and putting that logic in the controller (on the basis that callbacks can be a complete PITA)