Ich versuche, einen Ruby-Prozess auf Windows, um laichen so etwas wie dies mit:Spawned Ruby-Prozess auf Windows stirbt, wenn Shell beendet wird
p1 = spawn('ruby', 'loop.rb', [:out, :err] => ['process.log', "w"], :new_pgroup => true)
Ich löse auch dann aus dem Verfahren über:
p1.detach
Das sollte, soweit ich weiß, einen neuen Prozess schaffen, der unabhängig vom Elternteil ist. Ich verwende sogar den Parameter new_pgroup, um sicherzustellen, dass der neue Prozess seine eigene Prozessgruppe erhält.
Wenn ich mein Skript ausführe, wird der Unterprozess gestartet und läuft weiter. Die Ausführung des Skripts, das den Unterprozess hervorbringt, ist ebenfalls abgeschlossen. Wenn ich nun die Shell schließe, stirbt der Subprozess ab. Ich würde erwarten, dass es weiter läuft (unter OS X und Linux). Ich kann nicht herausfinden, ob dies ein Fehler in der Ruby-Laufzeit unter Windows ist oder ob dies eine Einschränkung von Windows ist und wie es Prozesse verarbeitet.
Der Vollständigkeit der vollständige Ruby-Code von dem, was ich zu tun versucht:
spawner.rb: über ruby spawner.rb
ausgeführt werden und laicht gerade einen neuen Teilprozess. Der Prozess erstellt loop.rb, die nur eine Endlosschleife ist. Je nach Betriebssystem gibt es einen anderen Parameter für die Erstellung der Prozessgruppe an.
require "tempfile"
require 'rbconfig'
class SpawnTest
def self.spawn_process
if os == :windows
p1 = spawn('ruby', 'loop.rb', [:out, :err] => ['process.log', "w"], :new_pgroup => true)
else
p1 = spawn('ruby', 'loop.rb', [:out, :err] => ['process.log', "w"], :pgroup => true)
end
# Detach from the processes so they will keep running
puts p1
Process.detach(p1)
end
def self.os
@os ||= (
host_os = RbConfig::CONFIG['host_os']
case host_os
when /mswin|msys|mingw|cygwin|bccwin|wince|emc/
:windows
when /darwin|mac os/
:macosx
when /linux/
:linux
when /solaris|bsd/
:unix
else
raise Error::WebDriverError, "unknown os: #{host_os.inspect}"
end
)
end
end
if __FILE__ == $0
SpawnTest.spawn_process
end
loop.rb
$stdout.sync = true
$stderr.sync = true
i = 0
while i < 10000
$stdout.puts "Iteration #{i}"
sleep 1
i = i + 1
end
$stdout.puts "Bye from #{Process.pid}"
fand ich die win32-process gem während meiner Untersuchungen. Es scheint Win32-API-Aufrufe zu verwenden, um Prozesse zu spawnen. Weiß jemand, ob diese Bibliothek das Problem beheben würde?
Jede Hilfe wird geschätzt.
Für was es wert ist, löst der win32-Prozess Edelstein mein Problem. Damit kann ich unter Windows Unterprozesse erstellen, die beim Schließen des Terminals nicht abstürzen. Ich weiß immer noch nicht, ob das Problem, das ich mit Kernel.spawn unter Windows sehe, auf einen Fehler, falsche Optionen oder ein mir unbekanntes "Feature" von Windows zurückzuführen ist. – Hardy
Können Sie bestätigen, dass die erstellten Prozesse tatsächlich in separaten Gruppen mit einem Tool wie [Process Explorer] (https://technet.microsoft.com/en-us/sysinternals/processexplorer.aspx) erstellt wurden? –
Ich nehme an, du meinst den TaskManager !? Ich kann die PGID dort nicht sehen. Ich sehe nur die Prozess-ID. Irgendeine Idee, wie man die PGID für einen laufenden Prozess unter Windows bekommt? Ich habe mit Cygwin und 'ps -W' versucht und ich kann den Prozess und eine Spalte für PGID sehen, aber es ist ziemlich viel '0' für alle Prozesse unabhängig. Ich glaube nicht, dass diese Ausgabe zuverlässig ist. – Hardy