Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 37 additions & 0 deletions changelog/13743.feature.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
Added support for native TOML configuration files.

While pytest, since version 6, supports configuration in ``pyproject.toml`` files under ``[tool.pytest.ini_options]``,
it does so in an "INI compatibility mode", where all configuration values are treated as strings or list of strings.
Now, pytest supports the native TOML data model.

In ``pyproject.toml``, the native TOML configuration is under the ``[tool.pytest]`` table.

.. code-block:: toml
# pyproject.toml
[tool.pytest]
minversion = "9.0"
addopts = ["-ra", "-q"]
testpaths = [
"tests",
"integration",
]
The ``[tool.pytest.ini_options]`` table remains supported, but both tables cannot be used at the same time.

If you prefer to use a separate configuration file, or don't use ``pyproject.toml``, you can use ``pytest.toml`` or ``.pytest.toml``:

.. code-block:: toml
# pytest.toml or .pytest.toml
[pytest]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wish I'd seen this earlier — I tend to prefer keeping the same section names in other TOML files due to the ease of migration between them: coveragepy/coveragepy#1952 (comment).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I disagree and think that would present a markedly worse UX coveragepy/coveragepy#1952 (comment)

minversion = "9.0"
addopts = ["-ra", "-q"]
testpaths = [
"tests",
"integration",
]
The documentation now shows configuration snippets in both TOML and INI formats, in a tabbed interface.

See :ref:`config file formats` for full details.
2 changes: 2 additions & 0 deletions changelog/13849.bugfix.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Hidden ``.pytest.ini`` files are now picked up as the config file even if empty.
This was an inconsistency with non-hidden ``pytest.ini``.
1 change: 1 addition & 0 deletions doc/en/conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@
"sphinx.ext.todo",
"sphinx.ext.viewcode",
"sphinx_removed_in",
"sphinx_inline_tabs",
"sphinxcontrib_trio",
"sphinxcontrib.towncrier.ext", # provides `towncrier-draft-entries` directive
"sphinx_issues", # implements `:issue:`, `:pr:` and other GH-related roles
Expand Down
32 changes: 25 additions & 7 deletions doc/en/deprecations.rst
Original file line number Diff line number Diff line change
Expand Up @@ -845,20 +845,38 @@ that manipulate this type of file (for example, Jenkins, Azure Pipelines, etc.).
Users are recommended to try the new ``xunit2`` format and see if their tooling that consumes the JUnit
XML file supports it.

To use the new format, update your ``pytest.ini``:
To use the new format, update your configuration file:

.. code-block:: ini
.. tab:: toml

[pytest]
junit_family=xunit2
.. code-block:: toml

[pytest]
junit_family = "xunit2"

.. tab:: ini

.. code-block:: ini

[pytest]
junit_family = xunit2

If you discover that your tooling does not support the new format, and want to keep using the
legacy version, set the option to ``legacy`` instead:

.. code-block:: ini
.. tab:: toml

.. code-block:: toml

[pytest]
junit_family = "legacy"

.. tab:: ini

.. code-block:: ini

[pytest]
junit_family=legacy
[pytest]
junit_family = legacy

By using ``legacy`` you will keep using the legacy/xunit1 format when upgrading to
pytest 6.0, where the default format will be ``xunit2``.
Expand Down
20 changes: 14 additions & 6 deletions doc/en/example/markers.rst
Original file line number Diff line number Diff line change
Expand Up @@ -239,13 +239,21 @@ Registering markers

Registering markers for your test suite is simple:

.. code-block:: ini
.. tab:: toml

# content of pytest.ini
[pytest]
markers =
webtest: mark a test as a webtest.
slow: mark test as slow.
.. code-block:: toml

[pytest]
markers = ["webtest: mark a test as a webtest.", "slow: mark test as slow."]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is a example of dissonance

in toml this should be

[pytest.markers]
webtest = "..."
slow = "..."
``


.. tab:: ini

.. code-block:: ini

[pytest]
markers =
webtest: mark a test as a webtest.
slow: mark test as slow.

Multiple custom markers can be registered, by defining each one in its own line, as shown in above example.

Expand Down
96 changes: 70 additions & 26 deletions doc/en/example/pythoncollection.rst
Original file line number Diff line number Diff line change
Expand Up @@ -88,13 +88,21 @@ Example:
Changing directory recursion
-----------------------------------------------------

You can set the :confval:`norecursedirs` option in an ini-file, for example your ``pytest.ini`` in the project root directory:
You can set the :confval:`norecursedirs` option in a configuration file:

.. code-block:: ini
.. tab:: toml

# content of pytest.ini
[pytest]
norecursedirs = .svn _build tmp*
.. code-block:: toml

[pytest]
norecursedirs = [".svn", "_build", "tmp*"]

.. tab:: ini

.. code-block:: ini

[pytest]
norecursedirs = .svn _build tmp*

This would tell ``pytest`` to not recurse into typical subversion or sphinx-build directories or into any ``tmp`` prefixed directory.

Expand All @@ -108,14 +116,25 @@ the :confval:`python_files`, :confval:`python_classes` and
:confval:`python_functions` in your :ref:`configuration file <config file formats>`.
Here is an example:

