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
65 changes: 63 additions & 2 deletions .github/workflows/release.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -324,14 +324,16 @@ jobs:
(cd "$directory" && npm install --package-lock-only --ignore-scripts)
done

node scripts/generate-stack-facts.mjs

if git diff --quiet; then
echo "changed=false" >> "$GITHUB_OUTPUT"
exit 0
fi

git config user.name "github-actions[bot]"
git config user.email "41898282+github-actions[bot]@users.noreply.github.com"
git add pnpm-lock.yaml 'packages/**/package.json' 'infra/**/package.json' 'infra/**/package-lock.json'
git add pnpm-lock.yaml docs/reference/stack-facts.md 'packages/**/package.json' 'infra/**/package.json' 'infra/**/package-lock.json'
git commit -m "chore: sync published workspace versions"

echo "changed=true" >> "$GITHUB_OUTPUT"
Expand All @@ -354,7 +356,66 @@ jobs:
run: |
existing_pr="$(gh pr list --base main --head "$SYNC_BRANCH" --state open --json number --jq '.[0].number')"

body="Updates workspace package references, pnpm-lock.yaml, and infra/*/package-lock.json after a successful npm publish."
body="$(cat <<EOF
## Program and scope

- Tracker or issue: protected release run ${GITHUB_RUN_ID}
- Program gate(s) advanced: published-version reconciliation and reproducible OCI release inputs
- Why this change is needed: synchronize first-party package floors and standalone infrastructure locks after protected npm publication.
- Explicitly out of scope: product behavior beyond consuming the already-reviewed package artifacts.
- Exact head SHA reviewed: generated sync commit; hosted checks bind validation to the PR head.

## Impact

- [x] No public package source or manifest changed
- [x] Infrastructure source, dependency, image, or deployment configuration changed
- [x] Security-sensitive boundary changed

Affected services and intended patch versions are the changed infra package manifests in this PR.

## Verification

- Local commands and results: generated by protected release run ${GITHUB_RUN_ID} after successful npm publication.
- Hosted CI run: pending for this exact head.
- Conformance evidence: Not selected because no conformance input changed.
- Coverage delta: No product source changed.
- Lint/typecheck delta: Pending hosted affected-graph validation.
- Browser/mobile/packed-consumer evidence: The protected release passed package, clean-consumer, browser, and mobile verification before publication.
- Performance or bundle-size delta: No product source or bundle composition changed.
- [x] I self-reviewed the complete diff for correctness, security, compatibility, public API, artifacts, dependencies, docs, and operations
- [ ] All applicable checks are terminal and successful on the exact head; any scope-based skip is expected and validated by the merge gate

## Security and dependencies

- [x] Changelog, runtime relevance, peer compatibility, transitive graph, and audit results were reviewed by the protected release
- [x] No new override, advisory dismissal, quality suppression, or skipped test
- [x] Workflow permissions and lifecycle-script behavior remain least privilege

## Dependency evidence

- Release notes and necessity: The protected release already validated the coordinated package release notes and migration guidance.
- Runtime, build, and peer compatibility: The release verified the governed Node, browser, mobile, runtime, and peer-dependency contracts.
- Deduplicated lockfile: Workspace and standalone npm locks were regenerated once from the published first-party versions without lifecycle scripts.
- Audit and CodeQL: The release rejected high and critical package findings; exact-head CodeQL runs on this PR.
- Package and consumer tests: The release passed full builds, typecheck, package artifacts, clean consumers, browser, mobile, registry signatures, provenance, and reconciliation.
- Bundle and performance impact: No bundle composition changed; affected releases retain their documented compatibility contracts.
- Affected public package versions: Derived from the published workspace manifests synchronized by this exact commit.

## Release and operations

- [x] No npm publication was performed from a workstation or from this PR
- [x] Required npm patch bumps are included or intentionally deferred by the controlling program
- [x] Image/SBOM/provenance/deployment/rollback impact is documented by the protected infrastructure release
- [x] Documentation, changelog, migration, and operational guidance are current

The protected infrastructure release builds Linux/amd64 images, rejects high and critical findings, publishes immutable GHCR tags, and attaches SBOM, provenance, and signature evidence after merge. Existing immutable tags remain the rollback path.

## Completion evidence

- [x] Documentation, changelog, migration notes, release notes, and operator guidance are current or concretely not applicable
- [x] One qualified maintainer approval is sufficient; no last-pusher restriction is assumed
EOF
)"
if [[ -n "$existing_pr" ]]; then
gh pr edit "$existing_pr" \
--title "chore: sync published workspace versions" \
Expand Down
21 changes: 20 additions & 1 deletion scripts/package-release-artifacts.test.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -455,6 +455,25 @@ test('npm release workflow preserves scan, attestation, verification, and exact-
assert.match(verifyStep, /gh attestation verify/)
const pushSync = workflow.indexOf('- name: Push version sync branch')
const openSyncPr = workflow.indexOf('- name: Open version sync PR')
const prepareSync = workflow.slice(
workflow.indexOf('- name: Prepare published workspace version sync'),
pushSync
)
assert.match(prepareSync, /node scripts\/generate-stack-facts\.mjs/)
assert.match(prepareSync, /git add [^\n]*docs\/reference\/stack-facts\.md/)
assert.match(workflow.slice(pushSync, openSyncPr), tokenBinding)
assert.match(workflow.slice(openSyncPr), tokenBinding)
const openSyncPrStep = workflow.slice(openSyncPr)
assert.match(openSyncPrStep, tokenBinding)
assert.match(openSyncPrStep, /## Dependency evidence/)
for (const field of [
'Release notes and necessity',
'Runtime, build, and peer compatibility',
'Deduplicated lockfile',
'Audit and CodeQL',
'Package and consumer tests',
'Bundle and performance impact',
'Affected public package versions'
]) {
assert.match(openSyncPrStep, new RegExp(`- ${field}: \\S`))
}
})
Loading