Python subprocess.popen与主进程分离(Linux)

Python subprocess.popen与主进程分离(Linux),python,linux,subprocess,popen,Python,Linux,Subprocess,Popen,我正试图打开一个子流程,但已将其与调用它的父脚本分离。现在,如果我调用subprocess.popen,父脚本崩溃,子进程也会死掉 我知道windows有几个选项,但我没有找到*nix的任何选项 我也不需要使用subprocess调用它。我所需要的只是能够标定另一个分离的进程并获得pid。我认为这应该可以实现以下目的: 您可以创建将调用您的子进程的守护进程,传递detach\u process=True 对于linux,这根本不是问题。只需Popen()。例如,这里有一个小的垂死的恶魔.py #

我正试图打开一个子流程,但已将其与调用它的父脚本分离。现在,如果我调用subprocess.popen,父脚本崩溃,子进程也会死掉

我知道windows有几个选项,但我没有找到*nix的任何选项


我也不需要使用subprocess调用它。我所需要的只是能够标定另一个分离的进程并获得pid。

我认为这应该可以实现以下目的:


您可以创建将调用您的子进程的守护进程,传递
detach\u process=True

对于linux,这根本不是问题。只需
Popen()
。例如,这里有一个小的
垂死的恶魔.py

#!/usr/bin/python -u
from time import sleep
from subprocess import Popen
print Popen(["python", "-u", "child.py"]).pid
i = 0
while True:
    i += 1
    print "demon: %d" % i
    sleep(1)
    if i == 3:
        i = hurz # exception
#!/usr/bin/python -u
from time import sleep
i = 0
while True:
    i += 1
    print "child: %d" % i
    sleep(1)
    if i == 20:
        break
剥离一个
child.py

#!/usr/bin/python -u
from time import sleep
from subprocess import Popen
print Popen(["python", "-u", "child.py"]).pid
i = 0
while True:
    i += 1
    print "demon: %d" % i
    sleep(1)
    if i == 3:
        i = hurz # exception
#!/usr/bin/python -u
from time import sleep
i = 0
while True:
    i += 1
    print "child: %d" % i
    sleep(1)
    if i == 20:
        break

孩子继续计数(到控制台),而恶魔异常死亡。

我通过使用python守护进程执行以下操作,成功地让它工作:

process = subprocess.Popen(["python", "-u", "Child.py"])
    time.sleep(2)
    process.kill()
然后在Child.py中:

with daemon.DaemonContext():
    print("Child Started")
    time.sleep(30)
    print "Done"
    exit()
我会执行
process.kill()
,因为否则它会创建一个失效的python进程。我现在遇到的主要问题是popen返回的PID与流程的最终PID不匹配。我可以通过在Child.py中添加一个函数来使用pid更新数据库来解决这个问题


让我知道我是否遗漏了某些内容,或者这是一种可行的方法。

使用NOHUP选项分叉子脚本

可能相关:我看到了,但我没有尝试分离和退出。我需要父脚本继续运行,但如果它崩溃,我不希望子进程也停止。因此不要在父进程中调用
os.\u exit()
。。(它从链接的答案中检查活动状态配方中的PID)我认为这不起作用,除非您使用
shell=True
,如果不需要,这可能是一个负担。如果您的父python进程崩溃,您可以不受此影响。但是,如果将这种代码合并到处理异常的更高级别中,那么您将离开僵尸进程,除非您使用wait()或类似方法将其关闭。