diff options
Diffstat (limited to 'activesupport/lib/active_support/log_subscriber.rb')
-rw-r--r-- | activesupport/lib/active_support/log_subscriber.rb | 60 |
1 files changed, 40 insertions, 20 deletions
diff --git a/activesupport/lib/active_support/log_subscriber.rb b/activesupport/lib/active_support/log_subscriber.rb index d2a6e1bd82..e5b4ca2738 100644 --- a/activesupport/lib/active_support/log_subscriber.rb +++ b/activesupport/lib/active_support/log_subscriber.rb @@ -48,20 +48,19 @@ module ActiveSupport mattr_accessor :colorize_logging self.colorize_logging = true - class_attribute :logger - class << self - remove_method :logger def logger @logger ||= Rails.logger if defined?(Rails) + @logger end + attr_writer :logger + def attach_to(namespace, log_subscriber=new, notifier=ActiveSupport::Notifications) log_subscribers << log_subscriber - @@flushable_loggers = nil log_subscriber.public_methods(false).each do |event| - next if 'call' == event.to_s + next if %w{ start finish }.include?(event.to_s) notifier.subscribe("#{event}.#{namespace}", log_subscriber) end @@ -71,29 +70,44 @@ module ActiveSupport @@log_subscribers ||= [] end - def flushable_loggers - @@flushable_loggers ||= begin - loggers = log_subscribers.map(&:logger) - loggers.uniq! - loggers.select! { |l| l.respond_to?(:flush) } - loggers - end - end - # Flush all log_subscribers' logger. def flush_all! - flushable_loggers.each { |log| log.flush } + logger.flush if logger.respond_to?(:flush) end end - def call(message, *args) + def initialize + @queue_key = [self.class.name, object_id].join "-" + super + end + + def logger + LogSubscriber.logger + end + + def start(name, id, payload) return unless logger - method = message.split('.').first + e = ActiveSupport::Notifications::Event.new(name, Time.now, nil, id, payload) + parent = event_stack.last + parent << e if parent + + event_stack.push e + end + + def finish(name, id, payload) + return unless logger + + finished = Time.now + event = event_stack.pop + event.end = finished + event.payload.merge!(payload) + + method = name.split('.').first begin - send(method, ActiveSupport::Notifications::Event.new(message, *args)) + send(method, event) rescue Exception => e - logger.error "Could not log #{message.inspect} event. #{e.class}: #{e.message} #{e.backtrace}" + logger.error "Could not log #{name.inspect} event. #{e.class}: #{e.message} #{e.backtrace}" end end @@ -114,9 +128,15 @@ module ActiveSupport # def color(text, color, bold=false) return text unless colorize_logging - color = self.class.const_get(color.to_s.upcase) if color.is_a?(Symbol) + color = self.class.const_get(color.upcase) if color.is_a?(Symbol) bold = bold ? BOLD : "" "#{bold}#{color}#{text}#{CLEAR}" end + + private + + def event_stack + Thread.current[@queue_key] ||= [] + end end end |