问题描述
在下面显示的代码段中,我想测试run()
函数中的函数调用顺序,即f_3
在f_2
之后被调用,而{{1}之后被调用}:
f_1
有什么办法可以使用class TestMock:
def f_1(self) -> None:
pass
def f_2(self) -> None:
pass
def f_3(self) -> None:
pass
def run(self) -> None:
self.f_1()
self.f_2()
self.f_3()
来做到这一点?我曾尝试在测试文件中模拟pytest-mock
,f_1
和f_2
函数,并将f_3
与assert_has_calls
一起使用,但是没有成功。>
在此先感谢您的帮助或提示!
最好, 阿列克谢
解决方法
使用any_order=False
使您处在正确的轨道上,您只需要了解attach_mock
功能:
import yourmodule
def test_something(mocker):
mock = mocker.MagicMock()
mock.attach_mock(mocker.patch("yourmodule.TestMock.f_1"),"f_1")
mock.attach_mock(mocker.patch("yourmodule.TestMock.f_2"),"f_2")
mock.attach_mock(mocker.patch("yourmodule.TestMock.f_3"),"f_3")
yourinstance = yourmodule.TestMock()
yourinstance.run()
mock.assert_has_calls(
[
mocker.call.f_1(),mocker.call.f_2(),mocker.call.f_3(),],any_order=False,)
,
我已经完全切换到unittest.mock
,现在具有以下工作代码:
@mock.patch('.'.join([__name__,'TestMock','f_3']))
@mock.patch('.'.join([__name__,'f_2']))
@mock.patch('.'.join([__name__,'f_1']))
def test_order_2(f_1: mock.NonCallableMock,f_2: mock.NonCallableMock,f_3: mock.NonCallableMock) -> None:
manager = mock.Mock()
manager.attach_mock(f_1,'f_1')
manager.attach_mock(f_2,'f_2')
manager.attach_mock(f_3,'f_3')
obj = TestMock()
obj.run()
manager.assert_has_calls([mock.call.f_1,mock.call.f_2,mock.call.f_3],any_order=False)
这里是问题:我不太了解属性名称的含义,因此,它们是强制性的,但对我来说唯一合理的名称是函数名称本身...我已经修改了属性名称如下:
@mock.patch('.'.join([__name__,'f_1']))
def test_order_1(f_1: mock.NonCallableMock,f_1._extract_mock_name())
manager.attach_mock(f_2,f_2._extract_mock_name())
manager.attach_mock(f_3,f_3._extract_mock_name())
obj = TestMock()
obj.run()
manager.assert_has_calls([mock.call.f_1,any_order=False)
很高兴听到您对此的看法!
顺便说一下,为什么f_*
个模拟对象是mock.NonCallableMoc
类型的?我希望它们会被伪函数(Collable
)取代...
再次感谢您的帮助!
最好, 阿列克谢