diff options
author | Aaron Patterson <aaron.patterson@gmail.com> | 2018-07-26 12:03:31 -0700 |
---|---|---|
committer | Aaron Patterson <aaron.patterson@gmail.com> | 2018-07-26 12:03:31 -0700 |
commit | b0a16a97762c4cdcf36403d46968930099ddcd0f (patch) | |
tree | 24bcdc9b44b25f74e406c669705f8ea9986e5c24 /activesupport | |
parent | 0c0dba1caf72f78558554a28ca4fc01923cec6f1 (diff) | |
download | rails-b0a16a97762c4cdcf36403d46968930099ddcd0f.tar.gz rails-b0a16a97762c4cdcf36403d46968930099ddcd0f.tar.bz2 rails-b0a16a97762c4cdcf36403d46968930099ddcd0f.zip |
Subscribe to event objects via `subscribe_event`
Fanout notifier can send event objects to subscribers now. Also moved
`end` lower in the `finish!` method to guarantee that CPU time is
shorter than real time.
Diffstat (limited to 'activesupport')
-rw-r--r-- | activesupport/lib/active_support/notifications/fanout.rb | 38 | ||||
-rw-r--r-- | activesupport/lib/active_support/notifications/instrumenter.rb | 2 | ||||
-rw-r--r-- | activesupport/test/notifications_test.rb | 17 |
3 files changed, 56 insertions, 1 deletions
diff --git a/activesupport/lib/active_support/notifications/fanout.rb b/activesupport/lib/active_support/notifications/fanout.rb index 25aab175b4..91d8491c7e 100644 --- a/activesupport/lib/active_support/notifications/fanout.rb +++ b/activesupport/lib/active_support/notifications/fanout.rb @@ -27,6 +27,15 @@ module ActiveSupport subscriber end + def subscribe_event(pattern = nil, &block) + subscriber = Subscribers.event_object_subscriber pattern, block + synchronize do + @subscribers << subscriber + @listeners_for.clear + end + subscriber + end + def unsubscribe(subscriber_or_name) synchronize do case subscriber_or_name @@ -76,6 +85,14 @@ module ActiveSupport subscriber = Timed.new pattern, listener end + wrap_all pattern, subscriber + end + + def self.event_object_subscriber(pattern, block) + wrap_all pattern, EventObject.new(pattern, block) + end + + def self.wrap_all(pattern, subscriber) unless pattern AllMessages.new(subscriber) else @@ -130,6 +147,27 @@ module ActiveSupport end end + class EventObject < Evented + def start(name, id, payload) + stack = Thread.current[:_event_stack] ||= [] + event = build_event name, id, payload + event.start! + stack.push event + end + + def finish(name, id, payload) + stack = Thread.current[:_event_stack] + event = stack.pop + event.finish! + @delegate.call event + end + + private + def build_event(name, id, payload) + ActiveSupport::Notifications::Event.new name, nil, nil, id, payload + end + end + class AllMessages # :nodoc: def initialize(delegate) @delegate = delegate diff --git a/activesupport/lib/active_support/notifications/instrumenter.rb b/activesupport/lib/active_support/notifications/instrumenter.rb index 259cb4db98..72e5064679 100644 --- a/activesupport/lib/active_support/notifications/instrumenter.rb +++ b/activesupport/lib/active_support/notifications/instrumenter.rb @@ -76,8 +76,8 @@ module ActiveSupport end def finish! - @end = now @cpu_time_finish = now_cpu + @end = now @allocation_count_finish = now_allocations end diff --git a/activesupport/test/notifications_test.rb b/activesupport/test/notifications_test.rb index d035f993f7..e28560d88b 100644 --- a/activesupport/test/notifications_test.rb +++ b/activesupport/test/notifications_test.rb @@ -26,6 +26,23 @@ module Notifications end end + class SubscribeEventObjects < TestCase + def test_subscribe_events + events = [] + @notifier.subscribe_event do |event| + events << event + end + + ActiveSupport::Notifications.instrument("foo") + event = events.first + assert event, "should have an event" + assert_operator event.allocations, :>, 0 + assert_operator event.cpu_time, :>, 0 + assert_operator event.idle_time, :>, 0 + assert_operator event.duration, :>, 0 + end + end + class SubscribedTest < TestCase def test_subscribed name = "foo" |