I'm writing a multilogger implementation in order to enable my application to log to multiple back ends. The implementation looks like:
class MultiLogger < Logger
def initialize(loggers = [])
@loggers = []
end
def add(severity, message, _attributes, _environment, progname)
@loggers.each do |logger|
logger.add(severity, message, progname)
end
end
def info(message, attributes, environment, progname)
add(Logger::INFO, message, attributes, environment, progname)
end
...
end
Basically I'm only forwarding calls issued to MultiLogger#add
to all the loggers associated during the instantiation. The problem is that I need to set that logger as the Rails' default one, but I can't do that.
I'm adding config.logger = MultiLogger.new([Logger1.new, Logger2.new])
to my application.rb
file, but when I call logger.info
, I'm getting an error related to the arity of the add
method.
The strangest thing is that my custom add is never called, and that error is raised from ActiveSupport::LogerThreadSafeLevel#add
, like this: .rbenv/versions/2.6.6/lib/ruby/gems/2.6.0/gems/activesupport-6.0.3.2/lib/active_support/logger_thread_safe_level.rb:51:in 'add'
.
I think I'm missing something important about the inner workings of the Rails logging mechanism... but what? Is ActiveSupport
overwriting my add
method? What can I do in order to avoid that?
Rails expects the Logger#add method to follow the interface of the Ruby logger, that is one mandatory argument (the
severity
), followed by two optional arguments (themessage
and theprogname
) as well as an optional block.Here, Rails also assumed very specific semantics how these arguments are used by a logger implementation to build the final message (when passing either a
message
, aprogname
, a block or any combination of it.In your original code, you have defined additional mandatory parameters in your
add
method (namely_attributes
and_environment
) which are not provided when calling the method thus an Exception. Once you fix your parameter list (and implement the missing shortcut methods and accessors), everything should work.