问题 单元测试:如何断言同一方法的多个调用?


我有一个方法,它使用不同的参数调用另一个方法两次。

class A(object):
    def helper(self, arg_one, arg_two):
        """Return something which depends on arguments."""

    def caller(self):
        value_1 = self.helper(foo, bar)  # First call.
        value_2 = self.helper(foo_bar, bar_foo)  # Second call!

运用 assert_called_with 帮助我断言第一个电话,而不是第二个电话。甚至 assert_called_once_with 似乎没有帮助。我在这里想念的是什么?有没有办法测试这样的电话?


7339
2017-11-28 16:31


起源



答案:


您可以使用 mock_calls 其中包含对方法的所有调用。此列表包含第一个呼叫,第二个呼叫以及所有后续呼叫。所以你可以用。编写断言 mock_calls[1] 说明关于第二个电话的事情。


例如,如果 m = mock.Mock() 而代码呢 m.method(123) 然后你写:

assert m.method.mock_calls == [mock.call(123)]

断言调用列表 m.method 只是一个调用,即带参数123的调用。


10
2017-11-28 16:34



他们的文档中的示例没有多大意义。你能展示一个更好的例子吗? - byxor
@BrandonIbbotson我在上面的答案中添加了一个例子。 - Simeon Visser


答案:


您可以使用 mock_calls 其中包含对方法的所有调用。此列表包含第一个呼叫,第二个呼叫以及所有后续呼叫。所以你可以用。编写断言 mock_calls[1] 说明关于第二个电话的事情。


例如,如果 m = mock.Mock() 而代码呢 m.method(123) 然后你写:

assert m.method.mock_calls == [mock.call(123)]

断言调用列表 m.method 只是一个调用,即带参数123的调用。


10
2017-11-28 16:34



他们的文档中的示例没有多大意义。你能展示一个更好的例子吗? - byxor
@BrandonIbbotson我在上面的答案中添加了一个例子。 - Simeon Visser


要添加到Simon Visser的答案,您可以使用 unittest.TestCase  self.assertEqual() 方法而不是 assert 语法,我说在单元测试上下文中是一种更好的做法,因为你也可以添加注释,只要出错就会显示。

例如:

self.assertEqual(
    [
        mock.call(1, 'ValueA', True)),
        mock.call(2, 'ValueB', False)),
        mock.call(3, 'ValueC', False))
    ],
    mock_cur.execute.mock_calls,
    "The method was not called with the correct arguments."
) 

1
2017-10-05 10:12