Skip to content

ENT-13786: Reproducible container builds#2249

Open
larsewi wants to merge 4 commits into
cfengine:masterfrom
larsewi:reproducible-container-builds
Open

ENT-13786: Reproducible container builds#2249
larsewi wants to merge 4 commits into
cfengine:masterfrom
larsewi:reproducible-container-builds

Conversation

@larsewi
Copy link
Copy Markdown
Contributor

@larsewi larsewi commented May 11, 2026

Make the container build path produce bit-identical packages across two cache-cleared runs.

Four commits:

  1. Export SOURCE_DATE_EPOCH at the top of build-in-container-inner.sh. Honored by OpenSSL, Apache httpd, PHP, OpenLDAP, dpkg-buildpackage, and rpmbuild. Pins embedded build timestamps.
  2. composer install --prefer-dist to avoid leaving .git/ directories in the vendor tree. Hint, not enforced — see commit 4.
  3. PHP source patch so ext/phar honors SOURCE_DATE_EPOCH. Upstream PHP's phar packer unconditionally embeds time(NULL) into manifest entries. Patches four call sites in ext/phar/{phar,util,tar,zip}.c. Worth submitting upstream to php-src separately so we don't carry it indefinitely.
  4. Strip composer vendor .git/ after install. --prefer-dist falls back to source when GitHub's anonymous zipball API rate-limits (60 req/hour; mission-portal has dozens of packages). Matches what CI does accidentally via --exclude=".git" in build-scripts/transfer-to-buildmachine.
$ sha256sum *.deb
33247d26a4b05dadfe2f20e1810c69d2e8e148e9984d4c905ae5d562496f0fd4  post1-fix.deb
33247d26a4b05dadfe2f20e1810c69d2e8e148e9984d4c905ae5d562496f0fd4  post2-fix.deb

larsewi added 4 commits May 11, 2026 16:47
Pin embedded build timestamps in the container build entrypoint so
two builds of the same source produce identical binaries. Honored by
OpenSSL, Apache httpd, PHP, OpenLDAP, dpkg-buildpackage, and rpmbuild.
Derived from core's HEAD commit time, honoring a caller-provided
value if already set.

Ticket: ENT-13786
Signed-off-by: Lars Erik Wik <lars.erik.wik@northern.tech>
Composer's default falls back to cloning vendored packages, leaving
.git directories in the vendor tree with non-deterministic pack files
and reflog timestamps. --prefer-dist downloads zipballs instead, so
no .git directory is created.

Signed-off-by: Lars Erik Wik <lars.erik.wik@northern.tech>
PHP's phar embeds time(NULL) into every manifest entry, making
phar.phar non-reproducible. Patch ext/phar to honor SOURCE_DATE_EPOCH
when set, falling back to time(NULL) otherwise. Wire the patch into
both the rpm spec and debian rules.

Signed-off-by: Lars Erik Wik <lars.erik.wik@northern.tech>
Composer falls back to git clone when GitHub's anonymous zipball API
rate limit is hit, so --prefer-dist alone is not enough to guarantee a
.git-free vendor tree. Strip any .git directories that end up under
vendor/ after the composer installs.

Signed-off-by: Lars Erik Wik <lars.erik.wik@northern.tech>
@larsewi larsewi marked this pull request as ready for review May 12, 2026 08:58
Copy link
Copy Markdown
Contributor

@craigcomstock craigcomstock left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it the case that we could run the build-in-container-inner.sh script by itself on a host and build? We are putting a lot of important logic in there and I wonder if we shouldn't refactor things to make it more obvious that we could run this script "anywhere" so to speak?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

2 participants