Compare commits

...

18 Commits

Author SHA1 Message Date
Bruno Oliveira
6ec967a3f2 Prepare release 1.22.3 2018-07-23 16:36:39 -03:00
Bruno Oliveira
0722ea12ef Use a tox environment to update the release files 2018-07-23 16:36:26 -03:00
Ronny Pfannschmidt
bb91f5459d Merge pull request #309 from greut/cpu-count
plugin: get cpu_count from sched_getaffinity
2018-07-23 20:13:45 +02:00
Bruno Oliveira
00b7c4553a Merge pull request #311 from nicoddemus/skip-deploy
Skip deploy job on Travis if we are not on a tag
2018-07-21 19:20:25 -03:00
Bruno Oliveira
9ff6fc10d0 Skip deploy job on Travis if we are not on a tag 2018-07-21 18:17:21 -03:00
Bruno Oliveira
a06e75cc78 Fix flake8 issue 2018-07-21 12:09:44 -03:00
Yoan Blanc
04882074e1 plugin: get cpu_count from sched_getaffinity
Signed-off-by: Yoan Blanc <yoan.blanc@exoscale.ch>
2018-07-18 08:32:01 +02:00
Bruno Oliveira
06593498cd Merge pull request #306 from asottile/factor_out_py_std
Factor out py.std
2018-07-06 22:21:56 -03:00
Bruno Oliveira
57d09c2622 Merge pull request #308 from scop/dropthedot
Use pytest instead of py.test per upstream recommendation, #dropthedot
2018-07-06 22:20:53 -03:00
Ville Skyttä
663bbd5338 Use pytest instead of py.test per upstream recommendation, #dropthedot
http://blog.pytest.org/2016/whats-new-in-pytest-30/
https://twitter.com/hashtag/dropthedot
2018-07-07 00:01:11 +03:00
Bruno Oliveira
137b939a27 Merge pull request #307 from scop/grammar
Grammar fix
2018-07-06 12:05:26 -03:00
Ville Skyttä
17f6257a24 Grammar fix 2018-07-06 15:45:41 +03:00
Anthony Sottile
78fcf725cf Factor out py.std 2018-07-05 15:35:39 -07:00
Ronny Pfannschmidt
8d94fca964 Merge pull request #297 from nicoddemus/fix-init
Fix __init__ declaration
2018-06-11 06:01:17 +02:00
Bruno Oliveira
b06c52a5d2 Add .pytest_cache to gitignore 2018-06-03 16:10:55 -03:00
Bruno Oliveira
fd2e8a6711 Make all classes subclass from object 2018-06-03 16:10:24 -03:00
Bruno Oliveira
98ae25c12c Fix __init__ declaration 2018-06-03 16:06:52 -03:00
Bruno Oliveira
182d1f6433 Merge pull request #287 from nicoddemus/release-1.22.2
Preparing 1.22.2 release
2018-02-27 07:43:11 -03:00
24 changed files with 110 additions and 64 deletions

1
.gitignore vendored
View File

@@ -30,5 +30,6 @@ issue/
pytestdebug.log pytestdebug.log
.tox/ .tox/
.cache/ .cache/
.pytest_cache/
.eggs/ .eggs/
.idea/ .idea/

View File

@@ -25,6 +25,11 @@ env:
install: pip install tox setuptools_scm install: pip install tox setuptools_scm
script: tox script: tox
stages:
- test
- name: deploy
if: repo = pytest-dev/pytest-xdist AND tag IS present
jobs: jobs:
include: include:
- stage: test - stage: test

View File

@@ -1,3 +1,18 @@
pytest-xdist 1.22.3 (2018-07-23)
================================
Bug Fixes
---------
- Fix issue of virtualized or containerized environments not reporting the number of CPUs correctly. (`#9 <https://github.com/pytest-dev/pytest-xdist/issues/9>`_)
Trivial Changes
---------------
- Make all classes subclass from ``object`` and fix ``super()`` call in ``LoadFileScheduling``; (`#297 <https://github.com/pytest-dev/pytest-xdist/issues/297>`_)
pytest-xdist 1.22.2 (2018-02-26) pytest-xdist 1.22.2 (2018-02-26)
================================ ================================

