Compare commits

..

2 Commits

Author SHA1 Message Date
Ran Benita
f0bf4c9681 Merge pull request #9760 from bluetech/cherry-pick-release
Merge pull request #9758 from pytest-dev/release-7.1.0
2022-03-13 17:20:13 +02:00
Ran Benita
d87e1e67dd Merge pull request #9758 from pytest-dev/release-7.1.0
Prepare release 7.1.0

(cherry picked from commit 7d4d1ecde6)
2022-03-13 16:59:20 +02:00
27 changed files with 126 additions and 238 deletions

View File

@@ -1,56 +0,0 @@
name: deploy
on:
push:
tags:
# These tags are protected, see:
# https://github.com/pytest-dev/pytest/settings/tag_protection
- "[0-9]+.[0-9]+.[0-9]+"
- "[0-9]+.[0-9]+.[0-9]+rc[0-9]+"
# Set permissions at the job level.
permissions: {}
jobs:
deploy:
if: github.repository == 'pytest-dev/pytest'
runs-on: ubuntu-latest
timeout-minutes: 30
permissions:
contents: write
steps:
- uses: actions/checkout@v2
with:
fetch-depth: 0
persist-credentials: false
- name: Set up Python
uses: actions/setup-python@v2
with:
python-version: "3.7"
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install --upgrade build tox
- name: Build package
run: |
python -m build
- name: Publish package to PyPI
uses: pypa/gh-action-pypi-publish@master
with:
user: __token__
password: ${{ secrets.pypi_token }}
- name: Publish GitHub release notes
env:
GH_RELEASE_NOTES_TOKEN: ${{ github.token }}
run: |
sudo apt-get install pandoc
tox -e publish-gh-release-notes

View File

@@ -1,4 +1,4 @@
name: test
name: main
on:
push:
@@ -187,3 +187,46 @@ jobs:
fail_ci_if_error: true
files: ./coverage.xml
verbose: true
deploy:
if: github.event_name == 'push' && startsWith(github.event.ref, 'refs/tags') && github.repository == 'pytest-dev/pytest'
runs-on: ubuntu-latest
timeout-minutes: 30
permissions:
contents: write
needs: [build]
steps:
- uses: actions/checkout@v2
with:
fetch-depth: 0
persist-credentials: false
- name: Set up Python
uses: actions/setup-python@v2
with:
python-version: "3.7"
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install --upgrade build tox
- name: Build package
run: |
python -m build
- name: Publish package to PyPI
uses: pypa/gh-action-pypi-publish@master
with:
user: __token__
password: ${{ secrets.pypi_token }}
- name: Publish GitHub release notes
env:
GH_RELEASE_NOTES_TOKEN: ${{ github.token }}
run: |
sudo apt-get install pandoc
tox -e publish-gh-release-notes

View File

@@ -1,6 +1,6 @@
repos:
- repo: https://github.com/psf/black
rev: 22.3.0
rev: 22.1.0
hooks:
- id: black
args: [--safe, --quiet]
@@ -37,7 +37,7 @@ repos:
- flake8-typing-imports==1.12.0
- flake8-docstrings==1.5.0
- repo: https://github.com/asottile/reorder_python_imports
rev: v3.0.1
rev: v2.7.1
hooks:
- id: reorder-python-imports
args: ['--application-directories=.:src', --py37-plus]

View File

@@ -185,7 +185,6 @@ Katerina Koukiou
Keri Volans
Kevin Cox
Kevin J. Foley
Kian Eliasi
Kian-Meng Ang
Kodi B. Arfer
Kojo Idrissa
@@ -256,7 +255,6 @@ Ondřej Súkup
Oscar Benjamin
Parth Patel
Patrick Hayes
Paul Müller
Pauli Virtanen
Pavel Karateev
Paweł Adamczak

View File

@@ -50,8 +50,6 @@ Fix bugs
--------
Look through the `GitHub issues for bugs <https://github.com/pytest-dev/pytest/labels/type:%20bug>`_.
See also the `"status: easy" issues <https://github.com/pytest-dev/pytest/labels/status%3A%20easy>`_
that are friendly to new contributors.
:ref:`Talk <contact>` to developers to find out how you can fix specific bugs. To indicate that you are going
to work on a particular issue, add a comment to that effect on the specific issue.

