lib/semantic_logger/appender/file.rb in semantic_logger-0.5.3 vs lib/semantic_logger/appender/file.rb in semantic_logger-0.6.0

- old
+ new

@@ -2,75 +2,70 @@ # # Writes log messages to a file or open iostream # module SemanticLogger module Appender - class File - attr_accessor :formatter + class File < SemanticLogger::Base # Create a File Logger appender instance # # Example # require 'semantic_logger' # + # # Enable trace level logging + # SemanticLogger::Logger.level = :info + # # # Log to screen # SemanticLogger::Logger.appenders << SemanticLogger::Appender::File.new(STDOUT) # # # And log to a file at the same time # SemanticLogger::Logger.appenders << SemanticLogger::Appender::File.new('application.log') # # logger = SemanticLogger::Logger.new('test') # logger.info 'Hello World' # - def initialize(filename, &block) + # Example 2. To log all levels to file and only :info and above to screen: + # + # require 'semantic_logger' + # + # # Enable trace level logging + # SemanticLogger::Logger.level = :trace + # + # # Log to screen but only display :info and above + # SemanticLogger::Logger.appenders << SemanticLogger::Appender::File.new(STDOUT, :info) + # + # # And log to a file at the same time, including all :trace level data + # SemanticLogger::Logger.appenders << SemanticLogger::Appender::File.new('application.log') + # + # logger = SemanticLogger::Logger.new('test') + # logger.info 'Hello World' + # + def initialize(filename, level=nil, &block) raise "logger cannot be null when initializing the SemanticLogging::Appender::Logger" unless filename @filename = filename @log = if filename.respond_to?(:write) and filename.respond_to?(:close) filename else @log = open(filename, (::File::WRONLY | ::File::APPEND | ::File::CREAT)) # Force all log entries to write immediately without buffering + # Allows multiple processes to write to the same log file simultaneously @log.sync = true @log.set_encoding(Encoding::BINARY) if @log.respond_to?(:set_encoding) @log end - # Set the formatter to the supplied block - @formatter = block || self.default_formatter + # Set the log level and formatter if supplied + super(level, &block) end - # Default log formatter - # Replace this formatter by supplying a Block to the initializer - # Generates logs of the form: - # 2011-07-19 14:36:15.660 D [1149:ScriptThreadProcess] Rails -- Hello World\n - def default_formatter - Proc.new do |log| - message = log.message.to_s - tags = log.tags.collect { |tag| "[#{tag}]" }.join(" ") + " " if log.tags && (log.tags.size > 0) - - if log.payload - if log.payload.is_a?(Exception) - exception = log.payload - message << " -- " << "#{exception.class}: #{exception.message}\n#{(exception.backtrace || []).join("\n")}" - else - message << " -- " << log.payload.inspect - end - end - - str = "#{log.time.strftime("%Y-%m-%d %H:%M:%S")}.#{"%03d" % (log.time.usec/1000)} #{log.level.to_s[0..0].upcase} [#{$$}:#{log.thread_name}] #{tags}#{log.name} -- #{message}" - str << " (#{'%.1f' % log.duration}ms)" if log.duration - str << "\n" - str - end - end - # Pass log calls to the underlying Rails, log4j or Ruby logger # trace entries are mapped to debug since :trace is not supported by the # Ruby or Rails Loggers def log(log) # Since only one appender thread will be writing to the file at a time # it is not necessary to protect access to the file with a semaphore - @log.write(@formatter.call(log)) + # Allow this logger to filter out log levels lower than it's own + @log.write(@formatter.call(log) << "\n") if level_index <= (log.level_index || 0) end # Flush all pending logs to disk. # Waits for all sent documents to be writted to disk def flush