diff --git a/CHANGELOG.md b/CHANGELOG.md index 1dfaecb..438b03f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -88,6 +88,9 @@ adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). disable the recurring loop. ### Security +- Pin isolated PEP 517 source builds to the reviewed Hatchling 1.31.0 backend + identity so build isolation cannot silently resolve a different backend than + the hash-locked release toolchain. - Harden release publication evidence with validated integrating-PR identity, cross-repository required-workflow source checks, and Strix check-run annotations without adding an elevated release credential. diff --git a/pyproject.toml b/pyproject.toml index 14f95a1..808d7e8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,5 +1,5 @@ [build-system] -requires = ["hatchling"] +requires = ["hatchling==1.31.0"] build-backend = "hatchling.build" [project] diff --git a/tests/test_build_system_reproducibility.py b/tests/test_build_system_reproducibility.py new file mode 100644 index 0000000..28be3bd --- /dev/null +++ b/tests/test_build_system_reproducibility.py @@ -0,0 +1,27 @@ +"""Regression contracts for isolated PEP 517 build-tool identity.""" + +from __future__ import annotations + +from pathlib import Path + +try: + import tomllib +except ModuleNotFoundError: # pragma: no cover - Python 3.10 compatibility + import tomli as tomllib + +REPOSITORY_ROOT = Path(__file__).resolve().parents[1] +PYPROJECT_PATH = REPOSITORY_ROOT / "pyproject.toml" +RELEASE_REQUIREMENTS_PATH = REPOSITORY_ROOT / "requirements-release.txt" +REVIEWED_HATCHLING_VERSION = "1.31.0" + + +def test_pep517_build_isolation_uses_the_reviewed_hatchling_version() -> None: + """Keep isolated source builds on the same reviewed backend as release builds.""" + with PYPROJECT_PATH.open("rb") as pyproject_file: + build_system = tomllib.load(pyproject_file)["build-system"] + + assert build_system["build-backend"] == "hatchling.build" + assert build_system["requires"] == [f"hatchling=={REVIEWED_HATCHLING_VERSION}"] + + release_requirements = RELEASE_REQUIREMENTS_PATH.read_text(encoding="utf-8") + assert f"hatchling-{REVIEWED_HATCHLING_VERSION}-py3-none-any.whl" in release_requirements