2014-01-13 156 views
6

我一直有一个问题,我可以杀死产生节点的进程,但节点不会被杀死。有没有人有任何建议我可以做到这一点?子进程杀死子进程但不是子进程的进程

我的一些最新的失败尝试做到这一点是:

node.terminate() 

node.send_signal(signal.SIGINT) 
下面

是代码:

from subprocess import Popen 
import json 
import sys 
import os 
import signal 
import requests 

FNULL = open(os.devnull, 'w') 

json_data = open('nodes.json', 'r').read() 
data = json.loads(json_data) 

port = data['port'] 

# launch hub 
hub = Popen('java -jar selenium-server-standalone-2.37.0.jar -role hub -port %s' % port, stdout=FNULL, stderr=FNULL, shell=True) 

#launch nodes 
nodes = [] 
for node in data['nodes']: 
    options = '' 
    if node['name'] == 'CHROME': 
     options += '-Dwebdriver.chrome.driver=../grid/chromedriver ' 
    #options += ' -browser browserName='+node['name']+' maxInstances='+str(node['maxInstances']) 
    nodes.append(Popen('java -jar selenium-server-standalone-2.37.0.jar -role node -hub http://localhost:%i/grid/register %s' % (port, options), stdout=FNULL, stderr=FNULL, shell=True)) 

# wait for user input 
print "type 'q' and ENTER to close the grid:" 
while True: 
    line = sys.stdin.readline() 
    if line == 'q\n': 
     break 

# close nodes 
for node in nodes: 
    #node.terminate() 
    node.send_signal(signal.SIGINT) 

# close hub 
r = requests.get('http://localhost:'+str(port)+'/lifecycle-manager?action=shutdown') 

至于即时知道,我m基本上被迫使用shell = True,重定向工作 在t中处理孩子的stdout/stderr他父Python进程是不是一种选择,因为我无法在非等待的方式做它找到的功能(和孩子正在运行而父蟒蛇过程中必须做其他事情)

# close nodes 
for node in nodes: 
    node.send_signal(signal.SIGINT) 
    node.terminate()  

这似乎杀死除1个节点以外的所有进程。不总是一样的

+0

尝试添加:''node.wait()'' –

+0

@JamesMills添加node.wait()似乎阻止关机,可能是由于节点仍处于活动状态(因此它只是在等待它们完成) – Calum

+0

如果你不设置'shell = True'会怎么样? – kojiro

回答

2

你可以尝试使用os.killpg。该函数将信号发送给进程组,如果进程不改变进程组,它应该工作。

import os 
import signal 

os.killpg(os.getpgid(pid), signal.SIGINT) 

注意,这个过程将组如果要创建下外壳(bash中,zsh中,等)过程中发生变化,在这种情况下,更复杂的技术应该被使用。

+1

os.killpg(os.getpgid(pid),signal.SIGINT) – DanJ

+0

@DanJ谢谢,我编辑过我的回答 – maxbublis

+1

不幸的是,这也杀死了调用程序。您需要将“preexec_fn = os.setsid”添加到“Popen”。 –