From e8e26ae6dc9ee931f1295f1635bf85feff8378b7 Mon Sep 17 00:00:00 2001 From: Xavier Karma Date: Fri, 6 Nov 2026 20:23:22 +0530 Subject: [PATCH] docs(void): state that only the wheel is byte-reproducible The canonical sdist is built from the tag, but a second build of the same commit differs in tar and gzip timestamps, so its digest is recorded from the published asset, not from a rebuild. Correct the comments and docs that said "reproducible sdist". No behaviour change. --- .gitea/workflows/xbps-release.yml | 2 +- docs/RELEASE_PROCESS.md | 2 +- packaging/void/README.md | 7 +++++-- packaging/void/build-release.sh | 5 +++-- 4 files changed, 10 insertions(+), 6 deletions(-) diff --git a/.gitea/workflows/xbps-release.yml b/.gitea/workflows/xbps-release.yml index 8540c01..b85237a 100644 --- a/.gitea/workflows/xbps-release.yml +++ b/.gitea/workflows/xbps-release.yml @@ -8,7 +8,7 @@ name: xbps-release # and the committed Void template must already name that version; # 2. the XBPS_SIGNING_KEY secret must be non-empty and RSA 4096, and its public # half must be packaging/void/repository-key.plist; -# 3. the canonical reproducible sdist is built from the tag (Python 3.11, +# 3. the canonical sdist is built from the tag (Python 3.11, # uv 0.12/0.13, scripts/build_reproducible_wheel.py); # 4. every template builds in the pinned Void glibc image with podman (no # signing key in that phase), then the repository is signed in a second diff --git a/docs/RELEASE_PROCESS.md b/docs/RELEASE_PROCESS.md index 76249a5..5baf60c 100644 --- a/docs/RELEASE_PROCESS.md +++ b/docs/RELEASE_PROCESS.md @@ -558,7 +558,7 @@ approved each time: the workflow has no schedule and no manual trigger. 3. **Runner check.** podman, python3.11, uv 0.12/0.13, openssl, git and curl must be on the runner, or the job names what is missing and stops. 4. **Release.** `build-release.sh release` builds the canonical sdist from the - tag (reproducibly), builds every template in the pinned Void glibc container + tag, builds every template in the pinned Void glibc container without the key, signs the repository in a second container with no network, and installs `voculinux` from that repository in a clean image without the key. A local dry run is `just void-release vX.Y.Z` with `XBPS_SIGNING_KEY_FILE` diff --git a/packaging/void/README.md b/packaging/void/README.md index 872e58f..1b68eeb 100644 --- a/packaging/void/README.md +++ b/packaging/void/README.md @@ -151,7 +151,7 @@ throwaway RSA 4096 key generated in a temporary directory. The gate needs no host Void install and nothing is published. Stages, in order, each fails the run: 1. the tag gate (`check-tag`) and the committed template's version and `_tag`; -2. the reproducible sdist, built from the working tree; +2. the canonical sdist, built from the working tree; 3. `build`: every template in `PKGS` order (`smoke.sh` owns the list), linted with `xlint`, built with `xbps-src`, the sdist resolved by `xbps-src show`; 4. `sign`: the packages indexed and signed, with no network; @@ -177,7 +177,10 @@ Fail-closed, in this order, before any container starts: name that version and tag; - the key must be non-empty, valid, RSA 4096, and its public half must equal `repository-key.plist` byte for byte (a different key never publishes); -- the sdist must build, reproducibly, with Python 3.11 and uv 0.12/0.13. +- the canonical sdist must build with Python 3.11 and uv 0.12/0.13. Only its + wheel is compared byte for byte: a second build of the same tag has identical + contents, but the tar and gzip timestamps differ, so the release records the + digest of the sdist it publishes, not of a rebuild. Then three containers, each with only what it needs: diff --git a/packaging/void/build-release.sh b/packaging/void/build-release.sh index bcb1de9..c3a7625 100755 --- a/packaging/void/build-release.sh +++ b/packaging/void/build-release.sh @@ -12,7 +12,7 @@ # src/vocalinux/version.py, and the committed Void template must already # name that version and tag. Exits 1 otherwise. # build-release.sh release TAG --key-file FILE --out-dir DIR -# the whole release: gate, reproducible sdist, signed repository, +# the whole release: gate, canonical sdist, signed repository, # completeness check. Writes DIR/sdist and DIR/xbps. Publishes nothing; # the workflow publishes DIR. DIR must be absent or empty. # build-release.sh smoke @@ -155,7 +155,8 @@ check_key() { echo "signing key: RSA 4096, fingerprint $FINGERPRINT ($MODE)" } -# build_sdist: the canonical reproducible sdist, copied under its xbps name. +# build_sdist: the canonical sdist (the reproducible build path; only its wheel is +# compared byte for byte), copied under its xbps name. build_sdist() { command -v "$PYTHON" >/dev/null 2>&1 || fail "$PYTHON not found: the sdist is built with Python 3.11 (set PYTHON)"