UID2-6764: Add SLSA build provenance attestations to docker publish workflows#228
Open
BehnamMozafari wants to merge 10 commits intomainfrom
Open
UID2-6764: Add SLSA build provenance attestations to docker publish workflows#228BehnamMozafari wants to merge 10 commits intomainfrom
BehnamMozafari wants to merge 10 commits intomainfrom
Conversation
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Attestation runs after the docker push but before the changelog/release steps. Without continue-on-error, an attest failure leaves a half-finished release: image pushed, no GitHub Release created. Tolerate attest failures during the v3 rollout so consumers aren't stuck mid-release if attestation breaks. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This reverts commit 80a5560.
This was referenced May 8, 2026
Contributor
|
Can we do a real smoke test without "Attest build provenance" step being skipped? |
jon8787
reviewed
May 8, 2026
jon8787
reviewed
May 8, 2026
jon8787
reviewed
May 8, 2026
Addresses jon8787's review comments on PR #228: - #2 verify step: attest_image now calls 'gh attestation verify' immediately after signing so misconfigured signatures fail at build time, not consumer pull time. - #3 case sensitivity: lowercase the image ref once and reuse it for both signing and verifying. actions/attest@v4 already lowercases subject-name internally when push-to-registry is true (verified at the pinned commit 59d8942 in src/main.ts and src/subject.ts), but 'gh attestation verify' does NOT lowercase the OCI URI we pass it; doing it ourselves keeps the signed name and the verified URI byte-identical. - #4 NODE_OPTIONS comment: brief comment explaining why we mirror actions/attest-build-provenance's defensive HTTP header bump. - #5 extract: pulled the attest+verify pair into a single composite action so the Java workflow and the non-Java composite action share one implementation. Adds .github/workflows/test-attest-image.yaml: a manually-dispatched smoke test that builds a throwaway image and exercises the full attest+verify path. Use this whenever attest_image or actions/attest@v4 changes. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Drop after merge — only here so the smoke test can run before the workflow file lands on main (gh workflow run / API dispatch require the file to exist on the default branch). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
github.repository is mixed case; docker rejects mixed-case tags at push time. Compute a lowercased ref once and reuse it for the push tag, the attest_image input, and the independent re-verify command. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…st is green Run 25542801315 verified the attest+verify path end-to-end. Reverting to workflow_dispatch only so the test stops auto-firing and remains as an on-demand regression check after merge. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Run 25542801315 captured the verified attestation evidence on PR #228; keeping the workflow would just push throwaway test images on every manual dispatch. The composite action lives at actions/attest_image and can be re-tested in any future change by re-adding this workflow file ad-hoc. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds SLSA build-provenance attestation to every non-snapshot image published by the shared docker workflows.
actions/attest_imagewraps the full attest+verify path: it lowercases the image ref once, callsactions/attest@v4.1.0(pinned to59d8942), and immediately runsgh attestation verifyagainst the just-pushed digest.shared-publish-java-to-docker-versioned.yamlandactions/shared_publish_to_docker/action.yamlnow callattest_image@v3instead of inlining the attest block.id-token: writeandattestations: write.not_snapshotguard.Closes UID2-6764. Spike was UID2-5763.
Review-comment responses
test-attest-image.yamlworkflow that exercised the full attest+verify path against a throwaway image. Run25542801315green; full evidence below. Workflow then deleted in3954ca4since the captured evidence is permanent.gh attestation verifystepattest_imageso every release verifies in CI before any consumer pulls.subject-nameactions/attest@v4already auto-lowercasessubject-namewhenpush-to-registry: true(verified insrc/main.ts→downcaseName: inputs.pushToRegistry, applied atsrc/subject.tsline 47). However,gh attestation verifydoes not lowercase the OCI URI we pass it. To keep the signed name and the verify URI byte-identical,attest_imagelowercases once at the top and reuses the value for both. (The smoke test caught a real case-sensitivity failure in the first run when${{ github.repository }}evaluated toIABTechLab/...anddocker pushrejected it — proves the concern is real.)NODE_OPTIONSattest_image/action.yaml:Mirrors actions/attest-build-provenance, prevents oversized OCI registry auth-challenge headers triggering HPE_HEADER_OVERFLOW.actions/attest_image/action.yamlis the single implementation.Smoke test evidence
Run 25542801315 — all 9 steps green in 38s.
Test image:
ghcr.io/iabtechlab/uid2-shared-actions/test-attest@sha256:e008cbdd1c67eee898020ad96d56ff0d42d762585ef4c1153479abaf5a4112bbEnd-to-end chain: image digest → SLSA v1 provenance → workflow file at the exact branch ref → GitHub-hosted runner OIDC identity.
Test plan
IABTechLab/uid2-admin(Java path) — run 25421656856 — workflow succeeded, "Attest build provenance" step skipped (proves thenot_snapshotguard works).gh attestation verifysucceeds (output above).v3float is promoted; verified digests will be recorded in the UID2-6764 ticket.Post-merge sequence
update-major-version-tags.yamlonmainimmediately after — the refactored workflows referenceactions/attest_image@v3, and the window between merge and tag promotion is a window where consumers triggering would fail with "action not found".IABTechLab/uid2-admin:bmz-UID2-6764-test(only existed to pin the shared workflow at the feature branch for the snapshot smoke test).Caller-repo follow-up — already opened (one PR each, all open as of 2026-05-08)
Each grants
id-token: write+attestations: write(plus the implicit defaults the publish job already relied on). They're additive and harmless until this PR merges andv3is promoted.SDK images are explicitly out of scope; follow-up ticket to be filed separately.