Skip to content

ci: migrate no-mistakes gate to shared action - #47

Merged
kunchenguid merged 1 commit into
mainfrom
fm/tasks-axi-nm-migrate-r1
Aug 23, 2026
Merged

ci: migrate no-mistakes gate to shared action#47
kunchenguid merged 1 commit into
mainfrom
fm/tasks-axi-nm-migrate-r1

Conversation

@kunchenguid

Copy link
Copy Markdown
Owner

Intent

Migrate this repo's no-mistakes gate to the shared require-no-mistakes composite action, replicating the exact pattern already merged in rough-cut-axi PR #4 (the proven template).

Changes:

  1. .github/workflows/no-mistakes-required.yml: replace the entire inline gate run: step with a thin caller step using kunchenguid/no-mistakes/.github/actions/require-no-mistakes@32d396ac0f29135daf7fcb9964aba9d5f4e796d6 # post-v1.57.1, untagged (action added in #819). Keep EXACTLY as-is: the job name 'PR must be raised via no-mistakes', the job-level if: author exemptions (github-actions[bot], dependabot[bot], and this repo's release-please[bot]), concurrency, permissions, and this repo's paths-ignore release-output set. The enforcement logic (attestation parse, head-binding, skip-marker rejection) now lives in the shared action - deliberately do NOT keep a local copy.
  2. on.pull_request.types: set to [opened, edited, reopened] - DROP synchronize. This was verified safe: this repo's ruleset is advisory with NO required status check, so dropping synchronize cannot wedge a merge on 'Expected - waiting for status'. The verdict is a pure function of pull_request.body, and the pipeline pushes before it writes the Pipeline section, so a synchronize trigger pinned a FAILURE check run to a head whose body the same run was about to fix (upstream PR #773).
  3. REMOVE the now-dead gate-script test test/workflows/no-mistakes-gate.test.ts: it extracted the inline run: block at module init and executed it, so with the inline block gone it throws on import. rough-cut-axi PR feat(backends): round-trip firstmate backlog format #4 handled this the same way - it deleted its gate test file, its extractor helper, and the workflow-shape test that also extracted the script. No replacement test is added here, matching the reference PR: enforcement logic and its tests now live upstream in the no-mistakes repository.
  4. AGENTS.md: replaced the note instructing agents to hand-copy the gate byte-for-byte from gh-axi (that hand-copy drift is exactly what this migration kills) with a note pointing at the shared action, the immutable-SHA pinning rule (never @main, since main is editable by the very PR the gate judges), what this repo still owns locally, and why synchronize is omitted.

Explicit captain decisions carried into this work, so a reviewer reading only the diff does not flag them as regressions:

  • The shared action's last-wins verdict semantics are INTENDED. Relaxing the stricter local inline jq (which required every duplicate record of a step to be 'completed') to the shared action's semantics is CORRECT, not a regression. Do not try to preserve the extra strictness locally.
  • Losing local test coverage of the enforcement script is intended: the script no longer lives here. Do not add a substring/regex test over the workflow YAML to compensate.
  • The pin SHA was verified to exist and to contain .github/actions/require-no-mistakes/action.yml.
  • The existing test/release-ci-exclusions.test.ts assertions (paths-ignore coverage, bot author exemptions) still apply and still pass unchanged.

Verified locally before running: pnpm build, pnpm lint, pnpm test (430 tests, 21 files, all passing), and pnpm run build:skill -- --check are all green.

What Changed

  • Replace the inline no-mistakes enforcement script with the shared composite action pinned to an immutable commit.
  • Stop triggering the body-based gate on synchronize events while preserving local workflow configuration and author exemptions.
  • Remove obsolete inline-script tests and document the shared enforcement ownership and update policy.

Risk Assessment

✅ Low: The change is narrowly scoped, preserves repository-owned workflow settings, and delegates enforcement to the correctly pinned shared action without introducing unsupported local logic.

Testing

After the author-reported green build, lint, full test, and skill checks, targeted testing confirmed release-output exclusions, preserved workflow semantics, the exact composite-action pin, intended last-wins acceptance, and stale-head rejection. Temporary dependencies and test files were removed.

Evidence: Normalized workflow contract and pinned shared-action end-to-end gate transcript

Source: Normalized workflow contract and pinned shared-action end-to-end gate transcript