View File

@@ -24,13 +24,13 @@ To publish a new release ``X.Y.Z``, the steps are as follows:
#. Create a new branch named ``release-X.Y.Z`` from the latest ``master``. #. Create a new branch named ``release-X.Y.Z`` from the latest ``master``.
#. Install ``pytest-xdist`` and dev requirements in a virtualenv:: #. Install ``tox`` in a virtualenv::
$ pip install -e . -U -r dev-requirements.txt $ pip install tox
#. Update ``CHANGELOG.rst`` file by running:: #. Update the necessary files with::
$ towncrier --version X.Y.Z --yes $ tox -e release -- X.Y.Z
#. Commit and push the branch for review. #. Commit and push the branch for review.

View File

@@ -19,7 +19,7 @@ tag: feature
allow to run xdist own tests using its own mechanism. allow to run xdist own tests using its own mechanism.
currently this doesn't work because the remote side currently this doesn't work because the remote side
has no py.test plugin. How to configure/do has no pytest plugin. How to configure/do
register "xdist.plugin" on the remote side? register "xdist.plugin" on the remote side?
see to avoid any "from _pytest" internal imports see to avoid any "from _pytest" internal imports

View File

@@ -23,7 +23,7 @@
xdist: pytest distributed testing plugin xdist: pytest distributed testing plugin
======================================== ========================================
The `pytest-xdist`_ plugin extends py.test with some unique The `pytest-xdist`_ plugin extends pytest with some unique
test execution modes: test execution modes:
* test run parallelization_: if you have multiple CPUs or hosts you can use * test run parallelization_: if you have multiple CPUs or hosts you can use
@@ -32,14 +32,14 @@ test execution modes:
* ``--looponfail``: run your tests repeatedly in a subprocess. After each run * ``--looponfail``: run your tests repeatedly in a subprocess. After each run
py.test waits until a file in your project changes and then re-runs pytest waits until a file in your project changes and then re-runs
the previously failing tests. This is repeated until all tests pass the previously failing tests. This is repeated until all tests pass
after which again a full run is performed. after which again a full run is performed.
* `Multi-Platform`_ coverage: you can specify different Python interpreters * `Multi-Platform`_ coverage: you can specify different Python interpreters
or different platforms and run tests in parallel on all of them. or different platforms and run tests in parallel on all of them.
Before running tests remotely, ``py.test`` efficiently "rsyncs" your Before running tests remotely, ``pytest`` efficiently "rsyncs" your
program source code to the remote place. All test results program source code to the remote place. All test results
are reported back and displayed to your local terminal. are reported back and displayed to your local terminal.
You may specify different Python versions and interpreters. You may specify different Python versions and interpreters.
@@ -67,7 +67,7 @@ Speed up test runs by sending tests to multiple CPUs
To send tests to multiple CPUs, type:: To send tests to multiple CPUs, type::
py.test -n NUM pytest -n NUM
Especially for longer running tests or tests requiring Especially for longer running tests or tests requiring
a lot of I/O this can lead to considerable speed ups. This option can a lot of I/O this can lead to considerable speed ups. This option can
@@ -98,7 +98,7 @@ Running tests in a Python subprocess
To instantiate a python3.5 subprocess and send tests to it, you may type:: To instantiate a python3.5 subprocess and send tests to it, you may type::
py.test -d --tx popen//python=python3.5 pytest -d --tx popen//python=python3.5
This will start a subprocess which is run with the ``python3.5`` This will start a subprocess which is run with the ``python3.5``
Python interpreter, found in your system binary lookup path. Python interpreter, found in your system binary lookup path.
@@ -129,10 +129,10 @@ tests that you can successfully run locally. And you
have a ssh-reachable machine ``myhost``. Then have a ssh-reachable machine ``myhost``. Then
you can ad-hoc distribute your tests by typing:: you can ad-hoc distribute your tests by typing::
py.test -d --tx ssh=myhostpopen --rsyncdir mypkg mypkg pytest -d --tx ssh=myhostpopen --rsyncdir mypkg mypkg
This will synchronize your :code:`mypkg` package directory This will synchronize your :code:`mypkg` package directory
to an remote ssh account and then locally collect tests to a remote ssh account and then locally collect tests
and send them to remote places for execution. and send them to remote places for execution.
You can specify multiple :code:`--rsyncdir` directories You can specify multiple :code:`--rsyncdir` directories
@@ -140,11 +140,11 @@ to be sent to the remote side.
.. note:: .. note::
For py.test to collect and send tests correctly For pytest to collect and send tests correctly
you not only need to make sure all code and tests you not only need to make sure all code and tests
directories are rsynced, but that any test (sub) directory directories are rsynced, but that any test (sub) directory
also has an :code:`__init__.py` file because internally also has an :code:`__init__.py` file because internally
py.test references tests as a fully qualified python pytest references tests as a fully qualified python
module path. **You will otherwise get strange errors** module path. **You will otherwise get strange errors**
during setup of the remote side. during setup of the remote side.
@@ -168,7 +168,7 @@ It will tell you that it starts listening on the default
port. You can now on your home machine specify this port. You can now on your home machine specify this
new socket host with something like this:: new socket host with something like this::
py.test -d --tx socket=192.168.1.102:8888 --rsyncdir mypkg mypkg pytest -d --tx socket=192.168.1.102:8888 --rsyncdir mypkg mypkg
.. _`atonce`: .. _`atonce`:
@@ -180,7 +180,7 @@ Running tests on many platforms at once
The basic command to run tests on multiple platforms is:: The basic command to run tests on multiple platforms is::
py.test --dist=each --tx=spec1 --tx=spec2 pytest --dist=each --tx=spec1 --tx=spec2
If you specify a windows host, an OSX host and a Linux If you specify a windows host, an OSX host and a Linux
environment this command will send each tests to all environment this command will send each tests to all
@@ -242,7 +242,7 @@ You can also add default environments like this:
and then just type:: and then just type::
py.test --dist=each pytest --dist=each
to run tests in each of the environments. to run tests in each of the environments.

