我正在练习TDD,对此我还很陌生。在我的测试案例中,我想从stdin读取并检查输出是否与输入匹配。
对于stdin我想使用一个模拟对象。因此,我使用monkeypatch.setattr('sys.stdin', StringIO(string))
将stdin替换为StringIO,因为两者都具有方法read()
。
# XPath.py
import sys
from io import StringIO
class XPath:
def __init__(self):
self.stdin = sys.stdin
def readStdin(self):
return self.stdin.read()
# TestXPath.py
import pytest
from XPath import XPath
from io import StringIO
def test_CanReadFromStdin(monkeypatch):
xpath = XPath()
string = "<a></a>\n"
monkeypatch.setattr('sys.stdin', StringIO(string))
assert xpath.readStdin() == string
但是,此操作失败
FAILED [100%]
TestXPath.py:4 (test_CanReadFromStdin)
monkeypatch = <_pytest.monkeypatch.MonkeyPatch object at 0x7f2dafc5ec90>
def test_CanReadFromStdin(monkeypatch):
xpath = XPath()
string = "<a></a>\n"
monkeypatch.setattr('sys.stdin', StringIO(string))
> assert xpath.readStdin() == string
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
XPath.py:9: in readStdin
return self.stdin.read()
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
pytest被调用而没有任何标志。添加-s
导致永无休止的循环。有趣的是,当我在省略构造函数的同时将XPath.py中的行更改为:
def readStdin(self):
return sys.stdin.read()
测试成功运行。
为什么构造函数中的分配不起作用?
我已经提出了这个解决方案。我正在使用库中的Mock()
。然后我在构造函数中删除了stdin分配。
#XPath.py
import sys
class XPath:
def __init__(self, stream):
self.stream = stream
pass
def readStdin(self):
return self.stream.read()
# test_file.py
import pytest
from XPath import XPath
from io import StringIO
def test_CanReadFromStdin(monkeypatch):
string = "<a></a>\n"
from unittest.mock import Mock
mock_stdin = Mock()
mock_stdin.readline = Mock(StringIO(string))
monkeypatch.setattr('sys.stdin', StringIO(string))
import sys
xpath = XPath(sys.stdin)
assert xpath.readStdin() == string
Update:为了演示目的,我再次将流(stdin)包含在构造函数中。这样,我可以编写第二种方法并传递文件描述符。