2016-11-06 279 views
5

我正在使用python的unittest,并且想编写一个测试,启动一些线程并等待它们完成。线程执行一个包含一些unittest断言的函数。如果任何断言失败,我希望测试失败。这似乎并非如此。Python单元测试和多线程

编辑:最小可运行的例子(python3)

import unittest 
import threading 

class MyTests(unittest.TestCase): 

def test_sample(self): 
    t = threading.Thread(target=lambda: self.fail()) 
    t.start() 
    t.join() 

if __name__ == '__main__': 
    unittest.main() 

并且输出是:

sh-4.3$ python main.py -v                                                    
test_sample (__main__.MyTests) ... Exception in thread Thread-1:                                          
Traceback (most recent call last):                                                  
    File "/usr/lib64/python2.7/threading.py", line 813, in __bootstrap_inner                                        
    self.run()                                                       
    File "/usr/lib64/python2.7/threading.py", line 766, in run                                           
    self.__target(*self.__args, **self.__kwargs)                                              
    File "main.py", line 7, in <lambda>                                                 
    t = threading.Thread(target=lambda: self.fail())                                             
    File "/usr/lib64/python2.7/unittest/case.py", line 450, in fail                                          
    raise self.failureException(msg)                                                 
AssertionError: None                                                     

ok                                                          

----------------------------------------------------------------------                                         
Ran 1 test in 0.002s                                                     

OK  
+0

我认为你正在讨论这个错误。向我们展示一个被测功能的样本。 – Dan

+0

@Dan:它可以是任何东西,即使是最简单的'def test_fail(self):self.fail()' –

+0

所以你不应该在测试用例中触发线程。如果被测试的函数触发线程,则可以通过模拟目标函数并针对调用进行断言来测试该行为。你甚至可以模拟线程类。 – Dan

回答

1

的Python unittest断言是由异常连通,所以你必须确保异常结束在主线程中。因此,对于一个线程,意味着你必须运行.join(),因为这将引发从线程异常过度到主线程:

t = threading.Thread(target=lambda: self.assertTrue(False)) 
    t.start() 
    t.join() 

还要确保你没有任何try/except块可能吃起来在unittest之前的例外可以注册它们。

编辑self.fail()从一个线程调用时确实没有传达,即使.join()存在。不知道这是怎么回事。

+1

我试过你的例子。它不适用于我(python3.x),并产生与我的代码相同的结果。测试仍然通过。 –

0

在我的主线程中,我通过检查它们的退出代码来检测子进程失败(非零失败)。

proc.join() 
self.assertEqual(proc.exitcode, 0, 'Sub-process failed, check output for stack trace') 
+1

子进程不是线程。 –