From 74cfdc5feb9b07ff538b6c85d864437aadeb314e Mon Sep 17 00:00:00 2001 From: Ronny Pfannschmidt Date: Thu, 24 May 2018 07:30:38 +0200 Subject: [PATCH 1/4] add failing test for #3498 --- testing/test_unittest.py | 47 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 47 insertions(+) diff --git a/testing/test_unittest.py b/testing/test_unittest.py index e19773587..685ca1b7a 100644 --- a/testing/test_unittest.py +++ b/testing/test_unittest.py @@ -828,3 +828,50 @@ def test_class_method_containing_test_issue1558(testdir): """) reprec = testdir.inline_run() reprec.assertoutcome(passed=1) + + +@pytest.mark.issue(3498) +@pytest.mark.parametrize("base", [ + 'six.moves.builtins.object', + 'unittest.TestCase', + 'unittest2.TestCase', +]) +def test_usefixtures_marker_on_unittest(base, testdir): + module = base.rsplit('.', 1)[0] + pytest.importorskip(module) + testdir.makepyfile(conftest=""" + import pytest + + @pytest.fixture(scope='function') + def fixture1(request, monkeypatch): + monkeypatch.setattr(request.instance, 'fixture1', True ) + + + @pytest.fixture(scope='function') + def fixture2(request, monkeypatch): + monkeypatch.setattr(request.instance, 'fixture2', True ) + """) + + testdir.makepyfile(""" + import pytest + import {module} + + class Tests({base}): + fixture1 = False + fixture2 = False + + @pytest.mark.usefixtures("fixture1") + def test_one(self): + assert self.fixture1 + assert not self.fixture2 + + @pytest.mark.usefixtures("fixture1", "fixture2") + def test_two(self): + assert self.fixture1 + assert self.fixture2 + + + """.format(module=module, base=base)) + + result = testdir.runpytest() + result.assert_outcomes(passed=2) From da2c2e8492c85b315d3cc0892a69ff2fc9c259e8 Mon Sep 17 00:00:00 2001 From: Ronny Pfannschmidt Date: Thu, 24 May 2018 09:58:36 +0200 Subject: [PATCH 2/4] more debugging for #3498 --- testing/test_unittest.py | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/testing/test_unittest.py b/testing/test_unittest.py index 685ca1b7a..202b20c19 100644 --- a/testing/test_unittest.py +++ b/testing/test_unittest.py @@ -850,6 +850,20 @@ def test_usefixtures_marker_on_unittest(base, testdir): @pytest.fixture(scope='function') def fixture2(request, monkeypatch): monkeypatch.setattr(request.instance, 'fixture2', True ) + + def node_and_marks(item): + print(item.nodeid) + for mark in item.iter_markers(): + print(" ", mark) + + @pytest.fixture(autouse=True) + def my_marks(request): + node_and_marks(request.node) + + def pytest_collection_modifyitems(items): + for item in items: + node_and_marks(item) + """) testdir.makepyfile(""" @@ -873,5 +887,5 @@ def test_usefixtures_marker_on_unittest(base, testdir): """.format(module=module, base=base)) - result = testdir.runpytest() + result = testdir.runpytest('-s') result.assert_outcomes(passed=2) From 5a0c9aca639596b9d0bf5d909462b0435afda244 Mon Sep 17 00:00:00 2001 From: Ronny Pfannschmidt Date: Thu, 24 May 2018 10:29:42 +0200 Subject: [PATCH 3/4] correctly instantiate fixtureinfo for unittest tests, fixes #3498 --- _pytest/fixtures.py | 2 +- _pytest/python.py | 2 +- _pytest/unittest.py | 3 ++- changelog/3498.bugfix | 1 + 4 files changed, 5 insertions(+), 3 deletions(-) create mode 100644 changelog/3498.bugfix diff --git a/_pytest/fixtures.py b/_pytest/fixtures.py index 7b109ec11..6617c24a2 100644 --- a/_pytest/fixtures.py +++ b/_pytest/fixtures.py @@ -984,7 +984,7 @@ class FixtureManager(object): session.config.pluginmanager.register(self, "funcmanage") def getfixtureinfo(self, node, func, cls, funcargs=True): - if funcargs and not hasattr(node, "nofuncargs"): + if funcargs and not getattr(node, "nofuncargs", False): argnames = getfuncargnames(func, cls=cls) else: argnames = () diff --git a/_pytest/python.py b/_pytest/python.py index 8bcb051a2..2b37067d5 100644 --- a/_pytest/python.py +++ b/_pytest/python.py @@ -1155,7 +1155,7 @@ class Function(FunctionMixin, nodes.Item, fixtures.FuncargnamesCompatAttr): if fixtureinfo is None: fixtureinfo = self.session._fixturemanager.getfixtureinfo( - self.parent, self.obj, self.cls, + self, self.obj, self.cls, funcargs=not self._isyieldedfunction()) self._fixtureinfo = fixtureinfo self.fixturenames = fixtureinfo.names_closure diff --git a/_pytest/unittest.py b/_pytest/unittest.py index 3ddb39495..17c94bca4 100644 --- a/_pytest/unittest.py +++ b/_pytest/unittest.py @@ -54,7 +54,7 @@ class UnitTestCase(Class): continue funcobj = getattr(x, 'im_func', x) transfer_markers(funcobj, cls, module) - yield TestCaseFunction(name, parent=self) + yield TestCaseFunction(name, parent=self, callobj=funcobj) foundsomething = True if not foundsomething: @@ -66,6 +66,7 @@ class UnitTestCase(Class): class TestCaseFunction(Function): + nofuncargs = True _excinfo = None def setup(self): diff --git a/changelog/3498.bugfix b/changelog/3498.bugfix new file mode 100644 index 000000000..7260879c4 --- /dev/null +++ b/changelog/3498.bugfix @@ -0,0 +1 @@ +correctly instantiate fixtureinfo for unittest tests. \ No newline at end of file From bc25d51b2f59a92df28c37b436b21aa311a30913 Mon Sep 17 00:00:00 2001 From: Bruno Oliveira Date: Thu, 24 May 2018 07:27:40 -0300 Subject: [PATCH 4/4] Re-word changelog --- changelog/3498.bugfix | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/changelog/3498.bugfix b/changelog/3498.bugfix index 7260879c4..344038bee 100644 --- a/changelog/3498.bugfix +++ b/changelog/3498.bugfix @@ -1 +1 @@ -correctly instantiate fixtureinfo for unittest tests. \ No newline at end of file +Fix ``usefixtures`` mark applyed to unittest tests by correctly instantiating ``FixtureInfo``.