#python #python-3.x #python-unittest
#python #python-3.x #python-модульный тест
Вопрос:
Проще всего начать с примера…
Пример кода для тестирования:
type1_instance1 = f1()
type1_instance2 = f2()
compareResult = type1_instance1 < type1_intstance2
if compareResult:
print(type1_instance1.generate_value())
Экземпляры 1 и 2 являются экземплярами некоторого пользовательского класса.
При тестировании f1
и f2
издеваются над возвратом MagicMocks. Чтобы методы пользовательского класса могли вызываться для этих возвращаемых значений.
При выполнении кода сравнения я получаю сообщение об ошибке
‘<‘ не поддерживается между экземплярами ‘MagicMock’ и ‘MagicMock’
Какой наилучший способ позволить MagicMocks работать с перегруженными операторами?
Вот мое решение:
def __lt__(self, other):
return mock.MagicMock
compareable_MagicMock_Instance = MagicMock()
setattr(compareable_MagicMock_Instance, '__lt__', __lt__)
f1.return_value = compareable_MagicMock_Instance
f2.return_value = another_compareable_MagicMock_Instance
Ответ №1:
Вместо этого вы должны переопределить return_value
атрибут __lt__
атрибута MagicMock
объекта и использовать patch
для создания f1
и f2
возврата настроенного MagicMock
экземпляра:
from unittest.mock import patch, MagicMock
def f1():
pass
def f2():
pass
compareable_MagicMock_Instance = MagicMock()
compareable_MagicMock_Instance.__lt__.return_value = True
with patch('__main__.f1', return_value=compareable_MagicMock_Instance), patch('__main__.f2', return_value=compareable_MagicMock_Instance):
type1_instance1 = f1()
type1_instance2 = f2()
compareResult = type1_instance1 < type1_instance2
if compareResult:
print('type1_instance1 is less than type1_instance2')
Это выводит:
type1_instance1 is less than type1_instance2
Комментарии:
1. Я тоже думал об этом, но я видел в документах в разделе поддерживаемые методы, которые поддерживаются lt и т.д. Так почему же они уже не сопоставимы? docs.python.org/3/library /…
2. Под «поддерживаемым» в документе подразумевается только то, что при издевательстве над этими магическими методами перечисленные имена будут распознаны как вызываемые методы, а не обычные атрибуты. Вам все равно придется имитировать определенные магические методы, если вы хотите их использовать, поскольку методы не реализованы по умолчанию (и они не были бы полезны, даже если бы были реализованы по умолчанию, поскольку их возвращаемые значения по умолчанию, скорее всего, не те, которые вы хотите).