Testing and CI¶
How to run tests locally and how GitHub Actions is wired.
Quick start (local)¶
Clone the repo and install Python 3.12, 3.13, and 3.14 (see
requires-pythonand tox envs).Install dev dependencies with uv:
uv sync --extra test
Lint:
uv run tox -e lint
One Python version:
uv run tox -e py314
Bare
uv run pytestusespyproject.tomladdopts and prints term-missing coverage.All supported versions + combined coverage (optional):
uv run tox -e coverage
Parallel matrix (before commit):
uv run tox run-parallel -p auto -o --skip-env lint
Runs
py312,py313, andpy314concurrently, thenreport(depends) to combine coverage. Use-ofor live output.
Subset of tests: uv run tox -e py314 -- tests/v1/test_auth.py -q
Documentation¶
uv sync --extra docs
uv run tox -e docs
Build fails on Sphinx warnings (-W).
Tox environments¶
Env |
Purpose |
|---|---|
|
pre-commit on all files |
|
Sphinx HTML build (warnings as errors) |
|
pytest on current interpreter |
|
pytest + coverage data in |
|
|
|
Depends on |
|
Packaging (release workflow) |
Python versions are defined once in [testenv:py3{12,13,14}]; tox picks the
interpreter from the env name (no per-env basepython blocks).
Coverage behavior¶
Local pytest —
addopts = "--cov --cov-report=term-missing"inpyproject.toml.Tox py envs — replace addopts with
--cov --cov-report=so each version collects silently;reportprints the combined result once.Why replace, not append? pytest-cov treats
--cov-reportas multi-allowed; appending--cov-report=does not cancelterm-missingfrom config.
GitHub Actions¶
Workflows:
.github/workflows/cicd.yaml— lint, docs, test matrix (3.12–3.14), combined coverage, Codecov (on push/PR tomain)..github/workflows/reusable-ci.yaml— shared jobs; inputs for Python versions andrun-codecov..github/workflows/release.yaml— runs CI thentox -e buildand PyPI publish, and triggers a Read the Docs build (default branch only; requiresREADTHEDOCS_TOKEN).
CI test step mirrors tox py envs: COVERAGE_FILE=.coverage.py312, pytest with
-o addopts="--cov --cov-report=", JUnit XML per version. Coverage artifacts use
include-hidden-files: true because .coverage.* files are dotfiles excluded by
upload-artifact@v4 by default.
Maintenance¶
Add a Python version — extend
[testenv:py3{12,13,14}]factor intox.ini, updatepython-versionsdefault inreusable-ci.yaml, install the interpreter locally, bump classifiers inpyproject.toml.Dependabot —
.github/dependabot.yml(GitHub Actions, pip, pre-commit).