1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87
|
# frozen_string_literal: true
module Lumberjack
# A file-based logging device that extends the Writer device with automatic
# log rotation capabilities. This device wraps Ruby's standard Logger::LogDevice
# to provide file size-based and time-based log rotation while maintaining
# compatibility with the Lumberjack device interface.
#
# The device supports all the rotation features available in Ruby's Logger,
# including maximum file size limits, automatic rotation based on age, and
# automatic cleanup of old log files. This makes it suitable for production
# environments where log management is crucial.
#
# @example Basic file logging
# device = Lumberjack::Device::LogFile.new("/var/log/app.log")
#
# @example With size-based rotation (10MB files, keep 5 old files)
# device = Lumberjack::Device::LogFile.new(
# "/var/log/app.log",
# shift_size: 10 * 1024 * 1024, # 10MB
# shift_age: 5 # Keep 5 old files
# )
#
# @example With daily rotation
# device = Lumberjack::Device::LogFile.new(
# "/var/log/app.log",
# shift_age: "daily"
# )
#
# @example With weekly rotation
# device = Lumberjack::Device::LogFile.new(
# "/var/log/app.log",
# shift_age: "weekly"
# )
#
# @see Device::Writer
# @see Logger::LogDevice
class Device::LogFile < Device::Writer
# Initialize a new LogFile device with automatic log rotation capabilities.
# This constructor wraps Ruby's Logger::LogDevice while filtering options to
# only pass supported parameters, ensuring compatibility across Ruby versions.
#
# @param stream [String, IO] The log destination. Can be a file path string
# or an IO object. When a string path is provided, the file will be created
# if it doesn't exist, and parent directories will be created as needed.
# @param options [Hash] Configuration options for the log device. All options
# supported by Logger::LogDevice are accepted, including:
# - +:shift_age+ - Number of old files to keep, or rotation frequency
# ("daily", "weekly", "monthly")
# - +:shift_size+ - Maximum file size in bytes before rotation
# - +:shift_period_suffix+ - Suffix to add to rotated log files
# - +:binmode+ - Whether to open the log file in binary mode
def initialize(stream, options = {})
# Filter options to only include keyword arguments supported by Logger::LogDevice#initialize
supported_kwargs = ::Logger::LogDevice.instance_method(:initialize).parameters
.select { |type, _| type == :key || type == :keyreq }
.map { |_, name| name }
filtered_options = options.slice(*supported_kwargs)
logdev = ::Logger::LogDevice.new(stream, **filtered_options)
super(logdev, options)
end
# Get the file system path of the current log file. This method provides
# access to the actual file path being written to, which is useful for
# monitoring, log analysis tools, or other file-based operations.
#
# @return [String] The absolute file system path of the current log file
def path
stream.filename
end
# Expose the underlying stream.
#
# @return [IO]
# @api private
def dev
stream.dev
end
def reopen(logdev = nil)
stream.reopen(logdev)
end
end
end
|