.. code-block:: ini
.. tab:: toml

.. code-block:: toml

# content of pytest.ini
# Example 1: have pytest look for "check" instead of "test"
[pytest]
python_files = check_*.py
python_classes = Check
python_functions = *_check
# Example 1: have pytest look for "check" instead of "test"
[pytest]
python_files = ["check_*.py"]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

in future we might want to have python.* as table instead of the prefixes

python_classes = ["Check"]
python_functions = ["*_check"]

.. tab:: ini

.. code-block:: ini

# Example 1: have pytest look for "check" instead of "test"
[pytest]
python_files = check_*.py
python_classes = Check
python_functions = *_check

This would make ``pytest`` look for tests in files that match the ``check_*
.py`` glob-pattern, ``Check`` prefixes in classes, and functions and methods
Expand Down Expand Up @@ -152,12 +171,21 @@ The test collection would look like this:

You can check for multiple glob patterns by adding a space between the patterns:

.. code-block:: ini
.. tab:: toml

.. code-block:: toml

# Example 2: have pytest look for files with "test" and "example"
[pytest]
python_files = ["test_*.py", "example_*.py"]

# Example 2: have pytest look for files with "test" and "example"
# content of pytest.ini
[pytest]
python_files = test_*.py example_*.py
.. tab:: ini

.. code-block:: ini

# Example 2: have pytest look for files with "test" and "example"
[pytest]
python_files = test_*.py example_*.py

.. note::

Expand All @@ -178,14 +206,22 @@ example if you have unittest2 installed you can type:
pytest --pyargs unittest2.test.test_skipping -q

which would run the respective test module. Like with
other options, through an ini-file and the :confval:`addopts` option you
other options, through a configuration file and the :confval:`addopts` option you
can make this change more permanently:

.. code-block:: ini
.. tab:: toml

.. code-block:: toml

[pytest]
addopts = ["--pyargs"]

.. tab:: ini

# content of pytest.ini
[pytest]
addopts = --pyargs
.. code-block:: ini

[pytest]
addopts = --pyargs

Now a simple invocation of ``pytest NAME`` will check
if NAME exists as an importable package/module and otherwise
Expand Down Expand Up @@ -224,11 +260,19 @@ Customizing test collection

You can easily instruct ``pytest`` to discover tests from every Python file:

.. code-block:: ini
.. tab:: toml

.. code-block:: toml

[pytest]
python_files = ["*.py"]

.. tab:: ini

.. code-block:: ini

# content of pytest.ini
[pytest]
python_files = *.py
[pytest]
python_files = *.py

However, many projects will have a ``setup.py`` which they don't want to be
imported. Moreover, there may files only importable by a specific python
Expand Down
18 changes: 13 additions & 5 deletions doc/en/example/simple.rst
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,19 @@ every time you use ``pytest``. For example, if you always want to see
detailed info on skipped and xfailed tests, as well as have terser "dot"
progress output, you can write it into a configuration file:

.. code-block:: ini
.. tab:: toml

# content of pytest.ini
[pytest]
addopts = -ra -q
.. code-block:: toml

[pytest]
addopts = ["-ra", "-q"]

.. tab:: ini

.. code-block:: ini

[pytest]
addopts = -ra -q


Alternatively, you can set a ``PYTEST_ADDOPTS`` environment variable to add command
Expand All @@ -29,7 +37,7 @@ Here's how the command-line is built in the presence of ``addopts`` or the envir

.. code-block:: text

<pytest.ini:addopts> $PYTEST_ADDOPTS <extra command-line arguments>
<configuration file addopts> $PYTEST_ADDOPTS <extra command-line arguments>

So if the user executes in the command-line:

Expand Down
36 changes: 26 additions & 10 deletions doc/en/explanation/goodpractices.rst
Original file line number Diff line number Diff line change
Expand Up @@ -94,14 +94,21 @@ This has the following benefits:

For new projects, we recommend to use ``importlib`` :ref:`import mode <import-modes>`
(see which-import-mode_ for a detailed explanation).
To this end, add the following to your ``pyproject.toml``:
To this end, add the following to your configuration file:

.. code-block:: toml
.. tab:: toml

.. code-block:: toml

[pytest]
addopts = ["--import-mode=importlib"]

.. tab:: ini

.. code-block:: ini

[tool.pytest.ini_options]
addopts = [
"--import-mode=importlib",
]
[pytest]
addopts = --import-mode=importlib

.. _src-layout:

Expand All @@ -126,12 +133,21 @@ which are better explained in this excellent `blog post`_ by Ionel Cristian Măr
PYTHONPATH=src pytest

or in a permanent manner by using the :confval:`pythonpath` configuration variable and adding the
following to your ``pyproject.toml``:
following to your configuration file:

.. code-block:: toml
.. tab:: toml

.. code-block:: toml

[pytest]
pythonpath = ["src"]

.. tab:: ini

.. code-block:: ini

[tool.pytest.ini_options]
pythonpath = "src"
[pytest]
pythonpath = src

.. note::

Expand Down
Loading