关于python:如何让MagicMock表现得像个字典?

How to let MagicMock behave like a dict?

模拟http:/ /恩/最新mock.readthedocs.org index.html)是一个伟大的工具,在Python的单元测试。它可以方便的模拟方法的类或A或A。但我遇到的问题,它不能找到一个简单的方法来对付由模拟。

这是一个测试函数:

1
2
3
4
5
6
7
8
9
10
def function_to_be_tested(id, responses):
    if not id in responses:
        print '%s not exist'%pole_id
        return

    if id in responses.redundantErrorResponses:
        print '%s is redundant'%pole_id
        return

    do_something()

响应是一个论点,这样的对象有其他一些属性(如redundanterrorresponses)除了固有的特征。现在我想构建一个模拟的反应,让一个id in responses.redundantErrorResponsesid in responsesto true和false。这是我做的:

1
2
3
4
5
6
7
pole_id = 30
pole_value = 100
pole_dic = {pole_id:pole_value}
mock_responses = MagicMock()
mock_responses.__getitem__.side_effect = lambda k: pole_dic[k]
mock_responses.__iter__.side_effect = iter(pole_dic)
mock_responses.redundantErrorResponses = {}

但发生错误:

1
2
3
function_to_be_tested(pole_id, mock_responses)

>>30 not exist

因此构建一magicmock Mi-24对象同时CAN iterate样a字典或词典Mi-24 construct a同时支持功能(添加属性到magicmock)?


为什么要和__iter__混在一起?在我看来,你想和__contains__搞混:

1
2
3
4
5
6
7
8
9
10
11
12
>>> import mock
>>> m = mock.MagicMock()
>>> d = {'foo': 'bar'}
>>> m.__getitem__.side_effect = d.__getitem__
>>> m.__iter__.side_effect = d.__iter__
>>> m['foo']
'bar'
>>> 'foo' in m
False
>>> m.__contains__.side_effect = d.__contains__
>>> 'foo' in m
True

你可以创建一些愚蠢的类来做同样的事情。

1
2
3
In [94]: class MockResponses(dict):
   ....:     def redundantErrorResponses(self):
   ....:         return {}