View File

@@ -20,8 +20,8 @@
:target: https://codecov.io/gh/pytest-dev/pytest
:alt: Code coverage Status
.. image:: https://github.com/pytest-dev/pytest/workflows/test/badge.svg
:target: https://github.com/pytest-dev/pytest/actions?query=workflow%3Atest
.. image:: https://github.com/pytest-dev/pytest/workflows/main/badge.svg
:target: https://github.com/pytest-dev/pytest/actions?query=workflow%3Amain
.. image:: https://results.pre-commit.ci/badge/github/pytest-dev/pytest/main.svg
:target: https://results.pre-commit.ci/latest/github/pytest-dev/pytest/main

View File

@@ -6,8 +6,6 @@ Release announcements
:maxdepth: 2
release-7.1.2
release-7.1.1
release-7.1.0
release-7.0.1
release-7.0.0

View File

@@ -1,18 +0,0 @@
pytest-7.1.1
=======================================
pytest 7.1.1 has just been released to PyPI.
This is a bug-fix release, being a drop-in replacement. To upgrade::
pip install --upgrade pytest
The full changelog is available at https://docs.pytest.org/en/stable/changelog.html.
Thanks to all of the contributors to this release:
* Ran Benita
Happy testing,
The pytest Development Team

View File

@@ -1,23 +0,0 @@
pytest-7.1.2
=======================================
pytest 7.1.2 has just been released to PyPI.
This is a bug-fix release, being a drop-in replacement. To upgrade::
pip install --upgrade pytest
The full changelog is available at https://docs.pytest.org/en/stable/changelog.html.
Thanks to all of the contributors to this release:
* Anthony Sottile
* Bruno Oliveira
* Hugo van Kemenade
* Kian Eliasi
* Ran Benita
* Zac Hatfield-Dodds
Happy testing,
The pytest Development Team

View File

@@ -170,10 +170,10 @@ For information about fixtures, see :ref:`fixtures`. To see a complete list of a
See https://docs.python.org/library/how-to/capture-warnings.html for information
on warning categories.
tmp_path_factory [session scope] -- .../_pytest/tmpdir.py:184
tmp_path_factory [session scope] -- .../_pytest/tmpdir.py:183
Return a :class:`pytest.TempPathFactory` instance for the test session.
tmp_path -- .../_pytest/tmpdir.py:199
tmp_path -- .../_pytest/tmpdir.py:198
Return a temporary directory path object which is unique to each test
function invocation, created as a sub directory of the base temporary
directory.

View File

@@ -28,35 +28,6 @@ with advance notice in the **Deprecations** section of releases.
.. towncrier release notes start
pytest 7.1.2 (2022-04-23)
=========================
Bug Fixes
---------
- `#9726 <https://github.com/pytest-dev/pytest/issues/9726>`_: An unnecessary ``numpy`` import inside :func:`pytest.approx` was removed.
- `#9820 <https://github.com/pytest-dev/pytest/issues/9820>`_: Fix comparison of ``dataclasses`` with ``InitVar``.
- `#9869 <https://github.com/pytest-dev/pytest/issues/9869>`_: Increase ``stacklevel`` for the ``NODE_CTOR_FSPATH_ARG`` deprecation to point to the
user's code, not pytest.
- `#9871 <https://github.com/pytest-dev/pytest/issues/9871>`_: Fix a bizarre (and fortunately rare) bug where the `temp_path` fixture could raise
an internal error while attempting to get the current user's username.
pytest 7.1.1 (2022-03-17)
=========================
Bug Fixes
---------
- `#9767 <https://github.com/pytest-dev/pytest/issues/9767>`_: Fixed a regression in pytest 7.1.0 where some conftest.py files outside of the source tree (e.g. in the `site-packages` directory) were not picked up.
pytest 7.1.0 (2022-03-13)
=========================

View File

@@ -22,7 +22,7 @@ Install ``pytest``
.. code-block:: bash
$ pytest --version
pytest 7.1.2
pytest 7.1.0
.. _`simpletest`:

View File

