diff --git a/_pytest/deprecated.py b/_pytest/deprecated.py index 4f7b9e9361e..f657472f9ca 100644 --- a/_pytest/deprecated.py +++ b/_pytest/deprecated.py @@ -37,3 +37,18 @@ class RemovedInPytest4Warning(DeprecationWarning): " please use pytest.param(..., marks=...) instead.\n" "For more details, see: https://docs.pytest.org/en/latest/parametrize.html" ) + + +def node_customclass_warning(name): + return RemovedInPytest4Warning( + "use of node.{name} is deprecated, " + "use pytest_pycollect_makeitem(...) to create custom " + "collection nodes".format(name=name) + ) + + +def node_class_use_pytest_instead_warning(owner, name): + return RemovedInPytest4Warning( + "usage of {owner!r}.{name} is deprecated, " + "please use pytest.{name} instead".format( + name=name, owner=type(owner).__name__)) \ No newline at end of file diff --git a/_pytest/fixtures.py b/_pytest/fixtures.py index b588c312af9..ec1133c0f10 100644 --- a/_pytest/fixtures.py +++ b/_pytest/fixtures.py @@ -18,7 +18,7 @@ ) from _pytest.outcomes import fail, TEST_OUTCOME from _pytest.compat import FuncargnamesCompatAttr - +from _pytest.main import Node if sys.version_info[:2] == (2, 6): from ordereddict import OrderedDict else: @@ -1064,6 +1064,10 @@ def parsefactories(self, node_or_obj, nodeid=NOTSET, unittest=False): nodeid = node_or_obj.nodeid if holderobj in self._holderobjseen: return + if isinstance(holderobj, Node): + # ignore internal plugin instances that are also nodes + # this is a massive wtf + return self._holderobjseen.add(holderobj) autousenames = [] for name in dir(holderobj): diff --git a/_pytest/main.py b/_pytest/main.py index f05cb7ff3b3..89b6643271f 100644 --- a/_pytest/main.py +++ b/_pytest/main.py @@ -2,6 +2,7 @@ from __future__ import absolute_import, division, print_function import functools +import warnings import os import six import sys @@ -14,6 +15,7 @@ except ImportError: from UserDict import DictMixin as MappingMixin +from _pytest import deprecated from _pytest.config import directory_arg, UsageError, hookimpl from _pytest.runner import collect_one_node from _pytest.outcomes import exit @@ -220,12 +222,8 @@ def __init__(self, name): def __get__(self, obj, owner): if obj is None: return self - - # TODO: reenable in the features branch - # warnings.warn( - # "usage of {owner!r}.{name} is deprecated, please use pytest.{name} instead".format( - # name=self.name, owner=type(owner).__name__), - # PendingDeprecationWarning, stacklevel=2) + warnings.warn(deprecated.node_class_use_pytest_instead_warning( + owner=owner, name=self.name), stacklevel=2) return getattr(__import__('pytest'), self.name) @@ -312,10 +310,9 @@ def _getcustomclass(self, name): return getattr(__import__('pytest'), name) else: cls = getattr(self, name) - # TODO: reenable in the features branch - # warnings.warn("use of node.%s is deprecated, " - # "use pytest_pycollect_makeitem(...) to create custom " - # "collection nodes" % name, category=DeprecationWarning) + # OPTIONAL TODO: find a way to show the definition location + # of the class that owns that attribute + warnings.warn(deprecated.node_customclass_warning(name)) return cls def __repr__(self): diff --git a/_pytest/python.py b/_pytest/python.py index b794862671f..53beed84c74 100644 --- a/_pytest/python.py +++ b/_pytest/python.py @@ -595,6 +595,9 @@ def collect(self): self._preservedparent = self.parent.obj l = [] seen = {} + + mk_function = self._getcustomclass("Function") + for i, x in enumerate(self.obj()): name, call, args = self.getcallargs(x) if not callable(call): @@ -606,7 +609,8 @@ def collect(self): if name in seen: raise ValueError("%r generated tests with non-unique name %r" % (self, name)) seen[name] = True - l.append(self.Function(name, self, args=args, callobj=call)) + + l.append(mk_function(name, self, args=args, callobj=call)) self.warn('C1', deprecated.YIELD_TESTS) return l diff --git a/testing/python/collect.py b/testing/python/collect.py index bd7013b4488..c58eb6d9f96 100644 --- a/testing/python/collect.py +++ b/testing/python/collect.py @@ -1204,7 +1204,8 @@ def pytest_pycollect_makeitem(collector): def test_hello(): pass """) - result = testdir.runpytest() + result = testdir.runpytest( + '-W', "ignore::_pytest.deprecated.RemovedInPytest4Warning") result.stdout.fnmatch_lines([ "*1 passed*", ]) @@ -1229,7 +1230,9 @@ class MyTestClass(object): def test_hello(self): pass """) - result = testdir.runpytest("--collect-only") + result = testdir.runpytest( + "--collect-only", + '-W', "ignore::_pytest.deprecated.RemovedInPytest4Warning") result.stdout.fnmatch_lines([ "*MyClass*", "*MyInstance*",