我有一个类有一个昂贵的__init__
函数。我不想从测试中调用这个函数。在
在这个例子中,我创建了一个在__init__
中引发异常的类:
class ClassWithComplexInit(object):
def __init__(self):
raise Exception("COMPLEX!")
def get_value(self):
return 'My value'
我有第二个类,它构造ClassWithComplexInit
的实例并使用它的函数。在
我正试图围绕SystemUnderTest#my_func()
编写一些单元测试。我遇到的问题是无论我如何模拟ClassWithComplexInit
,总是执行__init__
函数并引发异常。在
class TestCaseWithoutSetUp(unittest.TestCase):
@mock.patch('mypackage.ClassWithComplexInit.get_value', return_value='test value')
def test_with_patched_function(self, mockFunction):
sut = SystemUnderTest()
result = sut.my_func() # fails, executes ClassWithComplexInit.__init__()
self.assertEqual('test value', result)
@mock.patch('mypackage.ClassWithComplexInit')
def test_with_patched_class(self, mockClass):
mockClass.get_value.return_value = 'test value'
sut = SystemUnderTest()
result = sut.my_func() # seems to not execute ClassWithComplexInit.__init__()
self.assertEqual('test value', result) # still fails
# AssertionError: 'test value' != <MagicMock name='ClassWithComplexInit().get_value()' id='4436402576'>
上面的第二种方法是我从this similar Q&A得到的,但它也不起作用。似乎不运行__init__
函数,但我的断言失败了,因为结果是一个模拟实例,而不是我的值。在
我还试图在setUp
函数中配置patch
实例,使用start
和{
class TestCaseWithSetUp(unittest.TestCase):
def setUp(self):
self.mockClass = mock.MagicMock()
self.mockClass.get_value.return_value = 'test value'
patcher = mock.patch('mypackage.ClassWithComplexInit', self.mockClass)
patcher.start()
self.addCleanup(patcher.stop)
def test_my_func(self):
sut = SystemUnderTest()
result = sut.my_func() # seems to not execute ClassWithComplexInit.__init__()
self.assertEqual('test value', result) # still fails
# AssertionError: 'test value' != <MagicMock name='mock().get_value()' id='4554658128'>
这似乎也避免了我的__init__
函数,但是我为get_value.return_value
设置的值没有得到尊重,get_value()
仍然返回一个MagicMock
实例。在
我如何模拟一个复杂的__init__
的类,它是由我测试的代码实例化的?理想情况下,我想要一个对TestCase类中的许多单元测试都有效的解决方案(例如,不需要patch
每个测试)。在
我使用的是Python版本2.7.6
。在
为什么不直接为测试创建子类并重写init呢?在
现在,
ClassWithComplexInit().get_value()
返回'My value'
,而不是引发异常。在首先,您需要使用与正在修补的名称相同的名称来创建
foo
,也就是说其次,您需要配置正确的模拟对象。您正在配置未绑定方法
^{pr2}$ClassWithComplexInit.get_value
,但需要配置ClassWithComplexInit.return_value.get_value
,这是一个Mock
对象,该对象将被foo.get_value()
调用。在相关问题 更多 >
编程相关推荐