13. Use pyproject.toml and uv.lock for Python dependencies¶
Date: 2026-10-19
Status¶
Accepted
Context¶
Since ADR 0007, Bedrock and Springfield compiled requirements/*.in files into hashed requirements/*.txt files, latterly with uv pip compile. dev.in included the compiled prod.txt, so the files had to be compiled in a fixed order. Our Makefile handled that, but Dependabot did not: it produced partial updates, such as a new prod.txt without a matching dev.txt, or a changed .txt file without its .in file. As a result, using Dependabot for Python dependencies was not practical.
Decision¶
We declare Python dependencies in pyproject.toml and lock them with uv in a single uv.lock:
- Production dependencies live in
[project] dependencies. Development tools live in thedevdependency group, and in Bedrock the docs tooling lives in thedocsgroup. uv.lockresolves all groups together, records hashes for every package and works across platforms.- The 7-day supply-chain delay moved into
[tool.uv]asexclude-newer, and Dependabot'suvecosystem uses a matching 7-day cooldown. - Local setup uses a uv-managed virtual environment (
.venvin each repo) instead of pyenv-virtualenv.
Consequences¶
- Dependabot can update Python dependencies, changing
pyproject.tomlanduv.lockin one pull request. - uv is required for local development, and
make install-local-python-depsno longer falls back to pip. - Existing pyenv-virtualenv setups need a one-time migration (see the installation docs), because uv cannot read a
.python-versionthat names a virtualenv. - Dependabot's uv support is newer than its pip support, so its first runs should be checked to make sure prod and dev updates both change
pyproject.tomlanduv.lock.