diff --git a/README.md b/README.md index 930b0ac..8efc562 100644 --- a/README.md +++ b/README.md @@ -148,8 +148,6 @@ process.leader = true process.start ``` -Note this does not work on Windows. - #### Detach from parent ```ruby diff --git a/lib/childprocess/abstract_process.rb b/lib/childprocess/abstract_process.rb index 5d70208..93fd064 100644 --- a/lib/childprocess/abstract_process.rb +++ b/lib/childprocess/abstract_process.rb @@ -28,9 +28,7 @@ class AbstractProcess # Set this to true to make the child process the leader of a new process group # # This can be used to make sure that all grandchildren are killed - # when the child process dies on non-Windows. - # - # Note that grandchildren are not killed on Windows even when the process is the leader of a new process group. + # when the child process dies. # attr_accessor :leader diff --git a/lib/childprocess/process_spawn_process.rb b/lib/childprocess/process_spawn_process.rb index 7134caa..11bd3a6 100644 --- a/lib/childprocess/process_spawn_process.rb +++ b/lib/childprocess/process_spawn_process.rb @@ -112,19 +112,15 @@ def send_signal(sig) assert_started log "sending #{sig}" - ::Process.kill sig, _pid - end - - def _pid if leader? if ChildProcess.unix? - -@pid # negative pid == process group + ::Process.kill sig, -@pid # negative pid == process group else - ChildProcess.logger.warn "ChildProcess#stop on leader of a new process group does not kill subprocess on Windows" - @pid + output = `taskkill /F /T /PID #{@pid}` + log output end else - @pid + ::Process.kill sig, @pid end end end diff --git a/spec/childprocess_spec.rb b/spec/childprocess_spec.rb index a4dddab..4a949c3 100644 --- a/spec/childprocess_spec.rb +++ b/spec/childprocess_spec.rb @@ -299,52 +299,20 @@ } end - if ChildProcess.unix? - it 'kills the full process tree on unix' do - Tempfile.open('kill-process-tree') do |file| - process = write_pid_in_sleepy_grand_child(file.path) - process.leader = true - process.start - - pid = wait_until(30) do - Integer(rewind_and_read(file)) rescue nil - end - - process.stop - expect(alive?(process.pid)).to eql(false) + it 'kills the full process tree' do + Tempfile.open('kill-process-tree') do |file| + process = write_pid_in_sleepy_grand_child(file.path) + process.leader = true + process.start - wait_until(3) { expect(alive?(pid)).to eql(false) } + pid = wait_until(30) do + Integer(rewind_and_read(file)) rescue nil end - end - elsif ChildProcess.windows? - it 'does not kill the full process tree on windows' do - Tempfile.open('no-kill-process-tree') do |file| - process = write_pid_in_sleepy_grand_child(file.path) - process.leader = true - process.start - pid = wait_until(30) do - Integer(rewind_and_read(file)) rescue nil - end + process.stop + expect(process).to be_exited - log = StringIO.new - original_logger = ChildProcess.logger - begin - ChildProcess.logger = Logger.new(log) - ChildProcess.logger.level = Logger::WARN - process.stop - ensure - ChildProcess.logger = original_logger - end - expect(log.string).to include("ChildProcess#stop on leader of a new process group does not kill subprocess on Windows") - - expect(alive?(process.pid)).to eql(false) - - # The grand child is not killed on Windows: - expect(alive?(pid)).to eql(true) - Process.kill(:SIGKILL, pid) - wait_until(3) { expect(alive?(pid)).to eql(false) } - end + wait_until(3) { expect(alive?(pid)).to eql(false) } end end