=== Normalized caller contract ===
{
  "pull_request": {
    "types": [
      "opened",
      "edited",
      "reopened"
    ],
    "branches": [
      "main"
    ],
    "paths-ignore": [
      ".release-please-manifest.json",
      "CHANGELOG.md",
      "package.json"
    ]
  },
  "permissions": {
    "contents": "read"
  },
  "concurrency": {
    "group": "no-mistakes-required-${{ github.event.pull_request.number }}-${{ (github.event.action == 'opened' || github.event.action == 'edited') && github.run_id || 'head-change' }}",
    "cancel-in-progress": true
  },
  "job": {
    "name": "PR must be raised via no-mistakes",
    "runs_on": "ubuntu-latest",
    "if": "github.event.pull_request.user.login != 'github-actions[bot]' && github.event.pull_request.user.login != 'dependabot[bot]' && github.event.pull_request.user.login != 'release-please[bot]'",
    "steps": [
      {
        "name": "Verify no-mistakes signature and pipeline attestation in PR body",
        "uses": "kunchenguid/no-mistakes/.github/actions/require-no-mistakes@32d396ac0f29135daf7fcb9964aba9d5f4e796d6"
      }
    ]
  }
}

=== Pinned action manifest ===
{
  "name": "Require no-mistakes",
  "using": "composite",
  "step": {
    "name": "Verify no-mistakes signature and pipeline attestation",
    "shell": "bash"
  }
}

=== End-user gate result: current-head attestation with last duplicate record completed ===
Found no-mistakes signature in PR #42 body.
Found structurally compliant pipeline step attestation.
::warning::PR-body attestation is author-editable and is not cryptographic proof that no-mistakes produced it.
exempt=false
compliant=true

=== End-user gate result: stale attestation after later push ===
::error::Pipeline attestation head_sha does not match the current PR head.

attestation.head_sha: 9ea7d1d8648d2fa012a74ac45e21cac589c62407
PR head: 0000000000000000000000000000000000000000

A later push must not pass on an older attestation. Re-run 'git push no-mistakes' so the PR body attestation binds to the current head.

See CONTRIBUTING.md for setup and the full workflow.

PR author: somedev
Found no-mistakes signature in PR #42 body.
exempt=false
compliant=false
exempt=false
exit_status=1

Pipeline

Updates from git push no-mistakes

✅ **intent** - passed

✅ No issues found.

✅ **Rebase** - passed

✅ No issues found.

✅ **Review** - passed

✅ No issues found.

✅ **Test** - passed

✅ No issues found.

  • pnpm install --frozen-lockfile
  • pnpm exec vitest run test/release-ci-exclusions.test.ts
  • Parsed the workflow into a normalized YAML model and compared preserved branches, paths-ignore, permissions, concurrency, job name, runner, and author exemptions against base commit 24ddd22db217a844f2103f4ea78247b9be86819b
  • Fetched the composite action and executable from pinned commit 32d396ac0f29135daf7fcb9964aba9d5f4e796d6, then executed a compliant last-wins duplicate-step fixture and a stale-head rejection fixture through its event-payload interface
✅ **Document** - passed

✅ No issues found.

✅ **Lint** - passed

✅ No issues found.

✅ **Push** - passed

✅ No issues found.

Replace the inline gate `run:` block in
.github/workflows/no-mistakes-required.yml with a thin caller of
kunchenguid/no-mistakes/.github/actions/require-no-mistakes, pinned to an
immutable commit SHA. Enforcement logic and its tests now live upstream, so
this repository no longer carries a hand-copied script that can drift from
its siblings.

Drop `synchronize` from the pull_request trigger: the verdict is a pure
function of the PR body, and the pipeline pushes before it writes the
Pipeline section, so a push-triggered run pinned a failure to a head whose
body the same run was about to fix. This repo's ruleset is advisory with no
required status check, so dropping the trigger cannot wedge a merge.

Remove test/workflows/no-mistakes-gate.test.ts, which extracted and executed
the now-absent inline block, and point AGENTS.md at the shared action.
@kunchenguid
kunchenguid merged commit 4c09455 into main Aug 23, 2026
5 checks passed
yjuyjuy added a commit to yjuyjuy/tasks-axi that referenced this pull request Aug 24, 2026
…e no-mistakes gate to the shared action (#6)

* fix(cli): speed up standalone version queries (kunchenguid#34)

* perf(cli): answer --version through the axi-sdk-js fast path

Extract the package-version helper out of the heavy `src/cli.ts` graph into a
leaf `src/version.ts` (node builtins only), and rewrite `bin/tasks-axi.ts` to
answer a bare `-v`/`-V`/`--version` via `axi-sdk-js/fast-path`, dynamically
importing the command graph only for everything else. Bumps axi-sdk-js to
^0.1.10 for the `./fast-path` subpath export.

Version output is byte-identical and all other argv shapes still route through
`runAxiCli` unchanged. Guarded by a deterministic ESM loader module trace with
a negative control plus flag parity; no wall-clock assertion in CI.

* no-mistakes(document): Confirm fast-path docs and lint cleanliness

* no-mistakes: apply CI fixes

* chore(main): release tasks-axi 0.2.5 (kunchenguid#35)

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* fix(cli): accept canonical Forgejo pull request URLs (kunchenguid#36)

* fix: accept canonical Forgejo pull request URLs as typed PR links

One classification seam (isPrUrl in src/pr-url.ts) now decides what
counts as a PR URL for prose link derivation, done/add --pr validation,
and public-followup pr_url deliverables: canonical GitHub
https://github.com/<owner>/<repo>/pull/<n> or Forgejo
https://<host>/<owner>/<repo>/pulls/<n> with a positive, no-leading-zero
number. Near misses (issue routes, singular/plural route confusion,
trailing slash, query/fragment, whitespace, userinfo, ports, encoded
separators, malformed segments) are rejected as --pr / pr_url values and
derive as doc links, never pr.

Fixes kunchenguid#19

* fix: validate pr links against the untrimmed input

Review follow-ups from pipeline run 01KZFA73D662DCSJ4HVWKW21QX: --pr values
and pr-kind addLinks are validated before any trim, so whitespace-padded
input is rejected instead of normalized. The literal NUL byte in
test/pr-url.test.ts is now written as a unicode source escape so git
treats the file as text; an embedded-space rejection case is added
alongside it.

* chore: remove committed no-mistakes evidence (now on orphan branch) (kunchenguid#39)

* chore: gitignore no-mistakes evidence dir (contributor safety) (kunchenguid#41)

* chore(agents): use @AGENTS.md import instead of CLAUDE.md symlink (kunchenguid#42)

Co-authored-by: Kun Chen <kun-1@kunchenguid.com>

* ci: require no-mistakes pipeline attestation in the gate (kunchenguid#45)

* ci: require no-mistakes pipeline attestation in the gate

* test: run the no-mistakes gate script on POSIX legs only

* ci: bind the no-mistakes attestation to the current PR head (kunchenguid#46)

* ci: migrate the no-mistakes gate to the shared composite action (kunchenguid#47)

Replace the inline gate `run:` block in
.github/workflows/no-mistakes-required.yml with a thin caller of
kunchenguid/no-mistakes/.github/actions/require-no-mistakes, pinned to an
immutable commit SHA. Enforcement logic and its tests now live upstream, so
this repository no longer carries a hand-copied script that can drift from
its siblings.

Drop `synchronize` from the pull_request trigger: the verdict is a pure
function of the PR body, and the pipeline pushes before it writes the
Pipeline section, so a push-triggered run pinned a failure to a head whose
body the same run was about to fix. This repo's ruleset is advisory with no
required status check, so dropping the trigger cannot wedge a merge.

Remove test/workflows/no-mistakes-gate.test.ts, which extracted and executed
the now-absent inline block, and point AGENTS.md at the shared action.

* fix: make the generated skill defer to live CLI guidance (kunchenguid#48)

* fix(skill): shrink SKILL.md to a CLI-deferring stub

Installed skills go stale when the npm package is bumped. Keep only
identity frontmatter plus pointers to live CLI help so regeneration
cannot re-inflate baked command docs.

Co-authored-by: Cursor <cursoragent@cursor.com>

* no-mistakes(review): Align skill documentation with minimal generator contract

* no-mistakes(document): Consolidate generated skill documentation

---------

Co-authored-by: Cursor <cursoragent@cursor.com>

* no-mistakes: apply CI fixes

---------

Co-authored-by: Kun Chen <3233006+kunchenguid@users.noreply.github.com>
Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Co-authored-by: Evelyn Scidmore <13389701+escidmore@users.noreply.github.com>
Co-authored-by: Kun Chen <kun-1@kunchenguid.com>
Co-authored-by: Cursor <cursoragent@cursor.com>
Co-authored-by: Chris Yuan <cyuan@hyfin.app>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant