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

Python unittest.mock:为何定义层打补丁无效?求深层解析

为什么patch a.SomeClass对b.some_function无效?

要搞懂这个问题,得先明白Python的导入逻辑和引用机制:

1. 导入时的引用复制

先看你的项目代码:

  • a.py定义SomeClass:
class SomeClass:
    pass
  • b.py通过from a import SomeClass导入,并在函数里使用:
from a import SomeClass

def some_function():
    return SomeClass()

当b模块第一次被加载时,from a import SomeClass会做两件事:

  • 找到a模块命名空间里的SomeClass类对象
  • 在b模块自己的命名空间里,创建一个名为SomeClass的变量,直接指向这个真实的类对象

这时候,a.SomeClass和b.SomeClass是同一个对象的两个独立引用——就像两个人各拿了一张指向同一栋房子的纸条,纸条本身是分开的,但指向的是同一个地方。

2. patch的作用范围

patch('a.SomeClass')的本质是:修改a模块命名空间里的SomeClass变量,让它指向一个mock对象,而不再是原来的真实类。

但问题在于,b模块里的SomeClass变量是早就复制好的引用,它不会自动跟着a模块里的变化更新。就像你把自己纸条上的地址改成了假房子,但你朋友手里的纸条还是原来的真实地址,他去找的时候还是会去真房子,不会去你改的假房子。

所以当some_function调用SomeClass()时,它用的是b模块自己命名空间里的那个真实类引用,完全没用到被patch过的a.SomeClass。

3. 正确的patch方式

要让mock生效,你需要patch的是b模块里的SomeClass引用,也就是用:

patch('b.SomeClass')

这样替换的是b模块命名空间里的SomeClass变量,当some_function调用SomeClass()时,就会使用这个mock对象了。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.29 16:58:14