Python中猴子补丁的下面是什么

2024-10-03 17:23:49 发布

您现在位置:Python中文网/ 问答频道 /正文

我有点困惑,并试图了解到底是什么,希望我能理解猴子补丁更好

我已经阅读了Where to patch,我知道我必须从您使用模块的地方进行修补。但是在文件里

a.py
    -> Defines SomeClass

b.py
    -> from a import SomeClass
    -> some_function instantiates SomeClass

如果我这样做from a import SomeClass

那我就得这样修补

@patch('b.SomeClass')

但是,为什么我要像这样导入模块

import a

我不得不用这样的补丁

@patch('a.SomeClass')

我只知道如何使用补丁,但我不明白为什么会这样?这是Python导入模块的方式吗


Tags: 模块文件tofrompyimport地方function
2条回答

这一切都与名称空间有关

b.py内部,当命令from a import SomeClass执行时,SomeClass被添加到模块b命名空间。因此,您有b.SomeClass

在另一种情况下,当仍然在b.py内部并且您执行命令import a时,所发生的一切就是模块b现在可以访问模块a的名称空间。因此,从全局的角度来看,b内部使用的类仍然是a.SomeClass

我们的目标是截取并修改您想要影响其行为的函数将使用的引用。最初,a.SomeClassb.SomeClass指向同一个对象;但是这个补丁将用其他的东西替换其中一个引用

在文档中,示例是您希望修改SomeClass所看到和使用的some_function。所以重要的是some_function()如何指代SomeClass

  1. 如果some_function包含对纯SomeClass的引用,它将被解析为自己模块中的一个变量:b在本例中(顺便说一下,b通过导入它创建了这个变量)。因此b.SomeClass是需要修补的

  2. 如果some_function显式引用a.SomeClass,那么这就是需要修补的引用

假设模块b.py包含以下两行:

import a
from a import SomeClass

应该修补哪个引用?为什么,some_function使用的那个!重要的不是如何将它导入b,而是使用它的代码如何访问它

相关问题 更多 >