Deprecate Config.warn and Node.warn, replaced by standard warnings

This commit is contained in:
Bruno Oliveira 2018-09-01 21:58:48 -03:00
parent 0c8dbdcd92
commit 78ac7d99f5
21 changed files with 197 additions and 75 deletions

View File

@ -209,8 +209,11 @@ class AssertionRewritingHook(object):
self._must_rewrite.update(names) self._must_rewrite.update(names)
def _warn_already_imported(self, name): def _warn_already_imported(self, name):
self.config.warn( import warnings
"P1", "Module already imported so cannot be rewritten: %s" % name from _pytest.warning_types import PytestWarning
warnings.warn(
"Module already imported so cannot be rewritten: %s" % name, PytestWarning
) )
def load_module(self, name): def load_module(self, name):
@ -746,13 +749,17 @@ class AssertionRewriter(ast.NodeVisitor):
the expression is false. the expression is false.
""" """
if isinstance(assert_.test, ast.Tuple) and self.config is not None: if isinstance(assert_.test, ast.Tuple):
fslocation = (self.module_path, assert_.lineno) from _pytest.warning_types import PytestWarning
self.config.warn( import warnings
"R1",
warnings.warn_explicit(
"assertion is always true, perhaps " "remove parentheses?", "assertion is always true, perhaps " "remove parentheses?",
fslocation=fslocation, PytestWarning,
filename=str(self.module_path),
lineno=assert_.lineno,
) )
self.statements = [] self.statements = []
self.variables = [] self.variables = []
self.variable_counter = itertools.count() self.variable_counter = itertools.count()

View File

