class Restartable
Main interface
Constants
- WAIT_SIGNALS
Public Class Methods
new(options = {}, &block)
click to toggle source
# File lib/restartable.rb, line 18 def initialize(options = {}, &block) @on_restart = Array(options[:on_restart]) @block = block run! end
version()
click to toggle source
# File lib/restartable.rb, line 12 def self.version Gem.loaded_specs['restartable'].version.to_s rescue 'DEV' end
Private Instance Methods
children_pids()
click to toggle source
# File lib/restartable.rb, line 115 def children_pids pgrp = Process.getpgrp Sys::ProcTable.ps.select do |pe| pgrp == case when pe.respond_to?(:pgid) then pe.pgid when pe.respond_to?(:pgrp) then pe.pgrp when pe.respond_to?(:ppid) then pe.ppid else fail 'Can\'t find process group id' end end.map(&:pid) - [$PROCESS_ID] end
interrupt!()
click to toggle source
# File lib/restartable.rb, line 50 def interrupt! if @interrupted @stop = true $stderr << "Don't restart!\n".red.bold else @interrupted = true end end
kill_children!()
click to toggle source
# File lib/restartable.rb, line 72 def kill_children! until children_pids.empty? $stderr << "Killing children…\n".yellow.bold signal_pair = 0 begin time, signal = WAIT_SIGNALS[signal_pair] Timeout.timeout(time) do Process.waitall wait_children end rescue Timeout::Error $stderr << "…SIG#{signal}…\n".yellow signal_children!(signal) retry if WAIT_SIGNALS[signal_pair += 1] end end end
run!()
click to toggle source
# File lib/restartable.rb, line 26 def run! Signal.trap('INT'){ interrupt! } Signal.trap('TERM'){ terminate! } until @stop @interrupted = nil $stderr << "^C to restart, double ^C to stop\n".green @cpid = fork do Signal.trap('INT', 'DEFAULT') Signal.trap('TERM', 'DEFAULT') @block.call end sleep 0.1 until @interrupted kill_children! break if @stop $stderr << "Waiting ^C 0.5 second than restart…\n".yellow.bold sleep 0.5 break if @stop @on_restart.each(&:call) end end
signal_children!(signal)
click to toggle source
# File lib/restartable.rb, line 105 def signal_children!(signal) children_pids.each do |pid| begin Process.kill(signal, pid) rescue Errno::ESRCH next end end end
terminate!()
click to toggle source
# File lib/restartable.rb, line 59 def terminate! interrupt! interrupt! end
wait_children()
click to toggle source
# File lib/restartable.rb, line 92 def wait_children children_pids.each do |pid| begin loop do Process.kill(0, pid) sleep 1 end rescue Errno::ESRCH next end end end