mirror of
https://github.com/discourse/discourse.git
synced 2025-02-16 23:32:44 +08:00
DEV: handle termination cleanly in autospec
This commit is contained in:
parent
91b73e0c2d
commit
cc3fc87dd7
|
@ -30,7 +30,15 @@ class Autospec::Manager
|
|||
|
||||
def run
|
||||
Signal.trap("HUP") { stop_runners; exit }
|
||||
Signal.trap("INT") { stop_runners; exit }
|
||||
|
||||
Signal.trap("INT") do
|
||||
begin
|
||||
stop_runners
|
||||
rescue => e
|
||||
puts "FAILED TO STOP RUNNERS #{e}"
|
||||
end
|
||||
exit
|
||||
end
|
||||
|
||||
ensure_all_specs_will_run
|
||||
start_runners
|
||||
|
|
|
@ -3,11 +3,16 @@ require "autospec/rspec_runner"
|
|||
module Autospec
|
||||
|
||||
class SimpleRunner < RspecRunner
|
||||
def initialize
|
||||
@mutex = Mutex.new
|
||||
end
|
||||
|
||||
def run(specs)
|
||||
puts "Running Rspec: " << specs
|
||||
# kill previous rspec instance
|
||||
self.abort
|
||||
@mutex.synchronize do
|
||||
self.abort
|
||||
end
|
||||
# we use our custom rspec formatter
|
||||
args = ["-r", "#{File.dirname(__FILE__)}/formatter.rb",
|
||||
"-f", "Autospec::Formatter", specs.split].flatten.join(" ")
|
||||
|
@ -18,24 +23,42 @@ module Autospec
|
|||
env["LOAD_PLUGINS"] = "1"
|
||||
puts "Loading plugins while running specs"
|
||||
end
|
||||
@pid = Process.spawn(env, "bin/rspec #{args}")
|
||||
_, status = Process.wait2(@pid)
|
||||
pid =
|
||||
@mutex.synchronize do
|
||||
@pid = Process.spawn(env, "bin/rspec #{args}")
|
||||
end
|
||||
|
||||
_, status = Process.wait2(pid)
|
||||
|
||||
status.exitstatus
|
||||
end
|
||||
end
|
||||
|
||||
def abort
|
||||
if @pid
|
||||
Process.kill("INT", @pid) rescue nil
|
||||
while (Process.getpgid(@pid) rescue nil)
|
||||
sleep 0.001
|
||||
end
|
||||
@pid = nil
|
||||
if pid = @pid
|
||||
Process.kill("TERM", pid) rescue nil
|
||||
wait_for_done(pid)
|
||||
pid = nil
|
||||
end
|
||||
end
|
||||
|
||||
def stop
|
||||
abort
|
||||
# assume sigint on child will take care of this?
|
||||
if pid = @pid
|
||||
wait_for_done(pid)
|
||||
end
|
||||
end
|
||||
|
||||
def wait_for_done(pid)
|
||||
i = 3000
|
||||
while (i > 0 && Process.getpgid(pid) rescue nil)
|
||||
sleep 0.001
|
||||
i -= 1
|
||||
end
|
||||
if (Process.getpgid(pid) rescue nil)
|
||||
STDERR.puts "Terminating rspec #{pid} by force cause it refused graceful termination"
|
||||
Process.kill("KILL", pid)
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
|
|
@ -61,11 +61,14 @@ class Demon::Base
|
|||
end
|
||||
end
|
||||
|
||||
def stop_signal
|
||||
"HUP"
|
||||
end
|
||||
|
||||
def stop
|
||||
@started = false
|
||||
if @pid
|
||||
# TODO configurable stop signal
|
||||
Process.kill("HUP", @pid)
|
||||
Process.kill(stop_signal, @pid)
|
||||
|
||||
wait_for_stop = lambda {
|
||||
timeout = @stop_timeout
|
||||
|
@ -82,7 +85,7 @@ class Demon::Base
|
|||
wait_for_stop.call
|
||||
|
||||
if alive?
|
||||
STDERR.puts "Process would not terminate cleanly, force quitting. pid: #{@pid}"
|
||||
STDERR.puts "Process would not terminate cleanly, force quitting. pid: #{@pid} #{self.class}"
|
||||
Process.kill("KILL", @pid)
|
||||
end
|
||||
|
||||
|
|
|
@ -6,6 +6,10 @@ class Demon::RailsAutospec < Demon::Base
|
|||
"rails-autospec"
|
||||
end
|
||||
|
||||
def stop_signal
|
||||
"TERM"
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def after_fork
|
||||
|
|
Loading…
Reference in New Issue
Block a user