Как издеваться над аргументом cls метода класса? - PullRequest
1 голос
/ 02 июля 2019

У меня есть класс, который использует classmethod в качестве пользовательского конструктора.

# my_module.py
class MyClass:
    def __init__(self, my_arg):
        self.my_arg = my_arg

    @classmethod
    def my_constructor(cls):
        return cls("my val")

Я хотел бы заявить в тесте, что конструктор был вызван с правильным значением, а экземпляр возвращен.

Я пробовал несколько способов исправления, но я не мог заставить его работать.

Я попытался пропатчить весь класс, используя аргумент wraps для выполнения реального метода.

# my_test.py
from unittest import TestCase
from unittest.mock import patch

from my_module import MyClass


class MyClassTestCase(TestCase):
    @patch("my_module.MyClass", wraps=MyClass)
    def test_my_constructor(self, my_class):
        result = my_class.my_constructor()
        my_class.assert_called_once_with("my val")
        self.assertEqual(result, my_class.return_value)

Проблема здесь в том, что аргумент cls , который получает метод _my_module.MyClass.my_class_, - это не мой Mock , а настоящий MyClass класс.

Другой моей идеей было использование patch.object для исправления реального конструктора __ init __ , но это тоже не сработало. На этот раз, потому что __ init __ не должен ничего возвращать, но MagicMock имеет возвращаемое значение.

# my_test.py
from unittest import TestCase
from unittest.mock import patch

from my_module import MyClass


class MyClassTestCase(TestCase):
    @patch.object(MyClass, "__init__")
    def test_my_constructor(self, init):
        result = MyClass.my_constructor()
        init.assert_called_once_with("my val")
        self.assertEqual(result, init.return_value)

Существует ли реальный способ утверждать, что класс MyClass был создан _my_constructor_ с заданными аргументами и возвращен?

...