Project

General

Profile

Download (2.92 KB) Statistics
| Branch: | Tag: | Revision:
require 'date'
require 'proxy/log_buffer/ring_buffer'

# Adopted from Celluloid library (ring_buffer.rb).
# Copyright (c) 2011-2014 Tony Arcieri. Distributed under the MIT License.
# https://github.com/celluloid/celluloid/blob/0-16-stable/lib/celluloid/logging/ring_buffer.rb
module Proxy::LogBuffer
LogRecord = Struct.new(:timestamp, :level, :message, :backtrace, :request_id) do
def to_h
h = {}
self.class.members.each {|m| h[m.to_sym] = self[m]}
h[:level] = case h[:level]
when ::Logger::Severity::INFO
:INFO
when ::Logger::Severity::WARN
:WARN
when ::Logger::Severity::ERROR
:ERROR
when ::Logger::Severity::FATAL
:FATAL
when ::Logger::Severity::DEBUG
:DEBUG
else
:UNKNOWN
end
h.delete(:backtrace) unless h[:backtrace]
h.delete(:request_id) unless h[:request_id]
h
end
end

class Buffer
def self.instance
@@buffer ||= Buffer.new
end

def initialize(size = nil, size_tail = nil, level_tail = nil)
@mutex = Mutex.new
@failed_modules = {}
@main_buffer = RingBuffer.new(size || ::Proxy::SETTINGS.log_buffer.to_i)
@tail_buffer = RingBuffer.new(size_tail || ::Proxy::SETTINGS.log_buffer_errors.to_i)
@level_tail = level_tail || ::Logger::Severity::ERROR
end

def push(rec)
@mutex.synchronize do
rec.timestamp = Time.now.utc.to_f
old_value = @main_buffer.push(rec)
@tail_buffer.push(old_value) if old_value && old_value.level >= @level_tail
end
end

def iterate_ascending
@mutex.synchronize do
@tail_buffer.iterate_ascending { |x| yield x }
@main_buffer.iterate_ascending { |x| yield x }
end
end

def iterate_descending
@mutex.synchronize do
@main_buffer.iterate_descending { |x| yield x }
@tail_buffer.iterate_descending { |x| yield x }
end
end

def to_a(from_timestamp = 0)
result = []
if from_timestamp == 0
iterate_ascending do |x|
result << x if x
end
else
iterate_ascending do |x|
result << x if x && x.timestamp >= from_timestamp
end
end
result
end

# Singleton logger does not allow per-module logging, until this is fixed
# initialization errors are kept in this explicit hash.
def failed_module(a_module, message)
@failed_modules[a_module] = message
end

def size
@main_buffer.size
end

def size_tail
@tail_buffer.size
end

def to_s
"#{size}/#{size_tail}"
end

def info
{
:size => size,
:tail_size => size_tail,
:level => @level,
:level_tail => @level_tail,
:failed_modules => @failed_modules,
}
end
end
end
(1-1/4)