Class: Delayed::Daemon

Inherits:
Object
  • Object
show all
Defined in:
lib/delayed/daemon.rb

Overview

Daemon controls the parent proces that runs the Pool and monitors the Worker processes.

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(pid_folder) ⇒ Daemon

Returns a new instance of Daemon.



10
11
12
# File 'lib/delayed/daemon.rb', line 10

def initialize(pid_folder)
  @pid_folder = pid_folder
end

Instance Attribute Details

#pid_folderObject (readonly)

Returns the value of attribute pid_folder.



8
9
10
# File 'lib/delayed/daemon.rb', line 8

def pid_folder
  @pid_folder
end

Instance Method Details

#daemonize!Object



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
# File 'lib/delayed/daemon.rb', line 25

def daemonize!
  FileUtils.mkdir_p(pid_folder)
  puts "Daemonizing..."

  exit if fork
  Process.setsid
  exit if fork
  Process.setpgrp

  @daemon = true
  lock_file = File.open(pid_file, "wb")
  # someone else is already running; just exit
  exit unless lock_file.flock(File::LOCK_EX | File::LOCK_NB)
  at_exit { lock_file.flock(File::LOCK_UN) }
  lock_file.puts(Process.pid.to_s)
  lock_file.flush

  # if we blow up so badly that we can't syslog the error, try to send
  # it somewhere useful
  last_ditch_logfile = Settings.last_ditch_logfile || "log/delayed_job.log"
  last_ditch_logfile = Settings.expand_rails_path(last_ditch_logfile) if last_ditch_logfile[0] != "|"
  $stdin.reopen("/dev/null")
  $stdout.reopen(open(last_ditch_logfile, "a")) # rubocop:disable Security/Open
  $stderr.reopen($stdout)
  $stdout.sync = $stderr.sync = true
end

#daemonized?Boolean

Returns:

  • (Boolean)


89
90
91
# File 'lib/delayed/daemon.rb', line 89

def daemonized?
  !!@daemon
end

#pidObject



81
82
83
84
85
86
87
# File 'lib/delayed/daemon.rb', line 81

def pid
  if File.file?(pid_file)
    pid = File.read(pid_file).to_i
    pid = nil unless pid.positive?
  end
  pid
end

#pid_fileObject



77
78
79
# File 'lib/delayed/daemon.rb', line 77

def pid_file
  File.join(pid_folder, "delayed_jobs_pool.pid")
end

#status(print: true, pid: self.pid) ⇒ Object



14
15
16
17
18
19
20
21
22
23
# File 'lib/delayed/daemon.rb', line 14

def status(print: true, pid: self.pid)
  alive = pid && (Process.kill(0, pid) rescue false) && :running
  alive ||= :draining if pid && Process.kill(0, -pid) rescue false
  if alive
    puts "Delayed jobs #{alive}, pool PID: #{pid}" if print
  elsif print && print != :alive
    puts "No delayed jobs pool running"
  end
  alive
end

#stop(kill: false, pid: self.pid) ⇒ Object

stop the currently running daemon (not this current process, the one in the pid_file)



53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
# File 'lib/delayed/daemon.rb', line 53

def stop(kill: false, pid: self.pid)
  alive = status(pid: pid, print: false)
  if alive == :running || (kill && alive == :draining)
    puts "Stopping pool #{pid}..."
    signal = kill ? "TERM" : "QUIT"
    begin
      Process.kill(signal, pid)
    rescue Errno::ESRCH
      # ignore if the pid no longer exists
    end
    wait(kill)
  else
    status
  end
end

#wait(kill) ⇒ Object



69
70
71
72
73
74
75
# File 'lib/delayed/daemon.rb', line 69

def wait(kill)
  if kill
    sleep(0.5) while status(pid: pid, print: false)
  else
    sleep(0.5) while status(pid: pid, print: false) == :running
  end
end