2010-11-07 06:45:48 +08:00
|
|
|
""" discovery and running of std-library "unittest" style tests. """
|
2010-11-13 16:05:11 +08:00
|
|
|
import pytest, py
|
2009-07-21 00:54:18 +08:00
|
|
|
import sys
|
2009-02-27 18:18:27 +08:00
|
|
|
|
2009-06-15 21:15:40 +08:00
|
|
|
def pytest_pycollect_makeitem(collector, name, obj):
|
2010-11-07 06:45:48 +08:00
|
|
|
unittest = sys.modules.get('unittest')
|
|
|
|
if unittest is None:
|
|
|
|
return # nobody can have derived unittest.TestCase
|
2009-10-09 21:09:26 +08:00
|
|
|
try:
|
2010-11-07 06:45:48 +08:00
|
|
|
isunit = issubclass(obj, unittest.TestCase)
|
2010-04-28 21:24:38 +08:00
|
|
|
except KeyboardInterrupt:
|
|
|
|
raise
|
|
|
|
except Exception:
|
2009-10-09 21:09:26 +08:00
|
|
|
pass
|
|
|
|
else:
|
|
|
|
if isunit:
|
|
|
|
return UnitTestCase(name, parent=collector)
|
2009-02-27 18:18:27 +08:00
|
|
|
|
2010-11-13 16:05:11 +08:00
|
|
|
class UnitTestCase(pytest.Class):
|
2009-02-27 18:18:27 +08:00
|
|
|
def collect(self):
|
|
|
|
loader = py.std.unittest.TestLoader()
|
2010-11-02 06:08:16 +08:00
|
|
|
for name in loader.getTestCaseNames(self.obj):
|
|
|
|
yield TestCaseFunction(name, parent=self)
|
2009-02-27 18:18:27 +08:00
|
|
|
|
|
|
|
def setup(self):
|
2010-11-02 06:08:16 +08:00
|
|
|
meth = getattr(self.obj, 'setUpClass', None)
|
|
|
|
if meth is not None:
|
|
|
|
meth()
|
2009-02-27 18:18:27 +08:00
|
|
|
|
|
|
|
def teardown(self):
|
2010-11-02 06:08:16 +08:00
|
|
|
meth = getattr(self.obj, 'tearDownClass', None)
|
|
|
|
if meth is not None:
|
|
|
|
meth()
|
2009-02-27 18:18:27 +08:00
|
|
|
|
2010-11-13 16:05:11 +08:00
|
|
|
class TestCaseFunction(pytest.Function):
|
2010-11-23 22:42:23 +08:00
|
|
|
_excinfo = None
|
2010-11-07 08:10:15 +08:00
|
|
|
def setup(self):
|
|
|
|
pass
|
|
|
|
def teardown(self):
|
|
|
|
pass
|
2010-11-02 06:08:16 +08:00
|
|
|
def startTest(self, testcase):
|
|
|
|
pass
|
2010-11-23 22:42:23 +08:00
|
|
|
|
|
|
|
def _addexcinfo(self, rawexcinfo):
|
|
|
|
#__tracebackhide__ = True
|
|
|
|
assert rawexcinfo
|
|
|
|
try:
|
|
|
|
self._excinfo = py.code.ExceptionInfo(rawexcinfo)
|
|
|
|
except TypeError:
|
|
|
|
try:
|
|
|
|
try:
|
|
|
|
l = py.std.traceback.format_exception(*rawexcinfo)
|
|
|
|
l.insert(0, "NOTE: Incompatible Exception Representation, "
|
|
|
|
"displaying natively:\n\n")
|
|
|
|
pytest.fail("".join(l), pytrace=False)
|
|
|
|
except (pytest.fail.Exception, KeyboardInterrupt):
|
|
|
|
raise
|
|
|
|
except:
|
|
|
|
pytest.fail("ERROR: Unknown Incompatible Exception "
|
|
|
|
"representation:\n%r" %(rawexcinfo,), pytrace=False)
|
|
|
|
except pytest.fail.Exception:
|
|
|
|
self._excinfo = py.code.ExceptionInfo()
|
|
|
|
except KeyboardInterrupt:
|
|
|
|
raise
|
|
|
|
|
2010-11-02 06:08:16 +08:00
|
|
|
def addError(self, testcase, rawexcinfo):
|
2010-11-23 22:42:23 +08:00
|
|
|
self._addexcinfo(rawexcinfo)
|
2010-11-02 06:08:16 +08:00
|
|
|
def addFailure(self, testcase, rawexcinfo):
|
2010-11-23 22:42:23 +08:00
|
|
|
self._addexcinfo(rawexcinfo)
|
2010-11-02 06:08:16 +08:00
|
|
|
def addSuccess(self, testcase):
|
|
|
|
pass
|
|
|
|
def stopTest(self, testcase):
|
|
|
|
pass
|
|
|
|
def runtest(self):
|
|
|
|
testcase = self.parent.obj(self.name)
|
|
|
|
testcase(result=self)
|
2010-11-23 22:42:23 +08:00
|
|
|
|
|
|
|
@pytest.mark.tryfirst
|
|
|
|
def pytest_runtest_makereport(item, call):
|
|
|
|
if isinstance(item, TestCaseFunction):
|
|
|
|
if item._excinfo:
|
|
|
|
call.excinfo = item._excinfo
|
|
|
|
item._excinfo = None
|
|
|
|
del call.result
|