require "thread"
require "open4"

path_to_cron = `which cronolog`
path_to_cron = path_to_cron.chomp

DELAY_TEMPLATES = { :daily => {:cmd_string => "#{path_to_cron}
",:format_string => "\%Y/\%m/\%d"},
  :hourly => {:cmd_string => "#{path_to_cron} --delay '1 hour'
",:format_string => nil},
  :midnight => {:cmd_string => "#{path_to_cron} --delay '12 hours'
",:format_string => nil}}

class Log4u

  def initialize(_file_name,delay_interval = :daily)

    raise(ArgumentError.new,"Invalid arguments") unless
[:daily,:hourly,:midnight].include? delay_interval

    @mutex = Mutex.new

    filename_string = File.basename(_file_name)
    dirname_string = File.dirname(_file_name)

    if (format_string = DELAY_TEMPLATES[delay_interval][:format_string])
      option_string =
"#{dirname_string}/#{format_string}/#{filename_string}"
    else
      option_string = "#{dirname_string}/#{filename_string}"
    end

    check_for_prgrm dirname_string

    cmd_string = DELAY_TEMPLATES[delay_interval][:cmd_string]
    pid,@log_pipe,stdout,stderr = Open4.popen4("#{cmd_string}
#{option_string}")
  end

  def check_for_prgrm dirname_string
    path_to_cron = `which cronolog`
    raise "Cronolog doesn't exist in path" if path_to_cron.empty?
    raise "Log Directory isn't writable" unless File.writable?
dirname_string
  end

  def time_string
    time_now = Time.now
    time_now.strftime("%I:%M%p")
  end

  def error msg
    @mutex.synchronize{ @log_pipe.puts "ERROR: #{time_string}: #{msg}" }
  end

  def info msg
    @mutex.synchronize{ @log_pipe.puts "INFO: #{time_string}: #{msg}" }
  end

  def debug msg
    @mutex.synchronize { @log_pipe.puts "DEBUG: #{time_string}: #{msg}"}
  end

  def close_log
    @mutex.synchronize { @log_pipe.close }
  end
end

I am facing following problems with above code:

  1. Doesn't detect the pipe errors and propagate it to parent ,
     and when used from threads would invariably lead to buggy code.
because threads won't
     detect the exception until abort_on_exception is true or a join is
performed.
     May be a problem of the author who is going to use it, but still if
i can simpify things a bit.
  2. Not sure, how it behaves when multiple processes/threads attempt to
get cronolog on
     the same file. In my tests cronolog seems to handle it, but not
entirely sure.
  3. Gives bloody zombie processes sometimes.


Any ideas folks?