diff --git a/changelog/3085.removal.rst b/changelog/3085.removal.rst new file mode 100644 index 000000000..67ba04c28 --- /dev/null +++ b/changelog/3085.removal.rst @@ -0,0 +1,3 @@ +Removed support for passing strings to ``pytest.main``. Now, always pass a list of strings instead. + +See our `docs `__ on information on how to update your code. diff --git a/changelog/4547.removal.rst b/changelog/4547.removal.rst new file mode 100644 index 000000000..a30d5d7bd --- /dev/null +++ b/changelog/4547.removal.rst @@ -0,0 +1,3 @@ +The deprecated ``record_xml_property`` fixture has been removed, use the more generic ``record_property`` instead. + +See our `docs `__ for more information. diff --git a/doc/en/deprecations.rst b/doc/en/deprecations.rst index 37cffb1fb..6ec80cbe8 100644 --- a/doc/en/deprecations.rst +++ b/doc/en/deprecations.rst @@ -149,28 +149,6 @@ As part of a large :ref:`marker-revamp`, :meth:`_pytest.nodes.Node.get_marker` i :ref:`the documentation ` on tips on how to update your code. -record_xml_property -~~~~~~~~~~~~~~~~~~~ - -.. deprecated:: 3.5 - -The ``record_xml_property`` fixture is now deprecated in favor of the more generic ``record_property``, which -can be used by other consumers (for example ``pytest-html``) to obtain custom information about the test run. - -This is just a matter of renaming the fixture as the API is the same: - -.. code-block:: python - - def test_foo(record_xml_property): - ... - -Change to: - -.. code-block:: python - - def test_foo(record_property): - ... - pytest_plugins in non-top-level conftest files ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ @@ -215,27 +193,6 @@ To update the code, use ``pytest.param``: -Passing command-line string to ``pytest.main()`` -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -.. deprecated:: 3.0 - -Passing a command-line string to ``pytest.main()`` is deprecated: - -.. code-block:: python - - pytest.main("-v -s") - -Pass a list instead: - -.. code-block:: python - - pytest.main(["-v", "-s"]) - - -By passing a string, users expect that pytest will interpret that command-line using the shell rules they are working -on (for example ``bash`` or ``Powershell``), but this is very hard/impossible to do in a portable way. - [pytest] section in setup.cfg files ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ @@ -353,6 +310,52 @@ more information. This has been documented as deprecated for years, but only now we are actually emitting deprecation warnings. +record_xml_property +~~~~~~~~~~~~~~~~~~~ + +*Removed in version 4.0.* + +The ``record_xml_property`` fixture is now deprecated in favor of the more generic ``record_property``, which +can be used by other consumers (for example ``pytest-html``) to obtain custom information about the test run. + +This is just a matter of renaming the fixture as the API is the same: + +.. code-block:: python + + def test_foo(record_xml_property): + ... + +Change to: + +.. code-block:: python + + def test_foo(record_property): + ... + + +Passing command-line string to ``pytest.main()`` +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +*Removed in version 4.0.* + +Passing a command-line string to ``pytest.main()`` is deprecated: + +.. code-block:: python + + pytest.main("-v -s") + +Pass a list instead: + +.. code-block:: python + + pytest.main(["-v", "-s"]) + + +By passing a string, users expect that pytest will interpret that command-line using the shell rules they are working +on (for example ``bash`` or ``Powershell``), but this is very hard/impossible to do in a portable way. + + + ``yield`` tests ~~~~~~~~~~~~~~~ diff --git a/src/_pytest/config/__init__.py b/src/_pytest/config/__init__.py index 3ed82694b..d68b1249e 100644 --- a/src/_pytest/config/__init__.py +++ b/src/_pytest/config/__init__.py @@ -173,12 +173,9 @@ def _prepareconfig(args=None, plugins=None): elif isinstance(args, py.path.local): args = [str(args)] elif not isinstance(args, (tuple, list)): - if not isinstance(args, str): - raise ValueError("not a string or argument list: %r" % (args,)) - args = shlex.split(args, posix=sys.platform != "win32") - from _pytest import deprecated + msg = "`args` parameter expected to be a list or tuple of strings, got: {!r} (type: {})" + raise TypeError(msg.format(args, type(args))) - warning = deprecated.MAIN_STR_ARGS config = get_config() pluginmanager = config.pluginmanager try: diff --git a/src/_pytest/deprecated.py b/src/_pytest/deprecated.py index 67f0d534f..8b2fbf3f9 100644 --- a/src/_pytest/deprecated.py +++ b/src/_pytest/deprecated.py @@ -17,11 +17,6 @@ from _pytest.warning_types import RemovedInPytest4Warning from _pytest.warning_types import UnformattedWarning -MAIN_STR_ARGS = RemovedInPytest4Warning( - "passing a string to pytest.main() is deprecated, " - "pass a list of arguments instead." -) - YIELD_TESTS = "yield tests were removed in pytest 4.0 - {name} will be ignored" @@ -82,12 +77,6 @@ WARNS_EXEC = PytestDeprecationWarning( "See https://docs.pytest.org/en/latest/deprecations.html#raises-warns-exec" ) -RECORD_XML_PROPERTY = RemovedInPytest4Warning( - 'Fixture renamed from "record_xml_property" to "record_property" as user ' - "properties are now available to all reporters.\n" - '"record_xml_property" is now deprecated.' -) - PYTEST_PLUGINS_FROM_NON_TOP_LEVEL_CONFTEST = RemovedInPytest4Warning( "Defining pytest_plugins in a non-top-level conftest is deprecated, " diff --git a/src/_pytest/junitxml.py b/src/_pytest/junitxml.py index 672fde5d5..1a06ea6d1 100644 --- a/src/_pytest/junitxml.py +++ b/src/_pytest/junitxml.py @@ -263,16 +263,6 @@ def record_property(request): return append_property -@pytest.fixture -def record_xml_property(record_property, request): - """(Deprecated) use record_property.""" - from _pytest import deprecated - - request.node.warn(deprecated.RECORD_XML_PROPERTY) - - return record_property - - @pytest.fixture def record_xml_attribute(request): """Add extra xml attributes to the tag for the calling test. diff --git a/testing/acceptance_test.py b/testing/acceptance_test.py index 0b7af5338..7276445ac 100644 --- a/testing/acceptance_test.py +++ b/testing/acceptance_test.py @@ -559,12 +559,11 @@ class TestInvocationVariants(object): def test_equivalence_pytest_pytest(self): assert pytest.main == py.test.cmdline.main - def test_invoke_with_string(self, capsys): - retcode = pytest.main("-h") - assert not retcode - out, err = capsys.readouterr() - assert "--help" in out - pytest.raises(ValueError, lambda: pytest.main(0)) + def test_invoke_with_invalid_type(self, capsys): + with pytest.raises( + TypeError, match="expected to be a list or tuple of strings, got: '-h'" + ): + pytest.main("-h") def test_invoke_with_path(self, tmpdir, capsys): retcode = pytest.main(tmpdir) diff --git a/testing/deprecated_test.py b/testing/deprecated_test.py index b971a9d2e..5f5b78032 100644 --- a/testing/deprecated_test.py +++ b/testing/deprecated_test.py @@ -40,25 +40,6 @@ def test_pytest_custom_cfg_deprecated(testdir): ) -def test_str_args_deprecated(tmpdir): - """Deprecate passing strings to pytest.main(). Scheduled for removal in pytest-4.0.""" - from _pytest.main import EXIT_NOTESTSCOLLECTED - - warnings = [] - - class Collect(object): - def pytest_warning_captured(self, warning_message): - warnings.append(str(warning_message.message)) - - ret = pytest.main("%s -x" % tmpdir, plugins=[Collect()]) - msg = ( - "passing a string to pytest.main() is deprecated, " - "pass a list of arguments instead." - ) - assert msg in warnings - assert ret == EXIT_NOTESTSCOLLECTED - - def test_getfuncargvalue_is_deprecated(request): pytest.deprecated_call(request.getfuncargvalue, "tmpdir")