python - 如何使用 pytest 设备优雅地模拟一个类?
问题描述
假设我有一个fixture
使用monkeypatch
.
# conftest.py
@pytest.fixture
def mock_dummyclass(monkeypatch):
def mock_function():
return None
monkeypatch.setattr(dummypackage, "dummyclass", mock_function)
现在,我必须在我的测试中使用这个夹具,以便模拟这个类。
#test_dummy.py
@pytest.mark.usefixtures("mock_dummyclass")
class TestManyDummyMethods:
def test_dummy_one():
import dummypackage # Flag A
def test_dummy_two():
import dummypackage # Flag B
...
def test_dummy_n():
import dummypackage # Flag N
正如您在标记行中看到的那样,我必须dummypackage
在每个函数中导入此模块,以确保在导入模块之前应用夹具(否则夹具将无效)。
在类内部导入dummypackage
会起作用,但self.dummypackage
在内部调用函数似乎也不是很优雅。
有没有更优雅的方法来实现这一点?
解决方案
评论:monkeypatch
图书馆似乎不再维护了。unittest.mock
应该可以提供你所需要的一切。
我会尽量避免依赖于将模块作为测试的一部分导入的解决方案,因为如果出于其他原因(例如导入其他功能)导入它会中断。
我正在使用os
作为示例,因为它存在并使其可重现。
如何最好地修补似乎取决于您如何从另一个模块导入。
示例 1:(从target_module1.py
导入join
方法os.path
):
from os.path import join
def some_method_using_join():
return join('parent', 'child')
这需要我们修补以下join
方法target_module1.py
:
target_module1_test.py
:
from unittest.mock import patch, MagicMock
import pytest
from target_module1 import some_method_using_join
@patch('target_module1.join')
def some_test(join_mock: MagicMock):
some_method_using_join()
示例 2:(target_module2.py
导入os
模块):
import os
def some_method_using_join():
return os.path.join('parent', 'child')
这允许我们修补join
方法os.path
:
target_module2_test.py
:
from unittest.mock import patch, MagicMock
import pytest
from target_module2 import some_method_using_join
@patch('os.path.join')
def some_test(join_mock: MagicMock):
some_method_using_join()
这假设您不需要修补在模块级别(即在导入时)使用的类或方法。
推荐阅读
- python - matplotlib.pyplot 如何确定 x 和 y 轴标签和比例图?
- r - 在R中将日期时间转换为字符串
- javascript - 删除元素时数组返回未定义
- android - 结果编译为“INSTALL_FAILED_NO_MATCHING_ABIS”
- sympy - 如何在 jupyter 笔记本中安装 sympy
- python-3.x - 如何列出所有已安装的python包
- firebase - Flutter Firebase 循环遍历文档中的集合
- r - 如何在值 x 和 y 之间替换数据框中的值
- javascript - 如何查看导入到 vs 代码的 png 图像的 x 和 y 值?
- php - 防止在没有 RBAC 会话的情况下直接访问文件 png 或 pdf