python unittest assertRaises 在 assertRaises 失败时抛出异常
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1230498/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
python unittest assertRaises throws exception when assertRaises fails
提问by
I've got code where assertRaises throws an exception when assertRaises fails. I thought that if assertRaises fails then the test would fail and I'd get a report at the end that says the test failed. I wasn't expecting the exception to be thrown. Below is my code. I'm I doing something wrong? I'm using Python 2.6.2.
我有代码,当 assertRaises 失败时,assertRaises 会抛出异常。我认为如果 assertRaises 失败,那么测试就会失败,最后我会得到一个报告,说测试失败。我没想到会抛出异常。下面是我的代码。我是不是做错了什么?我正在使用 Python 2.6.2。
import unittest
class myClass:
def getName(self):
raise myExcOne, "my exception one"
#raise myExcTwo, "my exception two"
#return "a"
class myExcOne(Exception):
"exception one"
class myExcTwo(Exception):
"exception two"
class test_myClass(unittest.TestCase):
def setUp(self):
self.myClass = myClass()
def testgetNameEmpty(self):
#self.assertRaises(myExcOne,self.myClass.getName)
#self.assertRaises(myExcTwo,self.myClass.getName)
try:
self.assertRaises(myExcTwo,self.myClass.getName)
except Exception as e:
pass
if __name__ == "__main__":
#unittest.main()
suite = unittest.TestLoader().loadTestsFromTestCase(test_myClass)
unittest.TextTestRunner(verbosity=2).run(suite)
回答by mhawke
The code as posted is wrong. For a start, class myClass():
shoudl be class myClass:
. Also if name == "main":
should be:
发布的代码是错误的。首先,class myClass():
应该是class myClass:
。还if name == "main":
应该是:
if __name__ == "__main__":
unittest.main()
Apart from these problems, this fails because getName()
is raising exception myExcOne
and your test expects exception myExcTwo
.
除了这些问题之外,这会失败,因为getName()
正在引发异常myExcOne
并且您的测试需要异常myExcTwo
。
Here is some code that works. Please edit the code in your question so that it is easy for us to cut and paste it into a Python session:
这是一些有效的代码。请编辑您问题中的代码,以便我们可以轻松地将其剪切并粘贴到 Python 会话中:
import unittest
class myExcOne(Exception): "exception one"
class myExcTwo(Exception): "exception two"
class myClass:
def getName(self):
raise myExcTwo
class test_myClass(unittest.TestCase):
def setUp(self):
self.myClass = myClass()
def testgetNameEmpty(self):
#self.assertRaises(myExcOne,self.myClass.getName)
self.assertRaises(myExcTwo,self.myClass.getName)
if __name__ == "__main__":
unittest.main()
回答by Alex Martelli
Starting with an aside, the ()
after the classname in a class
statement is perfectly correct in modern Python -- not an error at all.
与旁边,开始()
在类名之后class
的语句是现代的Python完全正确的-不是错误的。
On the meat of the issue, assertRaises(MyException, foo)
isdocumented to propagate exceptions raised by calling foo()
whose type is NOT a subclass of MyException
-- it only catches MyException
and subclasses thereof. As your code raises an exception of one type and your test expects one of a different unrelated type, the raised exception will then propagate, as per the docs of the unittest
module, here, and I quote:
在问题的核心上,assertRaises(MyException, foo)
被记录为传播通过调用foo()
其类型不是的子类而引发的异常MyException
——它只捕获MyException
及其子类。当您的代码引发一种类型的异常并且您的测试期望一种不同的不相关类型时,引发的异常将传播,根据unittest
模块的文档,here,我引用:
The test passes if exceptionis raised, is an error if another exception is raised, or fails if no exception is raised.
如果引发异常,则测试通过,如果引发另一个异常,则测试为错误,如果未引发异常,则测试失败。
And "is an error" means "propagates the other exception".
“是一个错误”意味着“传播另一个异常”。
As you catch the exception propagating in your try/except block, you nullify the error, and there's nothing left for unittest
to diagnose. If your purpose is to turn this error into a failure (a debatable strategy...), your except
block should call self.fail
.
当您捕获在 try/except 块中传播的异常时,您消除了错误,并且没有什么unittest
可诊断的了。如果您的目的是将此错误转化为失败(一个有争议的策略......),您的except
块应该调用self.fail
.