Для початку MagicMock
- це підклас Mock
.
class MagicMock(MagicMixin, Mock)
Як результат, MagicMock надає все, що надає Mock та багато іншого. Замість того, щоб думати про Mock як про зняту версію MagicMock, думайте про MagicMock як розширену версію Mock. Це має вирішити ваші запитання щодо того, чому Mock існує і що надає Mock поверх MagicMock.
По-друге, MagicMock забезпечує реалізацію за замовчуванням багатьох / найбільш магічних методів, тоді як Mock - ні. Дивіться тут для отримання додаткової інформації про надані магічні методи.
Деякі приклади наданих магічних методів:
>>> int(Mock())
TypeError: int() argument must be a string or a number, not 'Mock'
>>> int(MagicMock())
1
>>> len(Mock())
TypeError: object of type 'Mock' has no len()
>>> len(MagicMock())
0
І це можуть бути не такі інтуїтивні (принаймні, не інтуїтивні для мене):
>>> with MagicMock():
... print 'hello world'
...
hello world
>>> MagicMock()[1]
<MagicMock name='mock.__getitem__()' id='4385349968'>
Ви можете "побачити" методи, додані до MagicMock, коли ці методи викликаються вперше:
>>> magic1 = MagicMock()
>>> dir(magic1)
['assert_any_call', 'assert_called_once_with', ...]
>>> int(magic1)
1
>>> dir(magic1)
['__int__', 'assert_any_call', 'assert_called_once_with', ...]
>>> len(magic1)
0
>>> dir(magic1)
['__int__', '__len__', 'assert_any_call', 'assert_called_once_with', ...]
Отже, чому б не використовувати MagicMock весь час?
Питання до вас: Чи добре ви з реалізацією магічних методів за замовчуванням? Наприклад, чи добре, mocked_object[1]
щоб не помилитися? Ви не в порядку з будь-якими непередбачуваними наслідками через те, що чарівні способи реалізації вже є?
Якщо відповідь на ці питання - так, то продовжуйте використовувати MagicMock. Інакше дотримуйтесь Mock.