Python 从pyserial继承时的模拟
我有一个从Python 从pyserial继承时的模拟,python,unit-testing,mocking,pytest,Python,Unit Testing,Mocking,Pytest,我有一个从pyserial的serial.serial类继承的类,它看起来像这样: class SYM1(serial.Serial): def __init__(self, *args, debug=None, baudrate=4800, timeout=1, **kwargs): super().__init__(*args, baudrate=baudrate, timeout=timeout, **kwargs) LOG.info('using
pyserial
的serial.serial
类继承的类,它看起来像这样:
class SYM1(serial.Serial):
def __init__(self, *args, debug=None, baudrate=4800, timeout=1, **kwargs):
super().__init__(*args, baudrate=baudrate, timeout=timeout, **kwargs)
LOG.info('using port %s', self.port)
def read(self, count):
...
return super().read(count)
def write(self, data):
...
return super().write(data)
def connect(self):
...
def send_command(self, cmd, *args):
...
我想为类编写单元测试,但我不确定如何最好地进行设置,以便(a)在SYM1
类上定义的方法可以正常调用,而(b)从serial.serial
继承的方法可以模拟
我从这个开始:
import pytest
import serial
from unittest import mock
serial.Serial = mock.MagicMock
from symtool import symtool # NOQA
@pytest.fixture
def sym(monkeypatch):
s = symtool.SYM1('TESTDEV')
s.connect()
return s
def test_connect(sym):
pass
但这在这里失败了:
LOG.info('using port %s', self.port)
与:
这让我很困惑,因为如果它是mock.mock
对象,我希望:
>>> from unittest import mock
>>> m = mock.Mock()
>>> m.port
<Mock name='mock.port' id='139910315631568'>
这里发生了什么,正确的方法是什么?考虑不使用继承,而是使用组合
SYM1.\uuuu init\uuuuu
将在生产环境中使用Serial
的实例,但在测试中使用某个虚拟类的实例。您所有的SYM1
方法都将使用该对象,而不是重写继承的方法。问题是我正在重写read
和write
方法,这些方法由Serial
类的其他方法调用。我认为没有一种优雅的方式可以通过合成来实现这一点。def read(self,count):返回self.serial\u obj.read(count)
。调用方不知道您是否正在使用super
或委托给另一个对象。不,问题是当serial.serial
中的方法调用例如read
时。因此SYM1
调用self.read_直到(…)
,而read_直到
方法(定义在serial.serial
而不是SYM1
上)调用self.read
。如果我们调用self.serial\u obj.read\u直到
,这将不起作用。
>>> from unittest import mock
>>> m = mock.Mock()
>>> m.port
<Mock name='mock.port' id='139910315631568'>
AttributeError: 'super' object has no attribute 'write'