Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 57 additions & 0 deletions .github/workflows/release-verification-chain-policy.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
name: release-verification-chain-policy

on:
push:
branches: [main]
pull_request:
workflow_dispatch:

permissions:
contents: read

concurrency:
group: release-verification-chain-policy-${{ github.ref }}
cancel-in-progress: true

jobs:
qualify:
runs-on: ubuntu-24.04
steps:
- uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5, Node 24

- name: Qualify M1.29 automatic post-release chain
shell: bash
run: |
set -euo pipefail
file=.github/workflows/release-verification.yml

grep -Fq 'workflow_run:' "$file"
grep -Fq 'workflows: [release]' "$file"
grep -Fq 'types: [completed]' "$file"
grep -Fq "github.event.workflow_run.conclusion == 'success'" "$file"
grep -Fq "github.event.workflow_run.head_sha" "$file"
grep -Fq 'release-evidence.json' "$file"
grep -Fq '.release_commit == $commit' "$file"
grep -Fq 'No published release evidence is bound to release workflow commit' "$file"

# Existing independent fallbacks remain available.
grep -Fq 'release:' "$file"
grep -Fq 'types: [published]' "$file"
grep -Fq 'workflow_dispatch:' "$file"
grep -Fq "cron: '17 6 * * 1'" "$file"

# The release producer remains container-tag driven.
grep -Fq 'workflows: [container]' .github/workflows/release.yml
grep -Fq "startsWith(github.event.workflow_run.head_branch, 'v')" .github/workflows/release.yml
grep -Fq 'Create GitHub release if missing' .github/workflows/release.yml

- name: Record M1.29 policy
run: |
{
echo '### M1.29 automatic release-verification chain'
echo
echo '- successful release workflow runs automatically trigger release-verification'
echo '- release-verification binds the selected GitHub Release to the producer head SHA through release-evidence.json'
echo '- workflow-run selection fails closed if no published evidence matches the producer commit'
echo '- release, manual dispatch and weekly schedule triggers remain as independent fallbacks'
} >> "$GITHUB_STEP_SUMMARY"
30 changes: 30 additions & 0 deletions .github/workflows/release-verification.yml
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
name: release-verification

on:
workflow_run:
workflows: [release]
types: [completed]
release:
types: [published]
workflow_dispatch:
Expand All @@ -19,6 +22,9 @@ permissions:

jobs:
verify:
if: >-
github.event_name != 'workflow_run' ||
github.event.workflow_run.conclusion == 'success'
runs-on: ubuntu-24.04
steps:
- name: Select release to audit
Expand All @@ -27,6 +33,7 @@ jobs:
GH_TOKEN: ${{ github.token }}
EVENT_TAG: ${{ github.event_name == 'release' && github.event.release.tag_name || '' }}
INPUT_TAG: ${{ github.event_name == 'workflow_dispatch' && inputs.tag || '' }}
WORKFLOW_COMMIT: ${{ github.event_name == 'workflow_run' && github.event.workflow_run.head_sha || '' }}
shell: bash
run: |
set -euo pipefail
Expand All @@ -35,6 +42,29 @@ jobs:
tag="$INPUT_TAG"
fi

if [[ -z "$tag" && -n "$WORKFLOW_COMMIT" ]]; then
while IFS= read -r candidate; do
[[ -n "$candidate" ]] || continue
metadata="$(gh release view "$candidate" --repo "$GITHUB_REPOSITORY" --json isDraft,assets)"
if ! jq -e '.isDraft == false and any(.assets[]?; .name == "release-evidence.json")' <<<"$metadata" >/dev/null; then
continue
fi
tmp="$(mktemp -d)"
if gh release download "$candidate" --repo "$GITHUB_REPOSITORY" --dir "$tmp" --pattern release-evidence.json >/dev/null 2>&1 &&
jq -e --arg commit "$WORKFLOW_COMMIT" '.release_commit == $commit' "$tmp/release-evidence.json" >/dev/null 2>&1; then
tag="$candidate"
rm -rf "$tmp"
break
fi
rm -rf "$tmp"
done < <(gh release list --repo "$GITHUB_REPOSITORY" --limit 100 --json tagName --jq '.[].tagName')

if [[ -z "$tag" ]]; then
echo "No published release evidence is bound to release workflow commit $WORKFLOW_COMMIT" >&2
exit 1
fi
fi

if [[ -z "$tag" ]]; then
while IFS= read -r candidate; do
[[ -n "$candidate" ]] || continue
Expand Down
Loading