@ -33,7 +33,6 @@ See [the docs](https://docs.pytest.org/en/latest/cache.html) for more informatio
@attr.s @attr.s
class Cache(object): class Cache(object):
_cachedir = attr.ib(repr=False) _cachedir = attr.ib(repr=False)
_warn = attr.ib(repr=False)
@classmethod @classmethod
def for_config(cls, config): def for_config(cls, config):
@ -41,14 +40,19 @@ class Cache(object):
if config.getoption("cacheclear") and cachedir.exists(): if config.getoption("cacheclear") and cachedir.exists():
shutil.rmtree(str(cachedir)) shutil.rmtree(str(cachedir))
cachedir.mkdir() cachedir.mkdir()
return cls(cachedir, config.warn) return cls(cachedir)
@staticmethod @staticmethod
def cache_dir_from_config(config): def cache_dir_from_config(config):
return paths.resolve_from_str(config.getini("cache_dir"), config.rootdir) return paths.resolve_from_str(config.getini("cache_dir"), config.rootdir)
def warn(self, fmt, **args): def warn(self, fmt, **args):
self._warn(code="I9", message=fmt.format(**args) if args else fmt) import warnings
from _pytest.warning_types import PytestWarning
warnings.warn(
message=fmt.format(**args) if args else fmt, category=PytestWarning
)
def makedir(self, name): def makedir(self, name):
""" return a directory path object with the given name. If the """ return a directory path object with the given name. If the

View File

@ -176,7 +176,9 @@ def _prepareconfig(args=None, plugins=None):
else: else:
pluginmanager.register(plugin) pluginmanager.register(plugin)
if warning: if warning:
config.warn("C1", warning) from _pytest.warning_types import PytestUsageWarning
warnings.warn(warning, PytestUsageWarning)
return pluginmanager.hook.pytest_cmdline_parse( return pluginmanager.hook.pytest_cmdline_parse(
pluginmanager=pluginmanager, args=args pluginmanager=pluginmanager, args=args
) )
@ -609,7 +611,26 @@ class Config(object):
fin() fin()
def warn(self, code, message, fslocation=None, nodeid=None): def warn(self, code, message, fslocation=None, nodeid=None):
""" generate a warning for this test session. """ """
.. deprecated:: 3.8
Use :py:func:`warnings.warn` or :py:func:`warnings.warn_explicit` directly instead.
Generate a warning for this test session.
"""
from _pytest.warning_types import RemovedInPytest4Warning
if isinstance(fslocation, (tuple, list)) and len(fslocation) > 2:
filename, lineno = fslocation[:2]
else:
filename = "unknown file"
lineno = 0
msg = "config.warn has been deprecated, use warnings.warn instead"
if nodeid:
msg = "{}: {}".format(nodeid, msg)
warnings.warn_explicit(
msg, RemovedInPytest4Warning, filename=filename, lineno=lineno
)
self.hook.pytest_logwarning.call_historic( self.hook.pytest_logwarning.call_historic(
kwargs=dict( kwargs=dict(
code=code, message=message, fslocation=fslocation, nodeid=nodeid code=code, message=message, fslocation=fslocation, nodeid=nodeid
@ -674,7 +695,6 @@ class Config(object):
r = determine_setup( r = determine_setup(
ns.inifilename, ns.inifilename,
ns.file_or_dir + unknown_args, ns.file_or_dir + unknown_args,
warnfunc=self.warn,
rootdir_cmd_arg=ns.rootdir or None, rootdir_cmd_arg=ns.rootdir or None,
) )
self.rootdir, self.inifile, self.inicfg = r self.rootdir, self.inifile, self.inicfg = r

View File

@ -10,7 +10,7 @@ def exists(path, ignore=EnvironmentError):
return False return False
def getcfg(args, warnfunc=None): def getcfg(args):
""" """
Search the list of arguments for a valid ini-file for pytest, Search the list of arguments for a valid ini-file for pytest,
and return a tuple of (rootdir, inifile, cfg-dict). and return a tuple of (rootdir, inifile, cfg-dict).
@ -34,9 +34,13 @@ def getcfg(args, warnfunc=None):
if exists(p): if exists(p):
iniconfig = py.iniconfig.IniConfig(p) iniconfig = py.iniconfig.IniConfig(p)
if "pytest" in iniconfig.sections: if "pytest" in iniconfig.sections:
if inibasename == "setup.cfg" and warnfunc: if inibasename == "setup.cfg":
warnfunc( import warnings
"C1", CFG_PYTEST_SECTION.format(filename=inibasename) from _pytest.warning_types import RemovedInPytest4Warning
warnings.warn(
CFG_PYTEST_SECTION.format(filename=inibasename),
RemovedInPytest4Warning,
) )
return base, p, iniconfig["pytest"] return base, p, iniconfig["pytest"]
if ( if (
@ -95,7 +99,7 @@ def get_dirs_from_args(args):
return [get_dir_from_path(path) for path in possible_paths if path.exists()] return [get_dir_from_path(path) for path in possible_paths if path.exists()]
def determine_setup(inifile, args, warnfunc=None, rootdir_cmd_arg=None): def determine_setup(inifile, args, rootdir_cmd_arg=None):
dirs = get_dirs_from_args(args) dirs = get_dirs_from_args(args)
if inifile: if inifile:
iniconfig = py.iniconfig.IniConfig(inifile) iniconfig = py.iniconfig.IniConfig(inifile)
@ -105,23 +109,28 @@ def determine_setup(inifile, args, warnfunc=None, rootdir_cmd_arg=None):
for section in sections: for section in sections:
try: try:
inicfg = iniconfig[section] inicfg = iniconfig[section]
if is_cfg_file and section == "pytest" and warnfunc: if is_cfg_file and section == "pytest":
from _pytest.warning_types import RemovedInPytest4Warning
from _pytest.deprecated import CFG_PYTEST_SECTION from _pytest.deprecated import CFG_PYTEST_SECTION
import warnings
warnfunc("C1", CFG_PYTEST_SECTION.format(filename=str(inifile))) warnings.warn(
CFG_PYTEST_SECTION.format(filename=str(inifile)),
RemovedInPytest4Warning,
)
break break
except KeyError: except KeyError:
inicfg = None inicfg = None
rootdir = get_common_ancestor(dirs) rootdir = get_common_ancestor(dirs)
else: else:
ancestor = get_common_ancestor(dirs) ancestor = get_common_ancestor(dirs)
rootdir, inifile, inicfg = getcfg([ancestor], warnfunc=warnfunc) rootdir, inifile, inicfg = getcfg([ancestor])
if rootdir is None: if rootdir is None:
for rootdir in ancestor.parts(reverse=True): for rootdir in ancestor.parts(reverse=True):
if rootdir.join("setup.py").exists(): if rootdir.join("setup.py").exists():
break break
else: else:
rootdir, inifile, inicfg = getcfg(dirs, warnfunc=warnfunc) rootdir, inifile, inicfg = getcfg(dirs)
if rootdir is None: if rootdir is None:
rootdir = get_common_ancestor([py.path.local(), ancestor]) rootdir = get_common_ancestor([py.path.local(), ancestor])
is_fs_root = os.path.splitdrive(str(rootdir))[1] == "/" is_fs_root = os.path.splitdrive(str(rootdir))[1] == "/"

View File

@ -1281,8 +1281,12 @@ class FixtureManager(object):
marker = defaultfuncargprefixmarker marker = defaultfuncargprefixmarker
from _pytest import deprecated from _pytest import deprecated
self.config.warn( filename, lineno = getfslineno(obj)
"C1", deprecated.FUNCARG_PREFIX.format(name=name), nodeid=nodeid warnings.warn_explicit(
deprecated.FUNCARG_PREFIX.format(name=name),
RemovedInPytest4Warning,
filename=str(filename),
lineno=lineno + 1,
) )
name = name[len(self._argprefix) :] name = name[len(self._argprefix) :]
elif not isinstance(marker, FixtureFunctionMarker): elif not isinstance(marker, FixtureFunctionMarker):

View File

@ -274,8 +274,11 @@ def record_xml_attribute(request):
The fixture is callable with ``(name, value)``, with value being The fixture is callable with ``(name, value)``, with value being
automatically xml-encoded automatically xml-encoded
""" """
request.node.warn( from _pytest.warning_types import PytestWarning
code="C3", message="record_xml_attribute is an experimental feature"
request.node.std_warn(
message="record_xml_attribute is an experimental feature",
category=PytestWarning,
) )
xml = getattr(request.config, "_xml", None) xml = getattr(request.config, "_xml", None)
if xml is not None: if xml is not None:

View File

@ -137,8 +137,20 @@ class Node(object):
return "<%s %r>" % (self.__class__.__name__, getattr(self, "name", None)) return "<%s %r>" % (self.__class__.__name__, getattr(self, "name", None))
def warn(self, code, message): def warn(self, code, message):
""" generate a warning with the given code and message for this """
item. """ .. deprecated:: 3.8
Use :meth:`Node.std_warn <_pytest.nodes.Node.std_warn>` instead.
Generate a warning with the given code and message for this item.
"""
from _pytest.warning_types import RemovedInPytest4Warning
self.std_warn(
"Node.warn has been deprecated, use Node.std_warn instead",
RemovedInPytest4Warning,
)
assert isinstance(code, str) assert isinstance(code, str)
fslocation = get_fslocation_from_item(self) fslocation = get_fslocation_from_item(self)
self.ihook.pytest_logwarning.call_historic( self.ihook.pytest_logwarning.call_historic(
@ -148,12 +160,24 @@ class Node(object):
) )
def std_warn(self, message, category=None): def std_warn(self, message, category=None):
"""Issue a warning for this item.
Warnings will be displayed after the test session, unless explicitly suppressed
:param Union[str,Warning] message: text message of the warning or ``Warning`` instance.
:param Type[Warning] category: warning category.
"""
from _pytest.warning_types import PytestWarning from _pytest.warning_types import PytestWarning
if category is None: if category is None:
assert isinstance(message, PytestWarning) assert isinstance(message, PytestWarning)
path, lineno = get_fslocation_from_item(self) path, lineno = get_fslocation_from_item(self)
warnings.warn_explicit(message, category, filename=str(path), lineno=lineno) warnings.warn_explicit(
message,
category,
filename=str(path),
lineno=lineno + 1 if lineno is not None else None,
)
# methods for ordering nodes # methods for ordering nodes
@property @property
@ -323,6 +347,8 @@ def get_fslocation_from_item(item):
* "fslocation": a pair (path, lineno) * "fslocation": a pair (path, lineno)
* "fspath": just a path * "fspath": just a path
:rtype: a tuple of (str|LocalPath, int) with filename and line number.
""" """
result = getattr(item, "location", None) result = getattr(item, "location", None)
if result is not None: if result is not None:
@ -330,7 +356,7 @@ def get_fslocation_from_item(item):
obj = getattr(item, "obj", None) obj = getattr(item, "obj", None)
if obj is not None: if obj is not None:
return getfslineno(obj) return getfslineno(obj)
return getattr(item, "fspath", None), None return getattr(item, "fspath", "unknown location"), -1
class Collector(Node): class Collector(Node):

View File

@ -44,7 +44,11 @@ from _pytest.mark.structures import (
get_unpacked_marks, get_unpacked_marks,
normalize_mark_list, normalize_mark_list,
) )
from _pytest.warning_types import PytestUsageWarning, RemovedInPytest4Warning from _pytest.warning_types import (
PytestUsageWarning,
RemovedInPytest4Warning,
PytestWarning,
)
# relative paths that we use to filter traceback entries from appearing to the user; # relative paths that we use to filter traceback entries from appearing to the user;
# see filter_traceback # see filter_traceback
@ -239,9 +243,12 @@ def pytest_pycollect_makeitem(collector, name, obj):
# or a funtools.wrapped. # or a funtools.wrapped.
# We musn't if it's been wrapped with mock.patch (python 2 only) # We musn't if it's been wrapped with mock.patch (python 2 only)
if not (isfunction(obj) or isfunction(get_real_func(obj))): if not (isfunction(obj) or isfunction(get_real_func(obj))):
collector.warn( filename, lineno = getfslineno(obj)
code="C2", warnings.warn_explicit(
message="cannot collect %r because it is not a function." % name, message="cannot collect %r because it is not a function." % name,
category=PytestWarning,
filename=str(filename),
lineno=lineno + 1,
) )
elif getattr(obj, "__test__", True): elif getattr(obj, "__test__", True):
if is_generator(obj): if is_generator(obj):
@ -800,7 +807,7 @@ class Generator(FunctionMixin, PyCollector):
) )
seen[name] = True seen[name] = True
values.append(self.Function(name, self, args=args, callobj=call)) values.append(self.Function(name, self, args=args, callobj=call))
self.warn("C1", deprecated.YIELD_TESTS) self.std_warn(deprecated.YIELD_TESTS, RemovedInPytest4Warning)
return values return values
def getcallargs(self, obj): def getcallargs(self, obj):
@ -1107,9 +1114,10 @@ class Metafunc(fixtures.FuncargnamesCompatAttr):
invocation through the ``request.param`` attribute. invocation through the ``request.param`` attribute.
""" """
if self.config: if self.config:
self.config.warn( self.definition.std_warn(
"C1", message=deprecated.METAFUNC_ADD_CALL, fslocation=None deprecated.METAFUNC_ADD_CALL, RemovedInPytest4Warning
) )
assert funcargs is None or isinstance(funcargs, dict) assert funcargs is None or isinstance(funcargs, dict)
if funcargs is not None: if funcargs is not None:
for name in funcargs: for name in funcargs:

View File

@ -31,8 +31,10 @@ def pytest_configure(config):
config.pluginmanager.register(config._resultlog) config.pluginmanager.register(config._resultlog)
from _pytest.deprecated import RESULT_LOG from _pytest.deprecated import RESULT_LOG
import warnings
from _pytest.warning_types import RemovedInPytest4Warning
config.warn("C1", RESULT_LOG) warnings.warn(RESULT_LOG, RemovedInPytest4Warning)
def pytest_unconfigure(config): def pytest_unconfigure(config):

View File

@ -526,7 +526,7 @@ class TestInvocationVariants(object):
assert pytest.main == py.test.cmdline.main assert pytest.main == py.test.cmdline.main
def test_invoke_with_string(self, capsys): def test_invoke_with_string(self, capsys):
retcode = pytest.main("-h") retcode = pytest.main(["-h"])
assert not retcode assert not retcode
out, err = capsys.readouterr() out, err = capsys.readouterr()
assert "--help" in out assert "--help" in out

View File

@ -5,6 +5,7 @@ import os
import pytest import pytest
@pytest.mark.filterwarnings("default")
def test_yield_tests_deprecation(testdir): def test_yield_tests_deprecation(testdir):
testdir.makepyfile( testdir.makepyfile(
""" """
@ -18,16 +19,18 @@ def test_yield_tests_deprecation(testdir):
yield func1, 1, 1 yield func1, 1, 1
""" """
) )
result = testdir.runpytest("-ra") result = testdir.runpytest()
result.stdout.fnmatch_lines( result.stdout.fnmatch_lines(
[ [
"*yield tests are deprecated, and scheduled to be removed in pytest 4.0*", "*test_yield_tests_deprecation.py:3:*yield tests are deprecated*",
"*test_yield_tests_deprecation.py:6:*yield tests are deprecated*",
"*2 passed*", "*2 passed*",
] ]
) )
assert result.stdout.str().count("yield tests are deprecated") == 2 assert result.stdout.str().count("yield tests are deprecated") == 2
@pytest.mark.filterwarnings("default")
def test_funcarg_prefix_deprecation(testdir): def test_funcarg_prefix_deprecation(testdir):
testdir.makepyfile( testdir.makepyfile(
""" """
@ -42,16 +45,18 @@ def test_funcarg_prefix_deprecation(testdir):
result.stdout.fnmatch_lines( result.stdout.fnmatch_lines(
[ [
( (
"*pytest_funcarg__value: " "*test_funcarg_prefix_deprecation.py:1: *pytest_funcarg__value: "
'declaring fixtures using "pytest_funcarg__" prefix is deprecated ' 'declaring fixtures using "pytest_funcarg__" prefix is deprecated*'
"and scheduled to be removed in pytest 4.0. "
"Please remove the prefix and use the @pytest.fixture decorator instead."
), ),
"*1 passed*", "*1 passed*",
] ]
) )
@pytest.mark.filterwarnings("default")
@pytest.mark.xfail(
reason="#2891 need to handle warnings during pre-config", strict=True
)
def test_pytest_setup_cfg_deprecated(testdir): def test_pytest_setup_cfg_deprecated(testdir):
testdir.makefile( testdir.makefile(
".cfg", ".cfg",
@ -66,6 +71,10 @@ def test_pytest_setup_cfg_deprecated(testdir):
) )
@pytest.mark.filterwarnings("default")
@pytest.mark.xfail(
reason="#2891 need to handle warnings during pre-config", strict=True
)
def test_pytest_custom_cfg_deprecated(testdir): def test_pytest_custom_cfg_deprecated(testdir):
testdir.makefile( testdir.makefile(
".cfg", ".cfg",
@ -80,6 +89,9 @@ def test_pytest_custom_cfg_deprecated(testdir):
) )
@pytest.mark.xfail(
reason="#2891 need to handle warnings during pre-config", strict=True
)
def test_str_args_deprecated(tmpdir, testdir): def test_str_args_deprecated(tmpdir, testdir):
"""Deprecate passing strings to pytest.main(). Scheduled for removal in pytest-4.0.""" """Deprecate passing strings to pytest.main(). Scheduled for removal in pytest-4.0."""
from _pytest.main import EXIT_NOTESTSCOLLECTED from _pytest.main import EXIT_NOTESTSCOLLECTED
@ -103,6 +115,10 @@ def test_getfuncargvalue_is_deprecated(request):
pytest.deprecated_call(request.getfuncargvalue, "tmpdir") pytest.deprecated_call(request.getfuncargvalue, "tmpdir")
@pytest.mark.filterwarnings("default")
@pytest.mark.xfail(
reason="#2891 need to handle warnings during pre-config", strict=True
)
def test_resultlog_is_deprecated(testdir): def test_resultlog_is_deprecated(testdir):
result = testdir.runpytest("--help") result = testdir.runpytest("--help")
result.stdout.fnmatch_lines(["*DEPRECATED path for machine-readable result log*"]) result.stdout.fnmatch_lines(["*DEPRECATED path for machine-readable result log*"])

View File

@ -462,6 +462,7 @@ class TestFunction(object):
assert isinstance(modcol, pytest.Module) assert isinstance(modcol, pytest.Module)
assert hasattr(modcol.obj, "test_func") assert hasattr(modcol.obj, "test_func")
@pytest.mark.filterwarnings("default")
def test_function_as_object_instance_ignored(self, testdir): def test_function_as_object_instance_ignored(self, testdir):
testdir.makepyfile( testdir.makepyfile(
""" """
@ -472,8 +473,14 @@ class TestFunction(object):
test_a = A() test_a = A()
""" """
) )
reprec = testdir.inline_run() result = testdir.runpytest()
reprec.assertoutcome() result.stdout.fnmatch_lines(
[
"collected 0 items",
"*test_function_as_object_instance_ignored.py:2: "
"*cannot collect 'test_a' because it is not a function.",
]
)
def test_function_equality(self, testdir, tmpdir): def test_function_equality(self, testdir, tmpdir):
from _pytest.fixtures import FixtureManager from _pytest.fixtures import FixtureManager
@ -1468,6 +1475,7 @@ def test_collect_functools_partial(testdir):
result.assertoutcome(passed=6, failed=2) result.assertoutcome(passed=6, failed=2)
@pytest.mark.filterwarnings("default")
def test_dont_collect_non_function_callable(testdir): def test_dont_collect_non_function_callable(testdir):
"""Test for issue https://github.com/pytest-dev/pytest/issues/331 """Test for issue https://github.com/pytest-dev/pytest/issues/331
@ -1490,7 +1498,7 @@ def test_dont_collect_non_function_callable(testdir):
result.stdout.fnmatch_lines( result.stdout.fnmatch_lines(
[ [
"*collected 1 item*", "*collected 1 item*",
"*cannot collect 'test_a' because it is not a function*", "*test_dont_collect_non_function_callable.py:2: *cannot collect 'test_a' because it is not a function*",
"*1 passed, 1 warnings in *", "*1 passed, 1 warnings in *",
] ]
) )

View File

@ -407,8 +407,8 @@ class TestMetafunc(object):
"<Module 'test_parametrize_ids_exception.py'>", "<Module 'test_parametrize_ids_exception.py'>",
" <Function 'test_foo[a]'>", " <Function 'test_foo[a]'>",
" <Function 'test_foo[b]'>", " <Function 'test_foo[b]'>",
"*test_parametrize_ids_exception.py:5: *parameter arg at position 0*", "*test_parametrize_ids_exception.py:6: *parameter arg at position 0*",
"*test_parametrize_ids_exception.py:5: *parameter arg at position 1*", "*test_parametrize_ids_exception.py:6: *parameter arg at position 1*",
] ]
) )

View File

@ -1075,6 +1075,7 @@ def test_diff_newline_at_end(monkeypatch, testdir):
) )
@pytest.mark.filterwarnings("default")
def test_assert_tuple_warning(testdir): def test_assert_tuple_warning(testdir):
testdir.makepyfile( testdir.makepyfile(
""" """
@ -1084,7 +1085,7 @@ def test_assert_tuple_warning(testdir):
) )
result = testdir.runpytest("-rw") result = testdir.runpytest("-rw")
result.stdout.fnmatch_lines( result.stdout.fnmatch_lines(
["*test_assert_tuple_warning.py:2", "*assertion is always true*"] ["*test_assert_tuple_warning.py:2:*assertion is always true*"]
) )

