Class: Padrino::Logger

Inherits:
Object show all
Includes:
Extensions
Defined in:
padrino-core/lib/padrino-core/logger.rb

Overview

Padrinos internal logger, using all of Padrino log extensions.

Defined Under Namespace

Modules: Colorize, Extensions Classes: Rack

Constant Summary collapse

Levels =
{
  fatal: 4,
  error: 3,
  warn: 2,
  info: 1,
  debug: 0,
  devel: -1
}
Config =

Configuration for a given environment, possible options are:

:log_level

Once of [:fatal, :error, :warn, :info, :debug]

:stream

Once of [:to_file, :null, :stdout, :stderr] our your custom stream

:log_path

Defines log file path or directory if :stream is :to_file

If it's a file, its location is created by mkdir_p.
If it's a directory, it must exist. In this case log name is '<env>.log'
:log_level

The log level from, e.g. :fatal or :info. Defaults to :warn in the production environment and :debug otherwise.

:auto_flush

Whether the log should automatically flush after new messages are added. Defaults to true.

:format_datetime

Format of datetime. Defaults to: “%d/%b/%Y %H:%M:%S”

:format_message

Format of message. Defaults to: “”%s - - [%s] "%s"“”

:log_static

Whether or not to show log messages for static files. Defaults to: false

:colorize_logging

Whether or not to colorize log messages. Defaults to: true

Defaults are:

:production  => { log_level: :warn, stream: :to_file }
:development => { log_level: :debug, stream: :stdout }
:test        => { log_level: :fatal, stream: :null }

In some cases, configuring the loggers before loading the framework is necessary. You can do so by setting PADRINO_LOGGER:

PADRINO_LOGGER = { staging: { log_level: :debug, stream: :to_file }}

Examples:

Padrino::Logger::Config[:development] = { log_level: :debug, stream: :to_file }
# or you can edit our defaults
Padrino::Logger::Config[:development][:log_level] = :error
# or change log file path
Padrino::Logger::Config[:development][:log_path] = 'logs/app-development.txt'
# or change log file directory
Padrino::Logger::Config[:development][:log_path] = '/var/logs/padrino'
# or you can use your stream
Padrino::Logger::Config[:development][:stream] = StringIO.new
{
  production: { log_level: :warn, stream: :to_file },
  development: { log_level: :debug, stream: :stdout, format_datetime: '' },
  test: { log_level: :debug, stream: :null }
}

Constants included from Extensions

Extensions::SOURCE_LOCATION_REGEXP

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Extensions

#bench, #colorize, #colorize!, #enable_source_location?, #exception, #name, #push, #resolve_source_location, #stylized_level

Constructor Details

#initialize(options = {}) ⇒ Logger

To initialize the logger you create a new object, proxies to set_log.

Parameters:

  • options (Hash) (defaults to: {})

Options Hash (options):

  • :stream (Symbol) — default: $stdout

    Either an IO object or a name of a logfile. Defaults to $stdout

  • :log_level (Symbol) — default: :production in the production environment and :debug otherwise

    The log level from, e.g. :fatal or :info.

  • :auto_flush (Symbol) — default: true

    Whether the log should automatically flush after new messages are added. Defaults to true.

  • :format_datetime (Symbol) — default: " [%d/%b/%Y %H:%M:%S] "

    Format of datetime.

  • :format_message (Symbol) — default: "%s -%s%s"

    Format of message.

  • :log_static (Symbol) — default: false

    Whether or not to show log messages for static files.

  • :colorize_logging (Symbol) — default: true

    Whether or not to colorize log messages. Defaults to: true.

  • :sanitize_encoding (Symbol) — default: false

    Logger will replace undefined or broken characters with “uFFFD” for Unicode and “?” otherwise. Can be an encoding, false or true. If it’s true, logger sanitizes to Encoding.default_external.



419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
# File 'padrino-core/lib/padrino-core/logger.rb', line 419

def initialize(options = {})
  @buffer           = []
  @auto_flush       = options.key?(:auto_flush) ? options[:auto_flush] : true
  @level            = options[:log_level] ? Padrino::Logger::Levels[options[:log_level]] : Padrino::Logger::Levels[:debug]
  @log              = options[:stream] || $stdout
  @log.sync         = true
  @format_datetime  = options[:format_datetime] || '%d/%b/%Y %H:%M:%S'
  @format_message   = options[:format_message]  || '%s - %s %s'
  @log_static       = options.key?(:log_static) ? options[:log_static] : false
  @colorize_logging = options.key?(:colorize_logging) ? options[:colorize_logging] : true
  @source_location  = options[:source_location]
  @sanitize_encoding = options[:sanitize_encoding] || false
  @sanitize_encoding = Encoding.default_external if @sanitize_encoding == true
  colorize! if @colorize_logging
end

Instance Attribute Details

#auto_flushObject

Returns the value of attribute auto_flush.



275
276
277
# File 'padrino-core/lib/padrino-core/logger.rb', line 275

def auto_flush
  @auto_flush
end

#bufferObject (readonly)

Returns the value of attribute buffer.



276
277
278
# File 'padrino-core/lib/padrino-core/logger.rb', line 276

