module ActiveRecord::DelayTouching
Public Class Methods
apply()
click to toggle source
Apply the touches that were delayed.
# File lib/activerecord/delay_touching.rb, line 62 def self.apply begin ActiveRecord::Base.transaction do state.records_by_attrs_and_class.each do |attr, classes_and_records| classes_and_records.each do |klass, records| touch_records attr, klass, records end end end end while state.more_records? ensure state.clear_records end
call() { || ... }
click to toggle source
Start delaying all touches. When done, apply them. (Unless nested.)
# File lib/activerecord/delay_touching.rb, line 49 def self.call state.nesting += 1 begin yield ensure apply if state.nesting == 1 end ensure # Decrement nesting even if `apply` raised an error. state.nesting -= 1 end
state()
click to toggle source
# File lib/activerecord/delay_touching.rb, line 40 def self.state Thread.current[:delay_touching_state] ||= State.new end
touch_records(attr, klass, records)
click to toggle source
Touch the specified records–non-empty set of instances of the same class.
# File lib/activerecord/delay_touching.rb, line 77 def self.touch_records(attr, klass, records) attributes = records.first.send(:timestamp_attributes_for_update_in_model) attributes << attr if attr if attributes.present? current_time = records.first.send(:current_time_from_proper_timezone) changes = {} attributes.each do |column| column = column.to_s changes[column] = current_time records.each do |record| # Don't bother if destroyed or not-saved next unless record.persisted? record.instance_eval do write_attribute column, current_time @changed_attributes.except!(*changes.keys) end end end klass.unscoped.where(klass.primary_key => records).update_all(changes) end state.updated attr, records records.each { |record| record.run_callbacks(:touch) } end
Public Instance Methods
touch(*names)
click to toggle source
Override ActiveRecord::Base#touch.
Calls superclass method
# File lib/activerecord/delay_touching.rb, line 9 def touch(*names) if self.class.delay_touching? && !try(:no_touching?) DelayTouching.add_record(self, *names) true else super end end