2014-09-13 97 views
5

mock.reset_mock()將不會重置副作用迭代器。有沒有辦法做到這一點,而不是再次創建模擬?模擬side_effect迭代器在耗盡後可以重置嗎?

>>> from mock import MagicMock 
>>> mock = MagicMock(side_effect = [1,2]) 
>>> mock(), mock() 
(1, 2) 
>>> mock() 

Traceback (most recent call last): 
    File "<pyshell#114>", line 1, in <module> 
    mock() 
    File "C:\Python27\Lib\site-packages\mock.py", line 955, in __call__ 
    return _mock_self._mock_call(*args, **kwargs) 
    File "C:\Python27\Lib\site-packages\mock.py", line 1013, in _mock_call 
    result = next(effect) 
StopIteration 
>>> mock.reset_mock() 
>>> mock() 

Traceback (most recent call last): 
    ... 
StopIteration 
>>> mock = MagicMock(side_effect = [1,2]) 
>>> mock(), mock() 
(1, 2) 
>>> 

這樣做的目的是重新使用在隨後的測試模擬,但我懷疑,就像一臺發電機,它不能重啓

所以(遲到總比不到好)被指出在我看了mock.py,發現side_effect是一個迭代對象(不能爲復位一旦累死了)正確的方向後:

def __set_side_effect(self, value): 
    value = _try_iter(value) 
    ... 

def _try_iter(obj): 
    ... 
    try: 
     return iter(obj) 
    except TypeError: 
     # XXXX backwards compatibility 
     # but this will blow up on first call - so maybe we should fail early? 
     return obj 

def reset_mock()沒有解決側面效應。

+0

如何通過無限迭代器? 'mock = MagicMock(side_effect = itertools.cycle([1,2]))';你不需要調用'reset_mock'。 – falsetru 2014-09-13 18:21:54

+1

@falsetru:但是如果模擬不正確使用,下一次調用模擬會給出錯誤的值。 – 2014-09-13 18:23:39

+2

你試過重新分配'side_effect'嗎? – user2357112 2014-09-13 18:24:15

回答

3

由於user2357112評論,重新分配side_effect將解決您的問題。

>>> from mock import MagicMock 
>>> 
>>> lst = [1, 2] 
>>> mock = MagicMock(side_effect=lst) 
>>> mock(), mock() 
(1, 2) 
>>> mock.side_effect = lst # <------- 
>>> mock(), mock() 
(1, 2) 
+0

謝謝,我甚至沒有想過這樣做。你擊敗了@ user2357112。 – wwii 2014-09-13 18:46:31