-
-
Notifications
You must be signed in to change notification settings - Fork 2.8k
Description
the bug starts with the change made at 70f3ad1 .
When running on a Jenkins CI that creates a little bit of a broken directory structure, there's a setup.cfg file in both the working checkout where tests are run from , as well as another one that is one directory upwards. this fools the logic at https://github.com/pytest-dev/pytest/blob/master/src/_pytest/config/findpaths.py#L85 into determining the wrong path as the root path.
to compound the issue, when using pytest-xdist, the logic seems to behave inconsistently, leading some workers to see a different root path, which then causes collection to fail as the test ids are different.
the change in behavior can be illustrated using the following directory layout:
[classic@photon3 foo]$ find .
.
./myproject
./myproject/tests
./myproject/tests/test_foo.py
./myproject/tests/conftest.py
./myproject/setup.cfg
./setup.cfg
[classic@photon3 foo]$ cat myproject/tests/test_foo.py
def test_foo():
print("hi")
[classic@photon3 foo]$ cat myproject/tests/conftest.py
import inspect
def pytest_pycollect_makeitem(collector, name, obj):
if inspect.isfunction(obj):
print(collector.config.rootdir)
return None
[classic@photon3 foo]$ cat setup.cfg
[tool:pytest]
addopts= --tb native -v -r fxX -p no:warnings -p no:logging --maxfail=25
python_files=tests/test_*.py
[classic@photon3 foo]$ cat myproject/setup.cfg
[tool:pytest]
addopts= --tb native -v -r fxX -p no:warnings -p no:logging --maxfail=25
python_files=tests/test_*.py
to sum up - the same setup.cfg file in both foo/ and foo/myproject, then the tests in foo/myproject/tests.
now the working directory, where I will normally set --rootdir, which is obviously going to be my workaround here, is foo/myproject. Let's cd there:
[classic@photon3 foo]$ cd myproject/
then run the tests giving the directory (yes, perfect storm of inputs , otherwise locate_config still gets the right answer):
[classic@photon3 myproject]$ pytest -v -s tests/
=========================================================== test session starts ===========================================================
platform linux -- Python 3.8.3, pytest-6.1.0, py-1.9.0, pluggy-0.13.0 -- /home/classic/.venv3/bin/python
cachedir: .pytest_cache
rootdir: /home/classic/tmp/foo, configfile: setup.cfg
plugins: forked-1.1.3, xdist-2.1.0, cov-2.8.1
collecting ... /home/classic/tmp/foo
collected 1 item
tests/test_foo.py::test_foo hi
PASSED
============================================================ 1 passed in 0.03s ============================================================
[classic@photon3 myproject]$
I just noticed it actually gives us the rootdir anyway, I didn't even have to print it. OK so you see above it's /home/classic/tmp/foo. with pytest 6.0.2, it's one directory inwards which is what it's been for years:
[classic@photon3 myproject]$ pytest -v -s tests/
=========================================================== test session starts ===========================================================
platform linux -- Python 3.8.3, pytest-6.0.2, py-1.9.0, pluggy-0.13.0 -- /home/classic/.venv3/bin/python
cachedir: .pytest_cache
rootdir: /home/classic/tmp/foo/myproject, configfile: setup.cfg
plugins: forked-1.1.3, xdist-2.1.0, cov-2.8.1
collecting ... /home/classic/tmp/foo/myproject
collected 1 item
tests/test_foo.py::test_foo hi
PASSED
============================================================ 1 passed in 0.02s ===========================================================
So I can totally get that you're going to say, you have three things confusing it, just set rootdir. Clearly that's what I'm going to do. but this is a behavioral change and most critically it seems to be behaving randomly when I am using pytest-xdist, and in my logs for those runs, it's reporting the correct rootdir but then it does not work the same way in each worker node. An excerpt of this run is below showing the correct rootdir at the top and then inconsistent rootdirs in the workers:
============================= test session starts ==============================
platform linux -- Python 3.7.5, pytest-6.1.0, py-1.9.0, pluggy-0.13.1 -- /home/jenkins/workspace/alembic_gerrit/6a4aefb0/.tox/py37-pyoptimize-sqla13-sqlite-postgresql-mysql-oracle/bin/python
cachedir: .tox/py37-pyoptimize-sqla13-sqlite-postgresql-mysql-oracle/.pytest_cache
rootdir: /home/jenkins/workspace/alembic_gerrit/6a4aefb0, configfile: setup.cfg
plugins: forked-1.3.0, xdist-2.1.0
gw0 I / gw1 I / gw2 I / gw3 I
[gw0] linux Python 3.7.5 cwd: /home/jenkins/workspace/alembic_gerrit/6a4aefb0
[gw1] linux Python 3.7.5 cwd: /home/jenkins/workspace/alembic_gerrit/6a4aefb0
[gw2] linux Python 3.7.5 cwd: /home/jenkins/workspace/alembic_gerrit/6a4aefb0
[gw3] linux Python 3.7.5 cwd: /home/jenkins/workspace/alembic_gerrit/6a4aefb0
[gw0] Python 3.7.5 (default, May 25 2020, 17:49:41) -- [GCC 8.3.1 20190507 (Red Hat 8.3.1-4)]
[gw1] Python 3.7.5 (default, May 25 2020, 17:49:41) -- [GCC 8.3.1 20190507 (Red Hat 8.3.1-4)]
[gw2] Python 3.7.5 (default, May 25 2020, 17:49:41) -- [GCC 8.3.1 20190507 (Red Hat 8.3.1-4)]
[gw3] Python 3.7.5 (default, May 25 2020, 17:49:41) -- [GCC 8.3.1 20190507 (Red Hat 8.3.1-4)]
gw0 [49] / gw1 [49] / gw2 [49] / gw3 [49]
scheduling tests via LoadScheduling
==================================== ERRORS ====================================
_____________________________ ERROR collecting gw1 _____________________________
Different tests were collected between gw0 and gw1. The difference is:
--- gw0
+++ gw1
@@ -1,49 +1,49 @@
-6a4aefb0/tests/test_script_consumption.py::ApplyVersionsFunctionalTest::test_steps
-6a4aefb0/tests/test_script_consumption.py::CallbackEnvironmentTest::test_steps
-6a4aefb0/tests/test_script_consumption.py::EncodingTest::test_encode
# ... lots of gw0s
#... then the gw1s come in with *different* root dir:
+tests/test_script_consumption.py::ApplyVersionsFunctionalTest::test_steps
+tests/test_script_consumption.py::CallbackEnvironmentTest::test_steps
+tests/test_script_consumption.py::EncodingTest::test_encode
# ... etc
Workaround is simple, I just set:
BASECOMMAND=python -m pytest --rootdir {toxinidir}
in my tox.ini