Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse files

Allow ActiveRecord observers to be disabled.

We have to use Observer#update rather than Observer#send since the enabled state is checked in #update before forwarding the method call on.
  • Loading branch information...
commit d3c15a1d31d77e44b142c96cb55b654f3552a89d 1 parent 943a373
@myronmarston myronmarston authored
View
4 activemodel/lib/active_model/observing.rb
@@ -226,10 +226,10 @@ def observed_classes #:nodoc:
# Send observed_method(object) if the method exists and
# the observer is enabled for the given object's class.
- def update(observed_method, object) #:nodoc:
+ def update(observed_method, object, &block) #:nodoc:
return unless respond_to?(observed_method)
return if disabled_for?(object)
- send(observed_method, object)
+ send(observed_method, object, &block)
end
# Special method sent by the observed class when it is inherited.
View
12 activemodel/test/cases/observing_test.rb
@@ -17,6 +17,10 @@ class << self
def on_spec(record)
stub.event_with(record) if stub
end
+
+ def around_save(record)
+ yield :in_around_save
+ end
end
class Foo
@@ -133,4 +137,12 @@ def teardown
foo = Foo.new
Foo.send(:notify_observers, :whatever, foo)
end
+
+ test "update passes a block on to the observer" do
+ yielded_value = nil
+ FooObserver.instance.update(:around_save, Foo.new) do |val|
+ yielded_value = val
+ end
+ assert_equal :in_around_save, yielded_value
+ end
end
View
2  activerecord/lib/active_record/observer.rb
@@ -111,7 +111,7 @@ def define_callbacks(klass)
callback_meth = :"_notify_#{observer_name}_for_#{callback}"
unless klass.respond_to?(callback_meth)
klass.send(:define_method, callback_meth) do |&block|
- observer.send(callback, self, &block)
+ observer.update(callback, self, &block)
end
klass.send(callback, callback_meth)
end
View
12 activerecord/test/cases/lifecycle_test.rb
@@ -231,6 +231,18 @@ def test_invalid_observer
assert_not_nil observer.topic_ids.last
end
+ test "able to disable observers" do
+ observer = DeveloperObserver.instance # activate
+ observer.calls.clear
+
+ ActiveRecord::Base.observers.disable DeveloperObserver do
+ Developer.create! :name => 'Ancestor', :salary => 100000
+ SpecialDeveloper.create! :name => 'Descendent', :salary => 100000
+ end
+
+ assert_equal [], observer.calls
+ end
+
def test_observer_is_called_once
observer = DeveloperObserver.instance # activate
observer.calls.clear
Please sign in to comment.
Something went wrong with that request. Please try again.