You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在pytest中使用fudge.patch?nose转pytest的兼容问题

解决pytest与fudge@patch的参数冲突问题

别担心,pytest和fudge并不是不兼容,只是它们的参数处理机制有点小冲突——pytest会默认把测试函数的所有参数都当成fixture来查找,而fudge的@patch装饰器是想把伪造对象直接注入参数里,这就导致了误会。

我之前也遇到过类似的问题,分享几个实用的解决技巧:

技巧1:改用fudge的上下文管理器(最推荐)

放弃装饰器写法,改用with语句来包裹伪造逻辑,这样测试函数不需要额外参数,pytest就不会瞎找fixture了,而且还能保留fudge那种集中设置的优势:

from datetime import datetime
from fudge import patch

def today():
    return datetime.utcnow()

def something():
    return today()

test_time = datetime(2018, 1, 1, 12, 34, 56)

def test_something():
    with patch('today') as fake_today:
        fake_today.expects_call().returns(test_time)
        result = something()
        assert result == test_time

这种写法和你原来的逻辑完全一致,只是把装饰器换成了上下文管理器,完美避开pytest的fixture检测。

技巧2:把fudge伪造逻辑封装成pytest fixture

如果多个测试都需要用到类似的伪造对象,可以把fudge的逻辑封装成pytest fixture,这样既能复用,又能符合pytest的参数规则:

import pytest
from datetime import datetime
from fudge import patch

def today():
    return datetime.utcnow()

def something():
    return today()

test_time = datetime(2018, 1, 1, 12, 34, 56)

@pytest.fixture
def mocked_today():
    with patch('today') as fake:
        fake.expects_call().returns(test_time)
        yield fake

def test_something(mocked_today):
    result = something()
    assert result == test_time

这个方法适合需要重复使用相同伪造规则的场景,而且完全兼容pytest的fixture体系。

为什么nose没问题?

nose的参数解析逻辑和pytest不一样,它允许装饰器直接向测试函数注入参数,不会把所有参数都当成fixture处理,所以你原来的写法在nose里能正常工作。

另外必须说一句,我也特别喜欢fudge这种把调用预期和返回值集中设置的方式,比mock那种拆成好几步的写法直观太多了,你的选择完全没问题😉

内容的提问来源于stack exchange,提问作者quantoid

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 03:43:39