Python模拟失败的呼叫断言

时间:2018-12-17 05:25:12

标签: python unit-testing mocking

我一直在阅读python模拟,但无法理解以下代码为何失败。

我有两个类,一个Potato和一个PotatoBag,如下所示。 Figure存储在food.py中,而Report存储在bag.py中。

class Potato:
    def create_potato(self):
        pass

    def output_potato(self):
        pass


class PotatoBag:
    def __init__(self, potatoes):
        self.potatoes = potatoes

    def output_to_file(self):
        for fig in self.potatoes:
            fig.create_potato()
            fig.output_potato()

当前,我正在尝试对输出方法进行单元测试,以便Report使用模拟从Figure正确调用create_figureoutput_figure。这是我的测试代码:

from unittest.mock import MagicMock, patch
from bag import PotatoBag
from food import Potato
import pytest

@pytest.fixture(scope='module')
def potatoes():
    x = Potato()
    y = Potato()
    return [x, y]

@patch('food.Potato')
def test_output_to_file(mock_potato, potatoes):

    test_potato_bag = PotatoBag(potatoes)
    test_potato_bag.output_to_file()

    mock_potato.return_value.create_potato.assert_called()
    mock_potato.return_value.output_potato.assert_called()

立即pytest产生一个AssertionError,说明从未调用过create_figure。

_mock_self = <MagicMock name='Potato().create_potato' id='140480853451272'>

    def assert_called(_mock_self):
        """assert that the mock was called at least once
            """
        self = _mock_self
        if self.call_count == 0:
            msg = ("Expected '%s' to have been called." %
                   self._mock_name or 'mock')
>           raise AssertionError(msg)
E           AssertionError: Expected 'create_potato' to have been called.

/home/anaconda3/lib/python3.7/unittest/mock.py:792: AssertionError

我的代码有什么问题?

1 个答案:

答案 0 :(得分:1)

您是从灯具中向Report传递Figures列表,而不是模拟。

将测试更改为...

@patch('figure.Figure')
def test_output_to_file(mock_figure, figures):

    test_report = Report([mock_figure])
    test_report.output_to_file()

    mock_figure.create_figure.assert_called_once()
    mock_figure.output_figure.assert_called_once()

这可以解决测试output_to_file正确地调用Figure上的函数的问题,而实际上不必担心设置图形并处理调用这些函数可能带来的任何副作用或其他复杂性。可以省去Figure的单元测试的烦恼;)