View File

@@ -1 +0,0 @@
towncrier

View File

@@ -25,7 +25,7 @@ to run each test in a controlled subprocess. Here is a basic example::
If you run this with:: If you run this with::
$ py.test -n1 $ pytest -n1
=========================== test session starts ============================ =========================== test session starts ============================
platform linux2 -- Python 2.7.3 -- pytest-2.3.0.dev8 platform linux2 -- Python 2.7.3 -- pytest-2.3.0.dev8
plugins: xdist, bugzilla, cache, oejskit, cli, pep8, cov plugins: xdist, bugzilla, cache, oejskit, cli, pep8, cov
@@ -46,7 +46,7 @@ You'll see that a couple of tests are reported as crashing, indicated
by lower-case ``f`` and the respective failure summary. You can also use by lower-case ``f`` and the respective failure summary. You can also use
the xdist-provided parallelization feature to speed up your testing:: the xdist-provided parallelization feature to speed up your testing::
$ py.test -n3 $ pytest -n3
=========================== test session starts ============================ =========================== test session starts ============================
platform linux2 -- Python 2.7.3 -- pytest-2.3.0.dev8 platform linux2 -- Python 2.7.3 -- pytest-2.3.0.dev8
plugins: xdist, bugzilla, cache, oejskit, cli, pep8, cov plugins: xdist, bugzilla, cache, oejskit, cli, pep8, cov

View File

@@ -8,7 +8,7 @@ passenv = http_proxy https_proxy
deps = -rrequirements.txt deps = -rrequirements.txt
changedir = {envtmpdir} changedir = {envtmpdir}
commands = commands =
py.test -s -v \ pytest -s -v \
--doctest-modules \ --doctest-modules \
--junitxml=tests.xml \ --junitxml=tests.xml \
--dist=loadscope \ --dist=loadscope \

View File

