diff --git a/Changes.md b/Changes.md index dc621ab6..92cfd5d6 100644 --- a/Changes.md +++ b/Changes.md @@ -7,12 +7,18 @@ Heroku users: `heroku config:set REDIS_PROVIDER=REDISTOGO_URL` - Removed 'sidekiq/yaml\_patch', this was never documented or recommended. - Removed the 'started' worker data, it originally provided compatibility with resque-web - but overlaps the 'run_at' worker data. + but overlaps the 'run\_at' worker data. - Remove built-in error integration for Airbrake, Honeybadger, ExceptionNotifier and Exceptional. Just update your error gem to the latest version to pick up Sidekiq support. - Remove deprecated Sidekiq::Client.registered\_\* APIs - Remove deprecated support for the old Sidekiq::Worker#retries\_exhausted method. +2.17.5 +----------- + +- A `USR2` signal will now reopen _all_ logs, using IO#reopen. Thus, instead of creating a new Logger object, + Sidekiq will now just update the existing Logger's file descriptor [#1163]. +- Remove pidfile when shutting down if started with `-P` [#1470] 2.17.4 ----------- diff --git a/examples/sidekiq b/examples/sidekiq index b003e3b3..42f1e23a 100644 --- a/examples/sidekiq +++ b/examples/sidekiq @@ -73,6 +73,14 @@ case "$1" in stop) stop ;; + restart) + stop + while status > /dev/null + do + sleep 0.5 + done + start + ;; status) status diff --git a/lib/sidekiq/cli.rb b/lib/sidekiq/cli.rb index 1a0fcc91..05cadcb1 100644 --- a/lib/sidekiq/cli.rb +++ b/lib/sidekiq/cli.rb @@ -108,7 +108,7 @@ module Sidekiq when 'USR2' if Sidekiq.options[:logfile] Sidekiq.logger.info "Received USR2, reopening log file" - initialize_logger + Sidekiq::Logging.reopen_logs end when 'TTIN' Thread.list.each do |thread| @@ -179,7 +179,7 @@ module Sidekiq cfile = opts[:config_file] opts = parse_config(cfile).merge(opts) if cfile - + opts[:strict] = true if opts[:strict].nil? options.merge!(opts) @@ -313,6 +313,9 @@ module Sidekiq File.open(path, 'w') do |f| f.puts Process.pid end + at_exit do + FileUtils.rm_f path + end end end diff --git a/lib/sidekiq/logging.rb b/lib/sidekiq/logging.rb index 03739974..65744ae7 100644 --- a/lib/sidekiq/logging.rb +++ b/lib/sidekiq/logging.rb @@ -42,6 +42,51 @@ module Sidekiq @logger = (log ? log : Logger.new('/dev/null')) end + # This reopens ALL logfiles in the process that have been rotated + # using logrotate(8) (without copytruncate) or similar tools. + # A +File+ object is considered for reopening if it is: + # 1) opened with the O_APPEND and O_WRONLY flags + # 2) the current open file handle does not match its original open path + # 3) unbuffered (as far as userspace buffering goes, not O_SYNC) + # Returns the number of files reopened + def self.reopen_logs + to_reopen = [] + append_flags = File::WRONLY | File::APPEND + + ObjectSpace.each_object(File) do |fp| + begin + if !fp.closed? && fp.stat.file? && fp.sync && (fp.fcntl(Fcntl::F_GETFL) & append_flags) == append_flags + to_reopen << fp + end + rescue IOError, Errno::EBADF + end + end + + nr = 0 + to_reopen.each do |fp| + orig_st = begin + fp.stat + rescue IOError, Errno::EBADF + next + end + + begin + b = File.stat(fp.path) + next if orig_st.ino == b.ino && orig_st.dev == b.dev + rescue Errno::ENOENT + end + + begin + File.open(fp.path, 'a') { |tmpfp| fp.reopen(tmpfp) } + fp.sync = true + nr += 1 + rescue IOError, Errno::EBADF + # not much we can do... + end + end + nr + end + def logger Sidekiq::Logging.logger end diff --git a/lib/sidekiq/version.rb b/lib/sidekiq/version.rb index 01462d7f..eed4f4c0 100644 --- a/lib/sidekiq/version.rb +++ b/lib/sidekiq/version.rb @@ -1,3 +1,3 @@ module Sidekiq - VERSION = "2.17.4" + VERSION = "2.17.5" end