断言在 python 中调用函数后忽略函数的其余部分

Ignore the rest of a function after asserting that a function is called in python

提问人:Mounir 提问时间:8/19/2023 最后编辑:quamranaMounir 更新时间:8/19/2023 访问量:65

问:

在 Python 中,我们想要断言在调用另一个函数时调用了一个函数。但是,我们希望在调用所需函数后忽略执行。当我们不知道函数的其余部分时,就会出现这种必要性。稍后将要开发的函数的其余部分可能会从外部环境(如数据库网关)调用对象。典型的解决方案是模拟该对象。然而,当我们练习TDD时,我们可能还没有弄清楚其余的功能。因此,我们需要忽略它。 这是我想要开发的功能:

class A:
    def func(self):
        self.a()
        self.b() # the rest of the function that we do not develop yet and we want to ignore during the test because actually, we do not even know if there is actually a b function.`

测试功能

def test_a_is_called_during_func():
    mocked_a = Mock()
    with patch("A.a", new= mocked_a):
        A().func()
    mocked_a.assert_called_once()

我们需要在测试中添加一些东西来忽略 ,这改进了我们的测试设计,并使其独立,如果我们向函数添加一些东西,则无需返回此测试。b()

python 模拟 pytest tdd clean-architecture

评论

0赞 quamrana 8/19/2023
如果你是,你是怎么写到电话的?A.func()b()"are practising TDD"
0赞 Mounir 8/19/2023
对不起,我会更正代码。该代码实际上不是我在 python 中的实际代码。谢谢你的评论。
0赞 quamrana 8/19/2023
我看到您已经对代码片段进行了更改,但它们似乎只是使其运行的修复程序。我的评论成立。怎么可能打电话?应该在某个地方有一个测试,一旦编写,就需要该调用。如果不再执行该调用,则测试应失败。A.func()b()
0赞 Mounir 8/19/2023
我们实际上还没有开发 b()。我们甚至不知道是否存在 b()。我想以增量方式定义我的测试。func 稍后可能需要调用 b()。但是,我们还不知道 b。可能,将是一个依赖注入。
0赞 quamrana 8/19/2023
只需删除对的调用,直到测试调用它。b()

答:

2赞 slothrop 8/19/2023 #1

实现此目的的一种方法是让 method 的模拟版本抛出您创建的一些自定义异常。然后,除了调用 之外,不会继续执行 ,并且您可以在测试中捕获异常。例如:afunca

class AbortTestedFunctionException(Exception):
    pass


def test_a_is_called_during_func():
    mocked_a = Mock(side_effect=AbortTestedFunctionException())

    with patch("A.a", new=mocked_a):
        try:
            A().func()
        except AbortTestedFunctionException:
            pass
    mocked_a.assert_called_once()

这不是万无一失的:如果使用 执行一揽子异常处理策略,它将无法按预期工作。functry... except Exception

评论

0赞 Mounir 8/19/2023
感谢您编写解决方案。我希望这将有助于其他人改进他们的测试。
0赞 Mounir 8/19/2023
如果您有兴趣,我们可能会就此发表会议论文?
0赞 slothrop 8/19/2023
谢谢你的提问,但我不得不说不,其他一切都在我的盘子里!
0赞 Mounir 8/19/2023
我可能会根据这次谈话在纸上写一个会议,所以我需要征得你的许可:)
0赞 slothrop 8/19/2023
没问题,很高兴你使用我在这里说的任何话:)