如何立即停止正在运行单元测试的Python子进程?终止和杀死无效
我有一个使用Tkinter做的图形界面,它运行着两个线程,一个是主线程负责界面,另一个是工作线程。工作线程用下面的代码创建了一个子进程:
myProcess = subprocess.Popen(['python', '-u', 'runTests.py'],
stdout=subprocess.PIPE,
stderr=subprocess.STDOUT)
文件runTests.py做了一些准备工作,然后使用下面的命令运行一个单元测试文件:
execfile('myUnitTests.py')
文件myUnitTests.py里有几个单元测试,有些测试运行时间超过五分钟。
从界面上,我点击一个按钮来停止测试的运行。这时,工作线程会发送一个信号去停止子进程:
myProcess.terminate()
但是,terminate命令并不会立刻停止这个进程,它会等到当前的单元测试运行完毕后才终止进程。
我试过使用os.kill
,但结果和terminate()
是一样的。
有没有什么办法可以让我的程序更灵敏,能够立刻杀掉这个子进程呢?
1 个回答
2
Python的文档 [ http://docs.python.org/library/signal.html ] 说:
- 虽然从Python用户的角度来看,信号处理程序是异步调用的,但它们只能在Python解释器的“原子”指令之间发生。这意味着在进行一些纯C语言实现的长时间计算时(比如在大文本上进行正则表达式匹配),信号的到达可能会被延迟很长时间。
所以,如果你的五分钟单元测试正在进行“纯C实现的长时间计算”,而且你的单元测试框架安装了一个处理myProcess.kill
替代myProcess.terminate
(或者,如果你没有2.6版本,可以用myProcess.send_signal(9)
)。SIGKILL
信号是无法被捕获的,应该会立即生效。
警告:任何在你退出单元测试框架时应该执行的清理操作都不会被执行。