View File

@ -759,16 +759,12 @@ def test_rewritten():
testdir.makepyfile("import a_package_without_init_py.module") testdir.makepyfile("import a_package_without_init_py.module")
assert testdir.runpytest().ret == EXIT_NOTESTSCOLLECTED assert testdir.runpytest().ret == EXIT_NOTESTSCOLLECTED
def test_rewrite_warning(self, pytestconfig, monkeypatch): def test_rewrite_warning(self, pytestconfig):
hook = AssertionRewritingHook(pytestconfig) hook = AssertionRewritingHook(pytestconfig)
warnings = [] from _pytest.warning_types import PytestWarning
def mywarn(code, msg): with pytest.warns(PytestWarning):
warnings.append((code, msg))
monkeypatch.setattr(hook.config, "warn", mywarn)
hook.mark_rewrite("_pytest") hook.mark_rewrite("_pytest")
assert "_pytest" in warnings[0][1]
def test_rewrite_module_imported_from_conftest(self, testdir): def test_rewrite_module_imported_from_conftest(self, testdir):
testdir.makeconftest( testdir.makeconftest(

View File

@ -31,6 +31,7 @@ class TestNewAPI(object):
val = config.cache.get("key/name", -2) val = config.cache.get("key/name", -2)
assert val == -2 assert val == -2
@pytest.mark.filterwarnings("default")
def test_cache_writefail_cachfile_silent(self, testdir): def test_cache_writefail_cachfile_silent(self, testdir):
testdir.makeini("[pytest]") testdir.makeini("[pytest]")
testdir.tmpdir.join(".pytest_cache").write("gone wrong") testdir.tmpdir.join(".pytest_cache").write("gone wrong")

View File

@ -135,13 +135,13 @@ class TestConfigCmdlineParsing(object):
""" """
) )
testdir.makefile( testdir.makefile(
".cfg", ".ini",
custom=""" custom="""
[pytest] [pytest]
custom = 1 custom = 1
""", """,
) )
config = testdir.parseconfig("-c", "custom.cfg") config = testdir.parseconfig("-c", "custom.ini")
assert config.getini("custom") == "1" assert config.getini("custom") == "1"
testdir.makefile( testdir.makefile(
@ -155,8 +155,8 @@ class TestConfigCmdlineParsing(object):
assert config.getini("custom") == "1" assert config.getini("custom") == "1"
def test_absolute_win32_path(self, testdir): def test_absolute_win32_path(self, testdir):
temp_cfg_file = testdir.makefile( temp_ini_file = testdir.makefile(
".cfg", ".ini",
custom=""" custom="""
[pytest] [pytest]
addopts = --version addopts = --version
@ -164,8 +164,8 @@ class TestConfigCmdlineParsing(object):
) )
from os.path import normpath from os.path import normpath
temp_cfg_file = normpath(str(temp_cfg_file)) temp_ini_file = normpath(str(temp_ini_file))
ret = pytest.main("-c " + temp_cfg_file) ret = pytest.main(["-c", temp_ini_file])
assert ret == _pytest.main.EXIT_OK assert ret == _pytest.main.EXIT_OK
@ -783,13 +783,14 @@ def test_collect_pytest_prefix_bug(pytestconfig):
assert pm.parse_hookimpl_opts(Dummy(), "pytest_something") is None assert pm.parse_hookimpl_opts(Dummy(), "pytest_something") is None
class TestWarning(object): class TestLegacyWarning(object):
@pytest.mark.filterwarnings("default")
def test_warn_config(self, testdir): def test_warn_config(self, testdir):
testdir.makeconftest( testdir.makeconftest(
""" """
values = [] values = []
def pytest_configure(config): def pytest_runtest_setup(item):
config.warn("C1", "hello") item.config.warn("C1", "hello")
def pytest_logwarning(code, message): def pytest_logwarning(code, message):
if message == "hello" and code == "C1": if message == "hello" and code == "C1":
values.append(1) values.append(1)
@ -802,9 +803,12 @@ class TestWarning(object):
assert conftest.values == [1] assert conftest.values == [1]
""" """
) )
reprec = testdir.inline_run() result = testdir.runpytest()
reprec.assertoutcome(passed=1) result.stdout.fnmatch_lines(
["*hello", "*config.warn has been deprecated*", "*1 passed*"]
)
@pytest.mark.filterwarnings("default")
def test_warn_on_test_item_from_request(self, testdir, request): def test_warn_on_test_item_from_request(self, testdir, request):
testdir.makepyfile( testdir.makepyfile(
""" """
@ -819,7 +823,6 @@ class TestWarning(object):
""" """
) )
result = testdir.runpytest("--disable-pytest-warnings") result = testdir.runpytest("--disable-pytest-warnings")
assert result.parseoutcomes()["warnings"] > 0
assert "hello" not in result.stdout.str() assert "hello" not in result.stdout.str()
result = testdir.runpytest() result = testdir.runpytest()
@ -828,6 +831,7 @@ class TestWarning(object):
===*warnings summary*=== ===*warnings summary*===
*test_warn_on_test_item_from_request.py::test_hello* *test_warn_on_test_item_from_request.py::test_hello*
*hello* *hello*
*test_warn_on_test_item_from_request.py:7:*Node.warn has been deprecated, use Node.std_warn instead*
""" """
) )
@ -847,7 +851,7 @@ class TestRootdir(object):
@pytest.mark.parametrize("name", "setup.cfg tox.ini pytest.ini".split()) @pytest.mark.parametrize("name", "setup.cfg tox.ini pytest.ini".split())
def test_with_ini(self, tmpdir, name): def test_with_ini(self, tmpdir, name):
inifile = tmpdir.join(name) inifile = tmpdir.join(name)
inifile.write("[pytest]\n") inifile.write("[pytest]\n" if name != "setup.cfg" else "[tool:pytest]\n")
a = tmpdir.mkdir("a") a = tmpdir.mkdir("a")
b = a.mkdir("b") b = a.mkdir("b")
@ -893,11 +897,14 @@ class TestRootdir(object):
class TestOverrideIniArgs(object): class TestOverrideIniArgs(object):
@pytest.mark.parametrize("name", "setup.cfg tox.ini pytest.ini".split()) @pytest.mark.parametrize("name", "setup.cfg tox.ini pytest.ini".split())
def test_override_ini_names(self, testdir, name): def test_override_ini_names(self, testdir, name):
section = "[pytest]" if name != "setup.cfg" else "[tool:pytest]"
testdir.tmpdir.join(name).write( testdir.tmpdir.join(name).write(
textwrap.dedent( textwrap.dedent(
""" """
[pytest] {section}
custom = 1.0""" custom = 1.0""".format(
section=section
)
) )
) )
testdir.makeconftest( testdir.makeconftest(

View File

@ -1005,6 +1005,7 @@ def test_record_property_same_name(testdir):
pnodes[1].assert_attr(name="foo", value="baz") pnodes[1].assert_attr(name="foo", value="baz")
@pytest.mark.filterwarnings("default")
def test_record_attribute(testdir): def test_record_attribute(testdir):
testdir.makepyfile( testdir.makepyfile(
""" """
@ -1023,7 +1024,10 @@ def test_record_attribute(testdir):
tnode.assert_attr(bar="1") tnode.assert_attr(bar="1")
tnode.assert_attr(foo="<1") tnode.assert_attr(foo="<1")
result.stdout.fnmatch_lines( result.stdout.fnmatch_lines(
["test_record_attribute.py::test_record", "*record_xml_attribute*experimental*"] [
"test_record_attribute.py::test_record",
"*test_record_attribute.py:6:*record_xml_attribute is an experimental feature",
]
) )

View File

@ -13,6 +13,9 @@ from _pytest.resultlog import (
) )
pytestmark = pytest.mark.filterwarnings("ignore:--result-log is deprecated")
def test_generic_path(testdir): def test_generic_path(testdir):
from _pytest.main import Session from _pytest.main import Session

View File

@ -37,7 +37,7 @@ def pyfile_with_warnings(testdir, request):
) )
@pytest.mark.filterwarnings("always") @pytest.mark.filterwarnings("default")
def test_normal_flow(testdir, pyfile_with_warnings): def test_normal_flow(testdir, pyfile_with_warnings):
""" """
Check that the warnings section is displayed, containing test node ids followed by Check that the warnings section is displayed, containing test node ids followed by

View File

@ -218,6 +218,9 @@ norecursedirs = .tox ja .hg cx_freeze_source testing/example_scripts
xfail_strict=true xfail_strict=true
filterwarnings = filterwarnings =
error error
ignore:yield tests are deprecated, and scheduled to be removed in pytest 4.0:
ignore:Metafunc.addcall is deprecated and scheduled to be removed in pytest 4.0:
ignore:Module already imported so cannot be rewritten:
# produced by path.local # produced by path.local
ignore:bad escape.*:DeprecationWarning:re ignore:bad escape.*:DeprecationWarning:re
# produced by path.readlines # produced by path.readlines