如何使用模拟库修补Python类
我很难为我的测试修补一个类。我正在尝试修补属于Scrapy-a类的东西 下面是一些代码:如何使用模拟库修补Python类,python,unit-testing,mocking,scrapy,python-mock,Python,Unit Testing,Mocking,Scrapy,Python Mock,我很难为我的测试修补一个类。我正在尝试修补属于Scrapy-a类的东西 下面是一些代码: from scrapy.selector import HtmlXPathSelector from mock import MagicMock, patch with patch('scrapy.selector.HtmlXPathSelector') as MockHtml: instance = MockHtml.return_value instance.method.return
from scrapy.selector import HtmlXPathSelector
from mock import MagicMock, patch
with patch('scrapy.selector.HtmlXPathSelector') as MockHtml:
instance = MockHtml.return_value
instance.method.return_value = 'foo'
example = HtmlXPathSelector()
print type(example)
assert example is instance
assert example.method == 'foo'
结果是:
<class 'scrapy.selector.lxmlsel.HtmlXPathSelector'>
Traceback (most recent call last):
File "<stdin>", line 6, in <module>
AssertionError
>>>
回溯(最近一次呼叫最后一次):
文件“”,第6行,在
断言错误
>>>
此示例与模拟库教程中的示例几乎相同。知道它为什么不工作吗?您不应该修补当前测试代码中已导入的类。相反,您需要在相应的模块(您想要测试)中修补该类。因此,如果在
mymodule
中导入了HtmlXPathSelector
,您将作为以下内容进行修补:
with patch('mymodule.HtmlXPathSelector') as MockClass:
...
有关更多详细信息,请参阅
编辑如果确实需要,可以使用以下内容修补当前模块中的类:
with patch('__main__.Class') as MockClass:
您的代码示例有两个问题。首先,您已经从scrapy模块中导入了HtmlXPathSelector,然后在事实发生后更改该名称。改为导入选择器,并使用其中的名称:
from scrapy import selector
from mock import MagicMock, patch
with patch('scrapy.selector.HtmlXPathSelector') as MockHtml:
instance = MockHtml.return_value
instance.method.return_value = 'foo'
example = selector.HtmlXPathSelector()
print type(example)
assert example is instance
assert example.method() == 'foo'
另一个问题是,您的最后一行正在检查
方法
,当它需要调用方法作为方法()
这太好了,谢谢!唯一的问题是,我在问题中给出的例子稍微简化了。。。事实上,在我正在测试的模块中,mypackage.foo_模块
,htmlxpath选择器
是这样导入的:从scrapy.selector导入htmlxpath选择器
,然后我正在测试的函数有一个实例化,比如hxs=htmlxpath选择器(XX)
。我是否必须更改我正在测试的类中的代码才能使其正常工作?或者更改产品代码以按照此示例的方式导入,或者使用patch('mypackage.foo_module.HtmlXPathSelector')
。第二种方式可能更好,因为这是一种更本地化的更改。我现在明白了,内德,谢谢。我刚才无意中听到了你的谈话。然后你回答了我的测试问题。真奇怪。:-)啊!这就是我想要的。。。我现在明白了,这个方法回答了我在Ned的回答中的评论。谢谢此时修补的链接返回503。@Drachenfels谢谢,将链接更改为指向readthedocs,应该更稳定。