def buffer
  @buffer
end

#colorize_loggingObject (readonly)

Returns the value of attribute colorize_logging.



276
277
278
# File 'padrino-core/lib/padrino-core/logger.rb', line 276

def colorize_logging
  @colorize_logging
end

#init_argsObject (readonly)

Returns the value of attribute init_args.



276
277
278
# File 'padrino-core/lib/padrino-core/logger.rb', line 276

def init_args
  @init_args
end

#levelObject

Returns the value of attribute level.



275
276
277
# File 'padrino-core/lib/padrino-core/logger.rb', line 275

def level
  @level
end

#logObject (readonly)

Returns the value of attribute log.



276
277
278
# File 'padrino-core/lib/padrino-core/logger.rb', line 276

def log
  @log
end

#log_staticObject

Returns the value of attribute log_static.



275
276
277
# File 'padrino-core/lib/padrino-core/logger.rb', line 275

def log_static
  @log_static
end

Class Method Details

.loggerObject



330
331
332
# File 'padrino-core/lib/padrino-core/logger.rb', line 330

def self.logger
  (@_logger ||= nil) || setup!
end

.logger=(logger) ⇒ Object



334
335
336
337
338
339
340
341
342
343
# File 'padrino-core/lib/padrino-core/logger.rb', line 334

def self.logger=(logger)
  unless logger.class.ancestors.include?(Padrino::Logger::Extensions)
    warn "      WARNING! `Padrino.logger = new_logger` no longer extends it with #colorize! and other features.\n                To do it with a custom logger you have to manually `new_logger.extend(Padrino::Logger::Extensions)`\n                before passing to `Padrino.logger = new_logger`.\n    MESSAGE\n  end\n  @_logger = logger\nend\n"

.mutexObject



326
327
328
# File 'padrino-core/lib/padrino-core/logger.rb', line 326

def self.mutex
  @_mutex ||= Mutex.new
end

.setup!Padrino::Logger

Setup a new logger.

Returns:



351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
# File 'padrino-core/lib/padrino-core/logger.rb', line 351

def self.setup!
  config_level = (PADRINO_LOG_LEVEL || Padrino.env || :test).to_sym # need this for PADRINO_LOG_LEVEL
  config = Config[config_level]

  unless config
    warn("No logging configuration for :#{config_level} found, falling back to :production")
    config = Config[:production]
  end

  stream =
    case config[:stream]
    when :to_file
      if (filename = config[:log_path])
        filename = Padrino.root(filename) unless Pathname.new(filename).absolute?
        if File.directory?(filename)
          filename = File.join(filename, "#{Padrino.env}.log")
        else
          FileUtils.mkdir_p(File.dirname(filename))
        end
        File.new(filename, 'a+')
      else
        FileUtils.mkdir_p(Padrino.root('log')) unless File.exist?(Padrino.root('log'))
        File.new(Padrino.root('log', "#{Padrino.env}.log"), 'a+')
      end
    when :null   then ::StringIO.new
    when :stdout then $stdout
    when :stderr then $stderr
    else config[:stream] # return itself, probabilly is a custom stream.
    end

  new_logger = Padrino::Logger.new(config.merge(stream: stream))
  new_logger.extend(Padrino::Logger::Extensions)
  self.logger = new_logger
end

Instance Method Details

#<<(message = nil) ⇒ Object Also known as: write

Directly append message to the log.

Parameters:

  • message (String) (defaults to: nil)

    The message



477
478
479
480
481
482
# File 'padrino-core/lib/padrino-core/logger.rb', line 477

def <<(message = nil)
  message << "\n" unless message[-1] == "\n"
  self.class.mutex.synchronize { @buffer << message }
  flush if @auto_flush
  message
end

#add(level, message = nil) ⇒ Object

Adds a message to the log - for compatibility with other loggers.



467
468
469
# File 'padrino-core/lib/padrino-core/logger.rb', line 467

def add(level, message = nil)
  write(message)
end

#closeNilClass

Close and remove the current log object.

Returns:

  • (NilClass)


458
459
460
461
462
# File 'padrino-core/lib/padrino-core/logger.rb', line 458

def close
  flush
  @log.close if @log.respond_to?(:close) && !@log.tty?
  @log = nil
end

#flushObject

Flush the entire buffer to the log object.



442
443
444
445
446
447
448
449
450
451
# File 'padrino-core/lib/padrino-core/logger.rb', line 442

def flush
  return unless @buffer.size.positive?
  self.class.mutex.synchronize do
    @buffer.each do |line|
      line.encode!(@sanitize_encoding, invalid: :replace, undef: :replace) if @sanitize_encoding
      @log.write(line)
    end
    @buffer.clear
  end
end

#format(message, level) ⇒ Object



485
486
487
# File 'padrino-core/lib/padrino-core/logger.rb', line 485

def format(message, level)
  Kernel.format(@format_message, stylized_level(level), colorize(Time.now.strftime(@format_datetime), :yellow), message.to_s.strip)
end

#source_location?Boolean

Returns:

  • (Boolean)


435
436
437
# File 'padrino-core/lib/padrino-core/logger.rb', line 435

def source_location?
  !!@source_location
end