【问题标题】:Python mockito: mock a single functionPython mockito:模拟单个函数
【发布时间】:2022-09-28 04:00:07
【问题描述】:

我需要在 mockito 中模拟单个函数(不是类成员,也不是导入模块的一部分)。我读到 mockito 模拟是可调用的,所以我可以使用 __call__() 函数,但不幸的是它对我不起作用。有一个旧的question 关于它在 3 年前被问到,我想从那时起可能有一些变化(所以请不要将此问题作为该旧线程的重复来解决)。

这是示例代码(取自那个旧线程):

import os
import unittest
from mockito import when, verify

def interesting_function():
    os.system(\'mkdir some_dir\')
    another_function()

def another_function():
    print(\'Done\')

class InterestingFunctionTests(unittest.TestCase):
    def test_interesting_function(self):
         when(another_function).__call__().thenReturn()
         interesting_function()
         verify(another_function).__call__()

它应该可以工作我收到以下错误:

mockito.verification.VerificationError:
Wanted but not invoked:

    __call__()

Instead got:

    Nothing

如何在 mockito 中模拟和验证单个函数?

我很感激任何帮助。

    标签: python unit-testing mockito


    【解决方案1】:

    老问题的答案是错误的。而且当时也是错的。

    你读到“模拟是可调用的”,这只是意味着

    m = mock()
    m()  # => None
    

    模拟已预先配置为可调用。这是一个特殊情况,因为否则普通的模拟完全是愚蠢的。 (用户必须配置它们。)

    但是在这里你甚至不需要模拟,你想要补丁(或:猴子补丁)功能。实际上,您不修补功能(这是什么意思),您猴子修补模块函数存在。模块也是一个对象。

    考虑:

    def interesting():
        also()
    

    如果您调用interesting(),python 会偶然发现名称also 并查找它,首先在本地函数范围内,然后在外部、全局、模块范围内。这意味着,如果您替换<module>.also,您将获得预期的效果,即不调用“真实”函数also,而是调用一个假函数。

    所以一般形式

    # the test.py
    import some_module as module_under_test
    
    def test_1():
        when(module_under_test).also()
        ...
        unstub()  # t.i. restore/undo the patching
    

    拥有一个测试文件和一个实现文件使这很容易,因为在测试模块中修补测试模块——这就是你的例子:interesting_function 存在于测试文件中——你通常不知道要修补什么,但实际上sys.modules[__name__] 是您当前的模块对象。

    【讨论】:

      猜你喜欢
      • 2020-07-14
      • 1970-01-01
      • 1970-01-01
      • 2014-06-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-03-30
      相关资源
      最近更新 更多