def self.included(base)
base.class_eval do
def transaction_with_callback(*args, &block)
outermost_call = @disable_rollback.nil?
@disable_rollback = false if outermost_call
transaction_without_callback(*args, &block)
ensure
@disable_rollback = nil if outermost_call
end
alias_method_chain :transaction, :callback
def commit_db_transaction_with_callback
increment_transaction_pointer
result = nil
begin
trigger_before_commit_callbacks
trigger_before_commit_on_create_callbacks
trigger_before_commit_on_update_callbacks
trigger_before_commit_on_save_callbacks
trigger_before_commit_on_destroy_callbacks
result = commit_db_transaction_without_callback
@disable_rollback = true
trigger_after_commit_callbacks
trigger_after_commit_on_create_callbacks
trigger_after_commit_on_update_callbacks
trigger_after_commit_on_save_callbacks
trigger_after_commit_on_destroy_callbacks
result
rescue
unless @disable_rollback
decrement_transaction_pointer
@already_decremented = true
end
raise
ensure
AfterCommit.cleanup(self)
decrement_transaction_pointer unless @already_decremented
end
end
alias_method_chain :commit_db_transaction, :callback
def rollback_db_transaction_with_callback
return if @disable_rollback
increment_transaction_pointer
begin
result = nil
trigger_before_rollback_callbacks
result = rollback_db_transaction_without_callback
trigger_after_rollback_callbacks
result
ensure
AfterCommit.cleanup(self)
decrement_transaction_pointer
end
decrement_transaction_pointer
end
alias_method_chain :rollback_db_transaction, :callback
def unique_transaction_key
[object_id, transaction_pointer]
end
def old_transaction_key
[object_id, transaction_pointer - 1]
end
protected
def trigger_before_commit_callbacks
AfterCommit.records(self).each do |record|
record.send :callback, :before_commit
end
end
def trigger_before_commit_on_create_callbacks
AfterCommit.created_records(self).each do |record|
record.send :callback, :before_commit_on_create
end
end
def trigger_before_commit_on_update_callbacks
AfterCommit.updated_records(self).each do |record|
record.send :callback, :before_commit_on_update
end
end
def trigger_before_commit_on_save_callbacks
AfterCommit.saved_records(self).each do |record|
record.send :callback, :before_commit_on_save
end
end
def trigger_before_commit_on_destroy_callbacks
AfterCommit.destroyed_records(self).each do |record|
record.send :callback, :before_commit_on_destroy
end
end
def trigger_before_rollback_callbacks
AfterCommit.records(self).each do |record|
record.send :callback, :before_rollback
end
end
def trigger_after_commit_callbacks
AfterCommit.records(self).each do |record|
record.send :callback, :after_commit
end
end
def trigger_after_commit_on_create_callbacks
AfterCommit.created_records(self).each do |record|
record.send :callback, :after_commit_on_create
end
end
def trigger_after_commit_on_update_callbacks
AfterCommit.updated_records(self).each do |record|
record.send :callback, :after_commit_on_update
end
end
def trigger_after_commit_on_save_callbacks
AfterCommit.saved_records(self).each do |record|
record.send :callback, :after_commit_on_save
end
end
def trigger_after_commit_on_destroy_callbacks
AfterCommit.destroyed_records(self).each do |record|
record.send :callback, :after_commit_on_destroy
end
end
def trigger_after_rollback_callbacks
AfterCommit.records(self).each do |record|
record.send :callback, :after_rollback
end
end
def transaction_pointer
Thread.current[:after_commit_pointer] ||= 0
end
def increment_transaction_pointer
Thread.current[:after_commit_pointer] ||= 0
Thread.current[:after_commit_pointer] += 1
end
def decrement_transaction_pointer
Thread.current[:after_commit_pointer] ||= 0
Thread.current[:after_commit_pointer] -= 1
end
end
end