@@ -198,8 +198,6 @@ option names are:
If you need to record the whole test suite logging calls to a file, you can pass
``--log-file=/path/to/log/file``. This log file is opened in write mode which
means that it will be overwritten at each run tests session.
Note that relative paths for the log-file location, whether passed on the CLI or declared in a
config file, are always resolved relative to the current working directory.
You can also specify the logging level for the log file by passing
``--log-file-level``. This setting accepts the logging level names as seen in

View File

@@ -1514,7 +1514,7 @@ passed multiple times. The expected format is ``name=value``. For example::
Sets a file name relative to the current working directory where log messages should be written to, in addition
Sets a file name relative to the ``pytest.ini`` file where log messages should be written to, in addition
to the other logging facilities that are active.
.. code-block:: ini

View File

@@ -5,6 +5,3 @@ sphinx-removed-in>=0.2.0
sphinx>=3.1,<4
sphinxcontrib-trio
sphinxcontrib-svg2pdfconverter
# XXX: sphinx<4 is broken with latest jinja2
jinja2<3.1

View File

@@ -1,5 +1,4 @@
import sys
from distutils.core import setup
if __name__ == "__main__":

View File

@@ -437,10 +437,8 @@ def _compare_eq_cls(left: Any, right: Any, verbose: int) -> List[str]:
if not has_default_eq(left):
return []
if isdatacls(left):
import dataclasses
all_fields = dataclasses.fields(left)
fields_to_check = [info.name for info in all_fields if info.compare]
all_fields = left.__dataclass_fields__
fields_to_check = [field for field, info in all_fields.items() if info.compare]
elif isattrs(left):
all_fields = left.__attrs_attrs__
fields_to_check = [field.name for field in all_fields if getattr(field, "eq")]

View File

