diff --git a/.github/instructions/ci/workflow-contract.instructions.md b/.github/instructions/ci/workflow-contract.instructions.md index a105d9ed8..160bb182d 100644 --- a/.github/instructions/ci/workflow-contract.instructions.md +++ b/.github/instructions/ci/workflow-contract.instructions.md @@ -43,6 +43,7 @@ permissions: ### Action Pinning - **Organization reusable workflows**: Reference reusable workflows from `z-shell/.github/.github/workflows/` at `@main` ([ADR-0042](../../../decisions/0042-organization-reusable-workflows-at-main.md)). A change merged to the protected `main` of `z-shell/.github` then reaches every caller without a pull request in each repository. This covers only those reusable workflows; organization actions under `z-shell/.github/actions/` are pinned like any other action. The organization Renovate preset (`renovate-config.json`) leaves these `@main` references unpinned. +- **Code scanning**: CodeQL's `actions/unpinned-tag` query reports each `@main` reference to an organization reusable workflow. In a repository that runs CodeQL on Actions, moving a caller to `@main` raises that alert as a pull request review thread, which required review-thread resolution blocks until it is resolved. Reply in the thread with the ADR-0042 reason, dismiss the alert as "won't fix" with that reason, and resolve the thread. Dismiss only alerts on `z-shell/.github/.github/workflows/*@main` references; any other `actions/unpinned-tag` alert is a pinning defect to fix. - **Immutable Commit SHAs**: Every other remote action and reusable workflow `uses:` reference MUST be pinned to a full 40-character commit SHA. - **Version Comments**: Append the associated release version after the SHA for auditability (e.g., `# v4.3.1`). - **Existing SHA pins**: A caller that pins an organization reusable workflow to a full SHA with the earlier interim `# main` comment remains valid until it moves to `@main` in its own reviewed change. Such a pin must name a commit on the default branch of `z-shell/.github`, never a pull request's branch commit. A squash merge leaves that commit on no branch, and callers pinned to it end every run in a startup failure with no jobs ([#774](https://github.com/z-shell/.github/issues/774)). Before pinning, `gh api repos/z-shell/.github/compare/main...SHA --jq .status` must print `behind` or `identical`. The daily Community Health Audit reports any other pin (`repo-settings-audit.rb --workflow-pins`). @@ -127,4 +128,5 @@ new uses; migrate existing uses through their owning rollout and runbook. - [ ] Concurrency follows the execution-control rules above, including documented required-check exceptions and distinct caller/callee groups. - [ ] Organization reusable workflows from `z-shell/.github/.github/workflows/` are referenced at `@main` (or keep an existing full-SHA pin on the default branch); every other remote action and reusable workflow is pinned to a 40-character commit SHA with its release comment. - [ ] Any pinact exception uses the shared template's exact repository/workflow and its `main` or full-SHA ref match. +- [ ] A CodeQL `actions/unpinned-tag` alert on an `@main` organization reusable-workflow reference is answered with the ADR-0042 reason, dismissed as "won't fix" and its thread resolved; any other such alert is fixed. - [ ] Actionlint and YAML syntax checks pass. diff --git a/decisions/0042-organization-reusable-workflows-at-main.md b/decisions/0042-organization-reusable-workflows-at-main.md index d547f37c4..5dfad2ada 100644 --- a/decisions/0042-organization-reusable-workflows-at-main.md +++ b/decisions/0042-organization-reusable-workflows-at-main.md @@ -27,6 +27,7 @@ The shared workflows live in `z-shell/.github`, whose `main` is protected and ch - A defect merged to a shared workflow reaches every caller at once. Review on `z-shell/.github` is the control for that risk; a caller that must freeze a revision can still pin a default-branch SHA under point 3. - Changing a shared workflow's inputs, outputs or required permissions affects every caller on its next run, so such changes need the same care as an interface change: keep them backward compatible or coordinate the callers first. - Moving existing callers from SHA pins to `@main` is separate, per-repository work. +- CodeQL's `actions/unpinned-tag` query reports an `@main` reference in every repository that analyzes Actions, as a pull request review thread when a caller moves. The [workflow contract](../knowledge/domains/ci/workflow-contract.md) sets the handling: reply with this decision as the reason, dismiss the alert as "won't fix" and resolve the thread ([#809](https://github.com/z-shell/.github/issues/809)). ## Acceptance diff --git a/knowledge/domains/ci/workflow-contract.md b/knowledge/domains/ci/workflow-contract.md index 2284d118c..562e451b0 100644 --- a/knowledge/domains/ci/workflow-contract.md +++ b/knowledge/domains/ci/workflow-contract.md @@ -39,6 +39,7 @@ permissions: ### Action Pinning - **Organization reusable workflows**: Reference reusable workflows from `z-shell/.github/.github/workflows/` at `@main` ([ADR-0042](../../../decisions/0042-organization-reusable-workflows-at-main.md)). A change merged to the protected `main` of `z-shell/.github` then reaches every caller without a pull request in each repository. This covers only those reusable workflows; organization actions under `z-shell/.github/actions/` are pinned like any other action. The organization Renovate preset (`renovate-config.json`) leaves these `@main` references unpinned. +- **Code scanning**: CodeQL's `actions/unpinned-tag` query reports each `@main` reference to an organization reusable workflow. In a repository that runs CodeQL on Actions, moving a caller to `@main` raises that alert as a pull request review thread, which required review-thread resolution blocks until it is resolved. Reply in the thread with the ADR-0042 reason, dismiss the alert as "won't fix" with that reason, and resolve the thread. Dismiss only alerts on `z-shell/.github/.github/workflows/*@main` references; any other `actions/unpinned-tag` alert is a pinning defect to fix. - **Immutable Commit SHAs**: Every other remote action and reusable workflow `uses:` reference MUST be pinned to a full 40-character commit SHA. - **Version Comments**: Append the associated release version after the SHA for auditability (e.g., `# v4.3.1`). - **Existing SHA pins**: A caller that pins an organization reusable workflow to a full SHA with the earlier interim `# main` comment remains valid until it moves to `@main` in its own reviewed change. Such a pin must name a commit on the default branch of `z-shell/.github`, never a pull request's branch commit. A squash merge leaves that commit on no branch, and callers pinned to it end every run in a startup failure with no jobs ([#774](https://github.com/z-shell/.github/issues/774)). Before pinning, `gh api repos/z-shell/.github/compare/main...SHA --jq .status` must print `behind` or `identical`. The daily Community Health Audit reports any other pin (`repo-settings-audit.rb --workflow-pins`). @@ -123,4 +124,5 @@ new uses; migrate existing uses through their owning rollout and runbook. - [ ] Concurrency follows the execution-control rules above, including documented required-check exceptions and distinct caller/callee groups. - [ ] Organization reusable workflows from `z-shell/.github/.github/workflows/` are referenced at `@main` (or keep an existing full-SHA pin on the default branch); every other remote action and reusable workflow is pinned to a 40-character commit SHA with its release comment. - [ ] Any pinact exception uses the shared template's exact repository/workflow and its `main` or full-SHA ref match. +- [ ] A CodeQL `actions/unpinned-tag` alert on an `@main` organization reusable-workflow reference is answered with the ADR-0042 reason, dismissed as "won't fix" and its thread resolved; any other such alert is fixed. - [ ] Actionlint and YAML syntax checks pass.