a11oy / .github /workflows /slsa.yml
betterwithage's picture
sync(space): full source mirror — resolve all GitHub<->Space drift (CTO)
a6a5d8e verified
Raw
History Blame
5.36 kB
name: SLSA Build L1 (provenance attestation)
# SLSA v1.0 Build L1 requires that provenance EXISTS describing how the
# artifact was built and is DISTRIBUTED to consumers
# (https://slsa.dev/spec/v1.0/levels#build-l1).
#
# The previous job was a no-op stub (`run: echo "SLSA L1 supply-chain checks OK"`)
# which emitted no provenance and therefore did not satisfy Build L1.
#
# This workflow now:
# 1. Builds the same a11oy-uds-<version>.tar.zst artifact produced by
# uds-sign-release.yml (git archive | zstd).
# 2. Generates an in-toto v1 SLSA provenance attestation for that artifact
# via actions/attest-build-provenance. The attestation is signed with the
# SAME Sigstore keyless flow already used for release signing
# (GitHub OIDC -> Fulcio short-lived cert -> Rekor transparency log).
# 3. Uploads the provenance bundle (.intoto.jsonl) as a release asset so it
# is distributed to consumers alongside the artifact.
#
# Doctrine v6: no echo stubs, verifiable provenance only.
on:
workflow_dispatch:
inputs:
tag_name:
description: 'Release tag to attest (e.g. uds-v0.3.0). Optional on push.'
required: false
type: string
release:
types: [published]
permissions:
contents: read
jobs:
provenance:
name: Build artifact + attest SLSA provenance
runs-on: ubuntu-latest
permissions:
id-token: write # OIDC token -> Sigstore Fulcio keyless signing
contents: write # upload provenance + write attestation to release
attestations: write # store the attestation in the repo attestations API
actions: read
steps:
- name: Resolve tag name
id: tag
run: |
if [[ "${{ github.event_name }}" == "release" ]]; then
TAG="${{ github.event.release.tag_name }}"
else
TAG="${{ inputs.tag_name }}"
fi
if [[ -z "${TAG}" ]]; then
# No tag context (e.g. manual dispatch on main): attest the current ref.
TAG="$(git rev-parse --short HEAD 2>/dev/null || echo main)"
VERSION="0.0.0-dev-${TAG}"
else
VERSION="${TAG#uds-v}"
fi
echo "tag=${TAG}" >> "$GITHUB_OUTPUT"
echo "version=${VERSION}" >> "$GITHUB_OUTPUT"
echo "tarball=a11oy-uds-${VERSION}.tar.zst" >> "$GITHUB_OUTPUT"
- name: Checkout
uses: actions/checkout@df4cb1c069e1874edd31b4311f1884172cec0e10 # v6.0.3
with:
ref: ${{ steps.tag.outputs.tag }}
fetch-depth: 0
- name: Build tar.zst (same artifact as uds-sign-release.yml)
id: build
run: |
VERSION="${{ steps.tag.outputs.version }}"
TARBALL="${{ steps.tag.outputs.tarball }}"
echo "Building ${TARBALL}..."
git archive \
--format=tar \
--prefix="a11oy-uds-${VERSION}/" \
HEAD \
| zstd -19 -T0 -o "${TARBALL}"
echo "Built ${TARBALL}: $(wc -c < "${TARBALL}") bytes"
echo "tarball_path=${PWD}/${TARBALL}" >> "$GITHUB_OUTPUT"
- name: Generate SLSA provenance attestation (Sigstore keyless)
id: attest
uses: actions/attest-build-provenance@a2bbfa25375fe432b6a289bc6b6cd05ecd0c4c32 # v4.1.0
with:
subject-path: ${{ steps.build.outputs.tarball_path }}
- name: Stage provenance as a distributable .intoto.jsonl
id: prov
run: |
VERSION="${{ steps.tag.outputs.version }}"
PROV_OUT="a11oy-uds-${VERSION}.tar.zst.intoto.jsonl"
# actions/attest-build-provenance writes the signed in-toto v1 bundle
# to a file whose path is exported as bundle-path.
cp "${{ steps.attest.outputs.bundle-path }}" "${PROV_OUT}"
echo "Provenance bundle: ${PROV_OUT} ($(wc -c < "${PROV_OUT}") bytes)"
echo "prov_file=${PROV_OUT}" >> "$GITHUB_OUTPUT"
- name: Upload provenance to the GitHub release (distribute to consumers)
if: github.event_name == 'release'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
TAG="${{ steps.tag.outputs.tag }}"
PROV_OUT="${{ steps.prov.outputs.prov_file }}"
gh release upload "${TAG}" "${PROV_OUT}" \
--clobber \
--repo szl-holdings/a11oy
echo "Provenance distributed as a release asset on ${TAG}."
- name: Upload provenance as workflow artifact (dispatch runs)
if: github.event_name != 'release'
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: ${{ steps.prov.outputs.prov_file }}
path: ${{ steps.prov.outputs.prov_file }}
retention-days: 90
- name: Print verification instructions
run: |
VERSION="${{ steps.tag.outputs.version }}"
echo "=== Verify SLSA provenance ==="
echo "slsa-verifier verify-artifact \\"
echo " --provenance-path a11oy-uds-${VERSION}.tar.zst.intoto.jsonl \\"
echo " --source-uri github.com/szl-holdings/a11oy \\"
echo " a11oy-uds-${VERSION}.tar.zst"
echo ""
echo "Or with the GitHub CLI (uses the repo attestations API + Rekor):"
echo " gh attestation verify a11oy-uds-${VERSION}.tar.zst --repo szl-holdings/a11oy"