@@ -538,7 +538,11 @@ class PytestPluginManager(PluginManager):
"""
if self._confcutdir is None:
return True
return path not in self._confcutdir.parents
try:
path.relative_to(self._confcutdir)
except ValueError:
return False
return True
def _try_load_conftest(
self, anchor: Path, importmode: Union[str, ImportMode], rootpath: Path

View File

@@ -111,7 +111,7 @@ def _imply_path(
NODE_CTOR_FSPATH_ARG.format(
node_type_name=node_type.__name__,
),
stacklevel=6,
stacklevel=3,
)
if path is not None:
if fspath is not None:

View File

@@ -319,6 +319,7 @@ class ApproxSequenceLike(ApproxBase):
def _repr_compare(self, other_side: Sequence[float]) -> List[str]:
import math
import numpy as np
if len(self.expected) != len(other_side):
return [
@@ -339,7 +340,7 @@ class ApproxSequenceLike(ApproxBase):
abs_diff = abs(approx_value.expected - other_value)
max_abs_diff = max(max_abs_diff, abs_diff)
if other_value == 0.0:
max_rel_diff = math.inf
max_rel_diff = np.inf
else:
max_rel_diff = max(max_rel_diff, abs_diff / abs(other_value))
different_ids.append(i)
@@ -572,7 +573,7 @@ def approx(expected, rel=None, abs=None, nan_ok: bool = False) -> ApproxBase:
>>> {'a': 0.1 + 0.2, 'b': 0.2 + 0.4} == approx({'a': 0.3, 'b': 0.6})
True
The comparison will be true if both mappings have the same keys and their
The comparision will be true if both mappings have the same keys and their
respective values match the expected tolerances.
**Tolerances**

View File

@@ -158,10 +158,9 @@ class TempPathFactory:
def get_user() -> Optional[str]:
"""Return the current user name, or None if getuser() does not work
in the current environment (see #1010)."""
try:
# In some exotic environments, getpass may not be importable.
import getpass
import getpass
try:
return getpass.getuser()
except (ImportError, KeyError):
return None

View File

@@ -1,12 +0,0 @@
from dataclasses import dataclass
from dataclasses import InitVar
@dataclass
class Foo:
init_only: InitVar[int]
real_attr: int
def test_demonstrate():
assert Foo(1, 2) == Foo(1, 3)

View File

@@ -92,7 +92,9 @@ SOME_INT = r"[0-9]+\s*"
class TestApprox:
def test_error_messages_native_dtypes(self, assert_approx_raises_regex):
def test_error_messages(self, assert_approx_raises_regex):
np = pytest.importorskip("numpy")
assert_approx_raises_regex(
2.0,
1.0,
@@ -133,22 +135,6 @@ class TestApprox:
],
)
# Specific test for comparison with 0.0 (relative diff will be 'inf')
assert_approx_raises_regex(
[0.0],
[1.0],
[
r" comparison failed. Mismatched elements: 1 / 1:",
rf" Max absolute difference: {SOME_FLOAT}",
r" Max relative difference: inf",
r" Index \| Obtained\s+\| Expected ",
rf"\s*0\s*\| {SOME_FLOAT} \| {SOME_FLOAT} ± {SOME_FLOAT}",
],
)
def test_error_messages_numpy_dtypes(self, assert_approx_raises_regex):
np = pytest.importorskip("numpy")
a = np.linspace(0, 100, 20)
b = np.linspace(0, 100, 20)
a[10] += 0.5
@@ -189,6 +175,18 @@ class TestApprox:
)
# Specific test for comparison with 0.0 (relative diff will be 'inf')
assert_approx_raises_regex(
[0.0],
[1.0],
[
r" comparison failed. Mismatched elements: 1 / 1:",
rf" Max absolute difference: {SOME_FLOAT}",
r" Max relative difference: inf",
r" Index \| Obtained\s+\| Expected ",
rf"\s*0\s*\| {SOME_FLOAT} \| {SOME_FLOAT} ± {SOME_FLOAT}",
],
)
assert_approx_raises_regex(
np.array([0.0]),
np.array([1.0]),

View File

@@ -882,13 +882,6 @@ class TestAssert_reprcompare_dataclass:
result.assert_outcomes(failed=1, passed=0)
result.stdout.no_re_match_line(".*Differing attributes.*")
def test_data_classes_with_initvar(self, pytester: Pytester) -> None:
p = pytester.copy_example("dataclasses/test_compare_initvar.py")
# issue 9820
result = pytester.runpytest(p, "-vv")
result.assert_outcomes(failed=1, passed=0)
result.stdout.no_re_match_line(".*AttributeError.*")
class TestAssert_reprcompare_attrsclass:
def test_attrs(self) -> None:

View File

@@ -204,8 +204,16 @@ class TestAssertionRewrite:
def f4() -> None:
assert sys == 42 # type: ignore[comparison-overlap]
verbose = request.config.getoption("verbose")
msg = getmsg(f4, {"sys": sys})
assert msg == "assert sys == 42"
if verbose > 0:
assert msg == (
"assert <module 'sys' (built-in)> == 42\n"
" +<module 'sys' (built-in)>\n"
" -42"
)
else:
assert msg == "assert sys == 42"
def f5() -> None:
assert cls == 42 # type: ignore[name-defined] # noqa: F821
@@ -216,7 +224,20 @@ class TestAssertionRewrite:
msg = getmsg(f5, {"cls": X})
assert msg is not None
lines = msg.splitlines()
assert lines == ["assert cls == 42"]
if verbose > 1:
assert lines == [
f"assert {X!r} == 42",
f" +{X!r}",
" -42",
]
elif verbose > 0:
assert lines == [
"assert <class 'test_...e.<locals>.X'> == 42",
f" +{X!r}",
" -42",
]
else:
assert lines == ["assert cls == 42"]
def test_assertrepr_compare_same_width(self, request) -> None:
"""Should use same width/truncation with same initial width."""
@@ -258,11 +279,14 @@ class TestAssertionRewrite:
msg = getmsg(f, {"cls": Y})
assert msg is not None
lines = msg.splitlines()
assert lines == [
"assert 3 == 2",
" + where 3 = Y.foo",
" + where Y = cls()",
]
if request.config.getoption("verbose") > 0:
assert lines == ["assert 3 == 2", " +3", " -2"]
else:
assert lines == [
"assert 3 == 2",
" + where 3 = Y.foo",
" + where Y = cls()",
]
def test_assert_already_has_message(self) -> None:
def f():
@@ -639,7 +663,10 @@ class TestAssertionRewrite:
assert len(values) == 11
msg = getmsg(f)
assert msg == "assert 10 == 11\n + where 10 = len([0, 1, 2, 3, 4, 5, ...])"
if request.config.getoption("verbose") > 0:
assert msg == "assert 10 == 11\n +10\n -11"
else:
assert msg == "assert 10 == 11\n + where 10 = len([0, 1, 2, 3, 4, 5, ...])"
def test_custom_reprcompare(self, monkeypatch) -> None:
def my_reprcompare1(op, left, right) -> str:
@@ -705,7 +732,10 @@ class TestAssertionRewrite:
msg = getmsg(f)
assert msg is not None
lines = util._format_lines([msg])
assert lines == ["assert 0 == 1\n + where 1 = \\n{ \\n~ \\n}.a"]
if request.config.getoption("verbose") > 0:
assert lines == ["assert 0 == 1\n +0\n -1"]
else:
assert lines == ["assert 0 == 1\n + where 1 = \\n{ \\n~ \\n}.a"]
def test_custom_repr_non_ascii(self) -> None:
def f() -> None:

View File

@@ -651,7 +651,7 @@ class Test_getinitialnodes:
for parent in col.listchain():
assert parent.config is config
def test_pkgfile(self, pytester: Pytester, monkeypatch: MonkeyPatch) -> None:
def test_pkgfile(self, pytester: Pytester) -> None:
"""Verify nesting when a module is within a package.
The parent chain should match: Module<x.py> -> Package<subdir> -> Session.
Session's parent should always be None.
@@ -660,8 +660,7 @@ class Test_getinitialnodes:
subdir = tmp_path.joinpath("subdir")
x = ensure_file(subdir / "x.py")
ensure_file(subdir / "__init__.py")
with monkeypatch.context() as mp:
mp.chdir(subdir)
with subdir.cwd():
config = pytester.parseconfigure(x)
col = pytester.getnode(config, x)
assert col is not None
@@ -1189,7 +1188,8 @@ def test_collect_with_chdir_during_import(pytester: Pytester) -> None:
"""
% (str(subdir),)
)
result = pytester.runpytest()
with pytester.path.cwd():
result = pytester.runpytest()
result.stdout.fnmatch_lines(["*1 passed in*"])
assert result.ret == 0
@@ -1200,7 +1200,8 @@ def test_collect_with_chdir_during_import(pytester: Pytester) -> None:
testpaths = .
"""
)
result = pytester.runpytest("--collect-only")
with pytester.path.cwd():
result = pytester.runpytest("--collect-only")
result.stdout.fnmatch_lines(["collected 1 item"])
@@ -1223,8 +1224,7 @@ def test_collect_pyargs_with_testpaths(
)
)
monkeypatch.setenv("PYTHONPATH", str(pytester.path), prepend=os.pathsep)
with monkeypatch.context() as mp:
mp.chdir(root)
with root.cwd():
result = pytester.runpytest_subprocess()
result.stdout.fnmatch_lines(["*1 passed in*"])

View File

@@ -252,34 +252,6 @@ def test_conftest_confcutdir(pytester: Pytester) -> None:
result.stdout.no_fnmatch_line("*warning: could not load initial*")
def test_installed_conftest_is_picked_up(pytester: Pytester, tmp_path: Path) -> None:
"""When using `--pyargs` to run tests in an installed packages (located e.g.
in a site-packages in the PYTHONPATH), conftest files in there are picked
up.
Regression test for #9767.
"""
# pytester dir - the source tree.
# tmp_path - the simulated site-packages dir (not in source tree).
pytester.syspathinsert(tmp_path)
pytester.makepyprojecttoml("[tool.pytest.ini_options]")
tmp_path.joinpath("foo").mkdir()
tmp_path.joinpath("foo", "__init__.py").touch()
tmp_path.joinpath("foo", "conftest.py").write_text(
textwrap.dedent(
"""\
import pytest
@pytest.fixture
def fix(): return None
"""
)
)
tmp_path.joinpath("foo", "test_it.py").write_text("def test_it(fix): pass")
result = pytester.runpytest("--pyargs", "foo")
assert result.ret == 0
def test_conftest_symlink(pytester: Pytester) -> None:
"""`conftest.py` discovery follows normal path resolution and does not resolve symlinks."""
# Structure: