Skip to main content

pytest-xdist-memory

Size pytest-xdist by available RAM, not by CPU count.

On a developer laptop the bottleneck of a parallel test run is usually memory. pytest -n auto starts one worker per core; with heavy workers (Django and a database, a browser per worker for Playwright, a live server...) a 14-core, 14 GB laptop goes into swap thrashing and freezes. This plugin measures how much a worker of your test suite needs on this machine and answers -n auto with as many workers as fit into the memory available right now.

Status: alpha.

What it does

With --xdist-memory (or xdist_memory = true in the ini file):

  • Measures the peak memory of every worker together with all its child processes: browsers, live servers, subprocesses. Linux uses PSS (a fair share of pages shared between processes, so the several processes of one Chromium are not counted several times over); other systems use RSS.
  • Measures containers too, if you ask it to: a test database started by testcontainers is not a child of pytest. Containers can be matched by name (--xdist-memory-docker SUBSTR) or, more precisely, by the host port they publish (--xdist-memory-docker-port-env VAR, where VAR is the environment variable your fixtures export with the port). Matching by port is exact even when parallel runs from other checkouts have containers with similar names. The peak is divided by the number of workers.
  • Records the peaks in a per-machine profile, .pytest-xdist-memory.json. Each -m marker expression is a separate "suite": -m playwright workers are much heavier than -m "not playwright" ones. The last 5 runs are kept, and the estimate uses the maximum. Runs with fewer than 20 tests, or interrupted runs, are not recorded.
  • Answers -n auto / -n logical: workers = (available - reserve - controller) / (worker_peak × safety + extra), capped by the CPU count. With --xdist-memory-performance-cores, Apple Silicon is capped at the number of performance cores.
  • Optional watchdog (--xdist-memory-watchdog): kills the run when the whole process tree, plus the measured containers, exceeds the memory available at start minus the reserve.

Nothing changes until you enable it. PYTEST_XDIST_AUTO_NUM_WORKERS still wins over the estimate.

Usage

pip install pytest-xdist-memory

# First run: no profile yet, so it assumes 1024 MB per worker; the run is measured.
pytest -n auto --xdist-memory

# Later runs use what was measured (per -m expression):
pytest -n auto --xdist-memory -m "not playwright"
pytest -n auto --xdist-memory -m playwright --xdist-memory-performance-cores

The terminal summary shows the measured peaks and the calculation:

================================ xdist-memory =================================
-n auto [default]: 3 workers: available 7282 MB - reserve 2048 - controller 215 = 5019 MB; per worker 1357 MB (910 x safety + extra 220); cpu cap 14; from profile (4 runs)
peak per worker 905 MB (all: [905, 871, 860]), controller 210 MB, containers 214 MB/worker
recorded in .pytest-xdist-memory.json [default]

Add .pytest-xdist-memory.json to .gitignore: the profile describes one machine.

Options

Option ini Default
--xdist-memory xdist_memory off enable
--xdist-memory-profile PATH xdist_memory_profile .pytest-xdist-memory.json relative to rootdir
--xdist-memory-reserve MB xdist_memory_reserve 2048 left for the desktop/system
--xdist-memory-safety F xdist_memory_safety 1.25 multiplier on the worker peak
--xdist-memory-default-worker MB xdist_memory_default_worker 1024 used until a run is recorded
--xdist-memory-extra MB xdist_memory_extra 0 fixed extra per worker (e.g. its DB)
--xdist-memory-docker SUBSTR xdist_memory_docker measure containers by name
--xdist-memory-docker-port-env VAR xdist_memory_docker_port_env measure the container publishing port $VAR
--xdist-memory-performance-cores xdist_memory_performance_cores off Apple Silicon: P-cores only
--xdist-memory-min-tests N xdist_memory_min_tests 20 smaller runs are not recorded
--xdist-memory-watchdog xdist_memory_watchdog off kill the run over budget
--xdist-memory-interval S xdist_memory_interval 2 sampling interval

Watchdog vs. a cgroup limit

The watchdog is portable but best effort: it checks once per sampling interval, so a very fast allocation spike can get past it. When it fires, it kills the workers and exits with code 3, without pytest's teardown: containers are left to their own reaper (Ryuk for testcontainers).

On Linux with systemd, a cgroup limit is the hard guarantee: the kernel kills the run instead of swapping the desktop to death. You can use both:

systemd-run --user --scope -q -p MemoryMax=6G -p MemorySwapMax=0 \
    pytest -n auto --xdist-memory

Neither is needed for measuring. Measuring uses only psutil (and docker stats, if you ask for containers).

Requirements

Python ≥ 3.10, pytest ≥ 7, psutil. pytest-xdist is optional: without it, the plugin only reports the peak of the whole process tree.

License

MIT

Metadata

Release files for pytest-xdist-memory 0.1.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for pytest-xdist-memory 0.1.0
File Size Uploaded Provenance Actions
pytest_xdist_memory-0.1.0.tar.gz 13.6 kB With provenance Details for pytest_xdist_memory-0.1.0.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for pytest-xdist-memory 0.1.0
File Interpreter ABI Platform Actions
pytest_xdist_memory-0.1.0-py3-none-any.whl Python 3 none any Details for pytest_xdist_memory-0.1.0-py3-none-any.whl

Total release size: 27.4 kB

Release files / pytest_xdist_memory-0.1.0.tar.gz

Download URL pytest_xdist_memory-0.1.0.tar.gz
Size 13.6 kB
Tags Source
SHA-256 checksum
How to use checksums
3ee916790c6e63fea4faefb143023769a9ecf859281003e3e399a729fd869346
BLAKE2b-256 checksum
How to use checksums
7e2a72e2c363b27d6bb3bcb7f59ffb8f1863dc6153d3b9ed7ca41ea6d6bf61da
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 6, 2026.

Transparency log

Release files / pytest_xdist_memory-0.1.0-py3-none-any.whl

Download URL pytest_xdist_memory-0.1.0-py3-none-any.whl
Size 13.8 kB
Tags Python 3
SHA-256 checksum
How to use checksums
821b99e10f4bdb04041c2344d05d394ba1f6a4c107532d13fe5a307a1dc67d61
BLAKE2b-256 checksum
How to use checksums
4b867a45e37443d1f6e3ca6975849aef0864f1da7cdf827dd9188aeb0ed905d6
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 6, 2026.

Transparency log

Security for pytest-xdist-memory 0.1.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

Full provenance

Both files in this release have been uploaded with provenance metadata.

Select from 2 files

Attestation for pytest_xdist_memory-0.1.0.tar.gz

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 6, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.1.0 This release

2 release files Full provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page