@@ -6,7 +6,7 @@ install_requires = ['execnet>=1.1', 'pytest>=3.0.0', 'pytest-forked']
setup( setup(
name="pytest-xdist", name="pytest-xdist",
use_scm_version={'write_to': 'xdist/_version.py'}, use_scm_version={'write_to': 'xdist/_version.py'},
description='py.test xdist plugin for distributed testing' description='pytest xdist plugin for distributed testing'
' and loop-on-failing modes', ' and loop-on-failing modes',
long_description=open('README.rst').read(), long_description=open('README.rst').read(),
license='MIT', license='MIT',

View File

@@ -1,4 +1,6 @@
import os
import re import re
import textwrap
import py import py
import pytest import pytest
@@ -54,8 +56,8 @@ class TestDistribution:
def test_n1_skip(self, testdir): def test_n1_skip(self, testdir):
p1 = testdir.makepyfile(""" p1 = testdir.makepyfile("""
def test_skip(): def test_skip():
import py import pytest
py.test.skip("myreason") pytest.skip("myreason")
""") """)
result = testdir.runpytest(p1, "-n1") result = testdir.runpytest(p1, "-n1")
assert result.ret == 0 assert result.ret == 0
@@ -78,7 +80,7 @@ class TestDistribution:
def test_manytests_to_one_popen(self, testdir): def test_manytests_to_one_popen(self, testdir):
p1 = testdir.makepyfile( p1 = testdir.makepyfile(
""" """
import py import pytest
def test_fail0(): def test_fail0():
assert 0 assert 0
def test_fail1(): def test_fail1():
@@ -86,7 +88,7 @@ class TestDistribution:
def test_ok(): def test_ok():
pass pass
def test_skip(): def test_skip():
py.test.skip("hello") pytest.skip("hello")
""", ) """, )
result = testdir.runpytest(p1, "-v", '-d', '--tx=popen', '--tx=popen') result = testdir.runpytest(p1, "-v", '-d', '--tx=popen', '--tx=popen')
result.stdout.fnmatch_lines([ result.stdout.fnmatch_lines([
@@ -124,7 +126,7 @@ class TestDistribution:
def test_dist_ini_specified(self, testdir): def test_dist_ini_specified(self, testdir):
p1 = testdir.makepyfile( p1 = testdir.makepyfile(
""" """
import py import pytest
def test_fail0(): def test_fail0():
assert 0 assert 0
def test_fail1(): def test_fail1():
@@ -132,7 +134,7 @@ class TestDistribution:
def test_ok(): def test_ok():
pass pass
def test_skip(): def test_skip():
py.test.skip("hello") pytest.skip("hello")
""", ) """, )
testdir.makeini(""" testdir.makeini("""
[pytest] [pytest]
@@ -145,13 +147,13 @@ class TestDistribution:
]) ])
assert result.ret == 1 assert result.ret == 1
@py.test.mark.xfail("sys.platform.startswith('java')", run=False) @pytest.mark.xfail("sys.platform.startswith('java')", run=False)
def test_dist_tests_with_crash(self, testdir): def test_dist_tests_with_crash(self, testdir):
if not hasattr(py.std.os, 'kill'): if not hasattr(os, 'kill'):
py.test.skip("no os.kill") pytest.skip("no os.kill")
p1 = testdir.makepyfile(""" p1 = testdir.makepyfile("""
import py import pytest
def test_fail0(): def test_fail0():
assert 0 assert 0
def test_fail1(): def test_fail1():
@@ -159,7 +161,7 @@ class TestDistribution:
def test_ok(): def test_ok():
pass pass
def test_skip(): def test_skip():
py.test.skip("hello") pytest.skip("hello")
def test_crash(): def test_crash():
import time import time
import os import os
@@ -299,7 +301,7 @@ class TestDistEach:
assert not result.ret assert not result.ret
result.stdout.fnmatch_lines(["*2 pass*"]) result.stdout.fnmatch_lines(["*2 pass*"])
@py.test.mark.xfail( @pytest.mark.xfail(
run=False, run=False,
reason="other python versions might not have py.test installed") reason="other python versions might not have py.test installed")
def test_simple_diffoutput(self, testdir): def test_simple_diffoutput(self, testdir):
@@ -307,7 +309,7 @@ class TestDistEach:
for name in ("python2.5", "python2.6"): for name in ("python2.5", "python2.6"):
interp = py.path.local.sysfind(name) interp = py.path.local.sysfind(name)
if interp is None: if interp is None:
py.test.skip("%s not found" % name) pytest.skip("%s not found" % name)
interpreters.append(interp) interpreters.append(interp)
testdir.makepyfile( testdir.makepyfile(
@@ -330,11 +332,11 @@ class TestDistEach:
class TestTerminalReporting: class TestTerminalReporting:
def test_pass_skip_fail(self, testdir): def test_pass_skip_fail(self, testdir):
testdir.makepyfile(""" testdir.makepyfile("""
import py import pytest
def test_ok(): def test_ok():
pass pass
def test_skip(): def test_skip():
py.test.skip("xx") pytest.skip("xx")
def test_func(): def test_func():
assert 0 assert 0
""") """)
@@ -421,7 +423,7 @@ def test_teardownfails_one_function(testdir):
["*def teardown_function(function):*", "*1 passed*1 error*"]) ["*def teardown_function(function):*", "*1 passed*1 error*"])
@py.test.mark.xfail @pytest.mark.xfail
def test_terminate_on_hangingnode(testdir): def test_terminate_on_hangingnode(testdir):
p = testdir.makeconftest(""" p = testdir.makeconftest("""
def pytest_sessionfinish(session): def pytest_sessionfinish(session):
@@ -585,7 +587,7 @@ def test_skipping(testdir):
def test_issue34_pluginloading_in_subprocess(testdir): def test_issue34_pluginloading_in_subprocess(testdir):
testdir.tmpdir.join("plugin123.py").write( testdir.tmpdir.join("plugin123.py").write(
py.code.Source(""" textwrap.dedent("""
def pytest_namespace(): def pytest_namespace():
return {'sample_variable': 'testing'} return {'sample_variable': 'testing'}
""")) """))

View File

@@ -31,7 +31,9 @@ def test_dist_options(testdir):
def test_auto_detect_cpus(testdir, monkeypatch): def test_auto_detect_cpus(testdir, monkeypatch):
import os import os
if hasattr(os, 'cpu_count'): if hasattr(os, 'sched_getaffinity'):
monkeypatch.setattr(os, 'sched_getaffinity', lambda _pid: set(range(99)))
elif hasattr(os, 'cpu_count'):
monkeypatch.setattr(os, 'cpu_count', lambda: 99) monkeypatch.setattr(os, 'cpu_count', lambda: 99)
else: else:
import multiprocessing import multiprocessing

View File

@@ -1,4 +1,5 @@
import py import py
import pprint
import pytest import pytest
from xdist.workermanage import WorkerController, unserialize_report from xdist.workermanage import WorkerController, unserialize_report
from xdist.remote import serialize_report from xdist.remote import serialize_report
@@ -14,7 +15,7 @@ def check_marshallable(d):
try: try:
marshal.dumps(d) marshal.dumps(d)
except ValueError: except ValueError:
py.std.pprint.pprint(d) pprint.pprint(d)
raise ValueError("not marshallable") raise ValueError("not marshallable")
@@ -344,7 +345,7 @@ class TestWorkerInteractor:
for data in worker.slp.channel: for data in worker.slp.channel:
worker.slp.process_from_remote(data) worker.slp.process_from_remote(data)
worker.slp.process_from_remote(worker.slp.ENDMARK) worker.slp.process_from_remote(worker.slp.ENDMARK)
py.std.pprint.pprint(hookrec.hookrecorder.calls) pprint.pprint(hookrec.hookrecorder.calls)
hookrec.hookrecorder.contains([ hookrec.hookrecorder.contains([
("pytest_collectstart", "collector.fspath == aaa"), ("pytest_collectstart", "collector.fspath == aaa"),
("pytest_pycollect_makeitem", "name == 'test_func'"), ("pytest_pycollect_makeitem", "name == 'test_func'"),

View File

@@ -1,5 +1,6 @@
import py import py
import pytest import pytest
import textwrap
import execnet import execnet
from _pytest.pytester import HookRecorder from _pytest.pytester import HookRecorder
from xdist import workermanage, newhooks from xdist import workermanage, newhooks
@@ -198,7 +199,7 @@ class TestNodeManager:
source.ensure("dir1", "somefile", dir=1) source.ensure("dir1", "somefile", dir=1)
dir2.ensure("hello") dir2.ensure("hello")
source.ensure("bogusdir", "file") source.ensure("bogusdir", "file")
source.join("tox.ini").write(py.std.textwrap.dedent(""" source.join("tox.ini").write(textwrap.dedent("""
[pytest] [pytest]
rsyncdirs=dir1/dir2 rsyncdirs=dir1/dir2
""")) """))
@@ -217,7 +218,7 @@ class TestNodeManager:
dir2.ensure("hello") dir2.ensure("hello")
source.ensure("foo", "bar") source.ensure("foo", "bar")
source.ensure("bar", "foo") source.ensure("bar", "foo")
source.join("tox.ini").write(py.std.textwrap.dedent(""" source.join("tox.ini").write(textwrap.dedent("""
[pytest] [pytest]
rsyncdirs = dir1 dir5 rsyncdirs = dir1 dir5
rsyncignore = dir1/dir2 dir5/dir6 foo* rsyncignore = dir1/dir2 dir5/dir6 foo*

15
tox.ini
View File

@@ -27,7 +27,7 @@ platform=
commands= commands=
# always clean to avoid code unmarshal mismatch on old python/pytest # always clean to avoid code unmarshal mismatch on old python/pytest
py.cleanup -aq py.cleanup -aq
py.test {posargs} pytest {posargs}
[testenv:flakes] [testenv:flakes]
changedir= changedir=
@@ -40,7 +40,18 @@ deps = readme
skip_install = true skip_install = true
commands = python setup.py check -r -s commands = python setup.py check -r -s
[testenv:release]
changedir=
decription = do a release, required posarg of the version number
basepython = python3.6
skipsdist = True
usedevelop = True
passenv = *
deps =
towncrier
commands =
towncrier --version {posargs} --yes
[pytest] [pytest]
addopts = -rsfxX addopts = -rsfxX
;; hello

View File

@@ -17,8 +17,8 @@ class Interrupted(KeyboardInterrupt):
""" signals an immediate interruption. """ """ signals an immediate interruption. """
class DSession: class DSession(object):
"""A py.test plugin which runs a distributed test session """A pytest plugin which runs a distributed test session
At the beginning of the test session this creates a NodeManager At the beginning of the test session this creates a NodeManager
instance which creates and starts all nodes. Nodes then emit instance which creates and starts all nodes. Nodes then emit
@@ -26,7 +26,7 @@ class DSession:
methods. methods.
Once a node is started it will automatically start running the Once a node is started it will automatically start running the
py.test mainloop with some custom hooks. This means a node pytest mainloop with some custom hooks. This means a node
automatically starts collecting tests. Once tests are collected automatically starts collecting tests. Once tests are collected
it will wait for instructions. it will wait for instructions.
""" """
@@ -316,7 +316,7 @@ class DSession:
self.config.hook.pytest_runtest_logreport(report=rep) self.config.hook.pytest_runtest_logreport(report=rep)
class TerminalDistReporter: class TerminalDistReporter(object):
def __init__(self, config): def __init__(self, config):
self.config = config self.config = config
self.tr = config.pluginmanager.getplugin("terminalreporter") self.tr = config.pluginmanager.getplugin("terminalreporter")

View File

@@ -1,5 +1,5 @@
""" """
Implement -f aka looponfailing for py.test. Implement -f aka looponfailing for pytest.
NOTE that we try to avoid loading and depending on application modules NOTE that we try to avoid loading and depending on application modules
within the controlling process (the one that starts repeatedly test within the controlling process (the one that starts repeatedly test
@@ -10,6 +10,7 @@
import py import py
import pytest import pytest
import sys import sys
import time
import execnet import execnet
@@ -157,7 +158,7 @@ def init_worker_session(channel, args, option_dict):
WorkerFailSession(config, channel).main() WorkerFailSession(config, channel).main()
class WorkerFailSession: class WorkerFailSession(object):
def __init__(self, config, channel): def __init__(self, config, channel):
self.config = config self.config = config
self.channel = channel self.channel = channel
@@ -211,7 +212,7 @@ class WorkerFailSession:
self.channel.send((trails, failreports, self.collection_failed)) self.channel.send((trails, failreports, self.collection_failed))
class StatRecorder: class StatRecorder(object):
def __init__(self, rootdirlist): def __init__(self, rootdirlist):
self.rootdirlist = rootdirlist self.rootdirlist = rootdirlist
self.statcache = {} self.statcache = {}
@@ -228,7 +229,7 @@ class StatRecorder:
changed = self.check() changed = self.check()
if changed: if changed:
return return
py.std.time.sleep(checkinterval) time.sleep(checkinterval)
def check(self, removepycfiles=True): # noqa, too complex def check(self, removepycfiles=True): # noqa, too complex
changed = False changed = False

View File

@@ -4,10 +4,17 @@ import pytest
def parse_numprocesses(s): def parse_numprocesses(s):
if s == 'auto': if s == 'auto':
try:
from os import sched_getaffinity
except ImportError:
try: try:
from os import cpu_count from os import cpu_count
except ImportError: except ImportError:
from multiprocessing import cpu_count from multiprocessing import cpu_count
else:
def cpu_count():
return len(sched_getaffinity(0))
try: try:
n = cpu_count() n = cpu_count()
except NotImplementedError: except NotImplementedError:

View File

@@ -14,7 +14,7 @@ import _pytest.hookspec
import pytest import pytest
class WorkerInteractor: class WorkerInteractor(object):
def __init__(self, config, channel): def __init__(self, config, channel):
self.config = config self.config = config
self.workerid = config.workerinput.get('workerid', "?") self.workerid = config.workerinput.get('workerid', "?")

View File

@@ -4,7 +4,7 @@ from xdist.workermanage import parse_spec_config
from xdist.report import report_collection_diff from xdist.report import report_collection_diff
class EachScheduling: class EachScheduling(object):
"""Implement scheduling of test items on all nodes """Implement scheduling of test items on all nodes
If a node gets added after the test run is started then it is If a node gets added after the test run is started then it is

View File

@@ -20,7 +20,7 @@ class LoadFileScheduling(LoadScopeScheduling):
This class behaves very much like LoadScopeScheduling, but with a file-level scope. This class behaves very much like LoadScopeScheduling, but with a file-level scope.
""" """
def __init(self, config, log=None): def __init__(self, config, log=None):
super(LoadFileScheduling, self).__init__(config, log) super(LoadFileScheduling, self).__init__(config, log)
if log is None: if log is None:
self.log = Producer('loadfilesched') self.log = Producer('loadfilesched')

View File

@@ -7,7 +7,7 @@ from xdist.workermanage import parse_spec_config
from xdist.report import report_collection_diff from xdist.report import report_collection_diff
class LoadScheduling: class LoadScheduling(object):
"""Implement load scheduling across nodes. """Implement load scheduling across nodes.
This distributes the tests collected across all nodes so each test This distributes the tests collected across all nodes so each test

View File

@@ -6,7 +6,7 @@ from xdist.report import report_collection_diff
from xdist.workermanage import parse_spec_config from xdist.workermanage import parse_spec_config
class LoadScopeScheduling: class LoadScopeScheduling(object):
"""Implement load scheduling across nodes, but grouping test by scope. """Implement load scheduling across nodes, but grouping test by scope.
This distributes the tests collected across all nodes so each test is run This distributes the tests collected across all nodes so each test is run

View File

@@ -1,6 +1,7 @@
import fnmatch import fnmatch
import os import os
import re import re
import threading
import py import py
import pytest import pytest
@@ -32,7 +33,7 @@ class NodeManager(object):
def __init__(self, config, specs=None, defaultchdir="pyexecnetcache"): def __init__(self, config, specs=None, defaultchdir="pyexecnetcache"):
self.config = config self.config = config
self._nodesready = py.std.threading.Event() self._nodesready = threading.Event()
self.trace = self.config.trace.get("nodemanager") self.trace = self.config.trace.get("nodemanager")
self.group = execnet.Group() self.group = execnet.Group()
if specs is None: if specs is None:
@@ -184,7 +185,7 @@ class HostRSync(execnet.RSync):
def make_reltoroot(roots, args): def make_reltoroot(roots, args):
# XXX introduce/use public API for splitting py.test args # XXX introduce/use public API for splitting pytest args
splitcode = "::" splitcode = "::"
result = [] result = []
for arg in args: for arg in args: