Visitar URL original
A field is load-bearing only if a later step reads it, and Deletion Completeness fires on the diff in every mode (#326) by chrislacey89 · Pull Request #333 · chrislacey89/skills · GitHub
Skip to content

A field is load-bearing only if a later step reads it, and Deletion Completeness fires on the diff in every mode (#326) - #333

Merged
chrislacey89 merged 8 commits into
prodfrom
execute-issue-326
Sep 3, 2026
Merged

chrislacey89 merged 8 commits into
prodfrom
execute-issue-326

Conversation

@chrislacey89

@chrislacey89 chrislacey89 commented Sep 3, 2026 •

Copy link
Copy Markdown
Owner

Summary

Skills in this pack write structure into GitHub issue and PR bodies: checklists, boundary maps, a context block, a review-currency stamp. Each field is a promise that some later step will look at it. This PR adds the authoring rule that makes that promise checkable, and fixes the one field where the promise was never kept.

The rule. docs/skill-anatomy.md § Prose economy already required "checkable, exhaustive completion criteria", but that bar is satisfied by a field simply rendering. A new bullet asks the question that predicts whether a field will do anything: what later step reads this, and what does it do when it does? A valid answer names a step and the act it takes, or names the human audience. A field a later step refuses to proceed without also names its scripts/test-*.sh pin. A matching line in the Minimum author checklist puts the rule where authors look.

The field where the promise failed. /execute's Deletion Completeness rung and /pre-merge's deletion-orphan checks fired only when a slice issue body contained a ### Deletes section. Readers were added and the writer never was, so the gate waited on a field nothing produced. The trigger is now the diff, which both steps already read. In author-mode and loop-mode that is git diff --diff-filter=DR --name-status "$BASE_REF...HEAD"; in reviewer-mode, where there is no local ref, it is the PR's file list from GitHub's list-files endpoint with the removed and renamed rows kept. The same query with the upstream PR's number is how a consumed upstream slice's deletions are read in any mode. ### Deletes survives as an optional hint naming which surfaces to sweep.

Why the suite grew. The git trigger is executable prose an agent copies out of a SKILL.md and runs unsupervised elsewhere, so it goes to a mechanism rather than to careful reading (CLAUDE.md § Commands a skill documents, rule (b)). test-documented-git-commands.sh now plants a deletion and a rename and runs the documented line against them, with two-dot and unfiltered mutants as negative controls, and pins that the checklist's copy of the line is byte-identical to /execute's.

This is the redo of #331. That PR was closed unmerged after an independent review found its trigger unreachable in --pr mode, a mis-cited dimension, a British spelling, restated counts, and a bullet that ended on two negations. Each is addressed in the last commit; the counts are deleted rather than corrected, because nothing here checks them.

PRD

Closes #326

Key Decisions

Review Notes

Verification commands run, each from this worktree at the head commit:

Command Exit
bash scripts/test-documented-git-commands.sh 0
every scripts/test-*.sh, run in a loop 0
bash scripts/sync-skill-references.sh --check 0
bash scripts/shellcheck-pinned.sh 0
git diff --diff-filter=DR --name-status origin/prod...HEAD (empty: this diff deletes nothing) 0
rg -i for client names over the diff (empty) 1

Local gates were not active for this branch. lefthook is not installed in this Conductor worktree, so every command above was run by hand. CI is the gate.

Skipped: Tier 2.5, 2.6 and 2.7 (runtime, non-dry path, production parity). This repo has no build, runtime, or deploy target.

Independent probe: a sub-agent that did not write this diff is dry-running the reviewer-mode trigger against live PRs. Its result is recorded in a comment on this PR, not here, so the body does not carry a claim the author wrote before the probe returned.

Review Currency

Reviewed by /pre-merge at c017a42. Commits pushed after this SHA have
not been through the review dimensions — /closeout surfaces the delta before merge.

…writes it

Adds the authoring criterion the pack was missing. "Checkable, exhaustive
completion criteria" is satisfied by write-existence — its own example is
"an issue is created" — so a new field passes the bar by rendering. Nothing
asked the question that actually predicted the outcome: what later step reads
this, and what does it do when it does.

The criterion asks for a reader that *branches or writes back*, not a checkbox
rate. Measuring a field by its tick rate is Meadows' wrong-goal trap: the
assumptions block is flat at 220/232 unchecked precisely because its reader
(/execute Step 0) gates without writing state, which is the correct design.

Human readers count. Blocked by and User Stories Addressed are named as the
informational bin so a mechanical-reader test cannot nominate them for cutting.

Refs #326 (Mediator change set item 1 and row 4).
…header nothing writes

The rung gated on the slice body containing a `### Deletes` section. Five
sites read that header — execute/SKILL.md twice, review-checklist.md three
times — and no skill in the pack ever writes it. /prd-to-issues renders
Produces, Consumes, Context, Acceptance Criteria and Assumptions, and by the
issue's Non-Goals it should not be taught to render Deletes, because that
would make reachability depend on planning-time compliance (the Context block
measures at 16 of 274 fulcrum issues).

Measured on 274 fulcrum issues: `### Deletes` appears in 0. Every one of the
five gates has been unreachable since it was written — Leveson's asynchronous
evolution, readers added and the writer never was.

The trigger is now the diff, which both steps already read:

  git diff --diff-filter=DR --name-status "$(...origin/HEAD...)"...HEAD

Verified against a scratch fixture rather than written from memory: a deleted
path prints `D<TAB><path>`, a rename prints `R100<TAB><old><TAB><new>`, and
the command exits 0 whether or not anything matched — so the prose gates on
output, not exit status. /execute carries the canonical statement and
review-checklist.md points at it; the following commit pins that the two
literals agree.

`### Deletes` survives as an optional hint naming which surfaces to sweep.

Refs #326 (Mediator change set item 2; rows 2 and 3).
Corroborated independently by
docs/solutions/architecture-decisions/deletion-unit-is-function-not-syntax-2026-08-15.md,
whose Prevention section proposed this same trigger change on a different
incident.
…st it

The trigger the previous commit installed is itself a documented command an
agent copies into someone else's repo, so it goes to the mechanism rather than
to review — CLAUDE.md § Commands a skill documents rule (b), and this suite's
own header ("Extend the suite when a skill documents another runnable command").
No new suite: #326's Non-Goals rule that out, and this shape already had a home.

Adding /execute to the census immediately found two defects in the prose the
previous commit shipped, neither visible by reading:

  1. The first draft inlined `$(git symbolic-ref … | sed …)` as the range
     endpoint — a branch NAME where only a ref is safe. That is the #298 defect
     verbatim, in prose written by someone who had just read the fix. /execute
     now carries the same detection block as the other five sites, and the same
     byte-identical **Residual:** paragraph, which it was also missing.
  2. The census's flag arm could not parse `--diff-filter=DR`, so the line
     matched nothing and dropped silently out of the endpoint check. The
     raw-`..HEAD` reconciliation is the only reason that was visible at all.

New in the suite:

  - A dedicated fixture planting one deletion, one rename, and one base-side
    ADDITION after the branch point. The main fixture deletes nothing, so it
    scores the trigger 0/0/0 — empty output there is indistinguishable from a
    broken command.
  - Three negative controls, each built by mutating the real extracted line:
    two-dot (invents a deletion for base-side work), filter dropped (the trigger
    stops discriminating and fires on any diff), and the existing bare-name one.
  - review-checklist.md is not a SKILL.md and falls outside every derived loop,
    so its copy is pinned byte-identical to /execute's canonical line. That is
    the mechanism behind review-checklist's own "same condition and same
    command" sentence.
  - The stat-triple case arm now keys on `--stat` rather than on `git diff`, and
    an unrecognised range shape fails by name instead of being scored against
    the wrong oracle.

Six mutations verified red before this landed, including reverting /execute to
the pre-#326 header gate (fatal) and dropping the filter (fatal).

Refs #326.
…half

deletion-unit-is-function-not-syntax-2026-08-15.md proposed this exact trigger
change on an unrelated incident and marked it "an /improve-pipeline candidate,
not yet filed." The previous commits filed and shipped it, so the entry now
says something false about the repo it describes.

Both halves recorded rather than one. #326's Mediator bounded the change set to
the trigger and declined the surface-list widening, so:

  - count 1 (header gate) — fixed, with the new command named
  - count 2 (surfaces are all code surfaces) — still open

The Shelf Life clause's retirement condition is a conjunction and only its first
half is met, so the entry does not retire. The clause now says so explicitly,
including the gap the wording opens: the rung fires on a diff that deletes or
renames a MODULE, which is narrower than "net-subtractive" — a prose diff that
removes a sole-site declaration without removing a file still does not trigger
it. That is this repo's own most common diff shape, and it is the strongest
candidate for a follow-up issue.

Refs #326.
…d drop the claims nothing checks

The #331 review found the new Deletion Completeness trigger reads
$BASE_REF, which Phase 1 resolves only in author-mode, so in
`/pre-merge --pr <n>` the rung could not fire: the unreachable-gate
class this branch exists to fix, one mode over. The checklist now
carries a reviewer-mode read of the same fact from the PR's file list
(GitHub's list-files endpoint, keeping `removed` and `renamed` rows),
and the same query with the upstream PR's number is how a consumed
upstream slice's deletions are read in every mode, which is the
coverage the "or an upstream slice" clause was claiming and the git
command alone did not compute.

Also from that review: the checklist cited Surgical Scope for a diff
stat that lives under Review-friendly Size (the cross-reference is
dropped rather than corrected); "recognise" in a script comment; the
anatomy bullet closed on two negations and now says what a valid
answer looks like; and the counts restated in prose and comments
("five reader sites", "0 of 274", "/prd-to-issues does not emit")
are deleted, since nothing here checks them.
… base ref, and pin the three things #333's review found unpinned

An independent probe of the reviewer-mode reach found that the
author-mode trigger, run with $BASE_REF unset, exits 0 and prints
nothing: git reads the empty left endpoint of `...HEAD` as HEAD, so
the rung's own prose reads the result as "nothing deleted, skip." The
checklist's block now opens with a `${BASE_REF:?}` guard, and the
suite runs the block both ways in the planted fixture. Writing that
guard produced its own defect first: an apostrophe inside the message
left bash looking for a closing quote, and the new assertion caught it
before it shipped.

The review's two Concerns are pinned in the same suite: the gate
sentence at both sites names the diff and not the header (reverting
it to the pre-#326 wording had left every assertion green), and the
reviewer-mode `--jq` filter, read from the checklist rather than
restated, is run against a fixture in the documented response shape.
GitHub's half of that command stays referenced to its docs.
…iew once found

Three comment lines in the new sections claimed more than the assertion
beneath them: a history of a prior review round that no commit here
carries, a pagination effect the check only establishes by presence, and
a CI runner fact nothing pins. Each now states the check it sits above.
@chrislacey89

Copy link
Copy Markdown
Owner Author

Review and probe record for this PR, kept here rather than in the body so the body carries no author-written claim about a probe that had not yet returned.

Review at f950d69 (/pre-merge author-mode, two delegated reviewers, dimensions split by the checklist's Runs in markers). Sub-agent A (Deep Modules, Vertical Slice Integrity, State Discipline, Surgical Scope, Review-friendly Size): no findings; it re-checked each of #331's six closing findings against the tree rather than the commit messages. Sub-agent B (Boundary Map Contracts, Test Quality, docs/solutions Adherence, Runtime Init, Fix Completeness; the first, fourth and fifth self-gated off): two Concerns. The gate sentence above the trigger was unpinned, so reverting it to the ### Deletes wording with the command untouched left the suite green. The reviewer-mode gh api line had no test at all.

Independent probe at f950d69 (a sub-agent that did not write the diff, dry-running the checklist's deletion trigger as /pre-merge --pr would). Verified against live PRs: the API query's removed row shape, the {owner}/{repo} placeholders resolving from the worktree, --paginate changing the file count on a 67-file PR, and the documented status enum. One defect: with $BASE_REF unset, the author-mode trigger exits 0 and prints nothing, which the rung's prose reads as a clean pass. One gap: no PR in this repo or in fulcrum carries an API renamed row, so the rename half was unverified and the mutant that drops the renamed arm survived.

Fix e447127 added a ${BASE_REF:?} guard to the checklist's block and three pins in test-documented-git-commands.sh: the gate sentence at both sites, the guard run both ways in the planted fixture, and the --jq filter (read from the checklist, not restated) against a fixture in the documented response shape. Writing the guard produced its own defect first: an apostrophe inside the message left bash looking for a closing quote, and the new assertion caught it before it was committed.

Independent re-probe at e447127 (fresh sub-agent). All ten mutations went red, including the fixture mutation that proves the renamed row is load-bearing. The renamed<TAB><old><TAB><new> shape was verified live against cli/cli#14128. Three residual overclaims in suite comments, all fixed in 462565c and c017a42 and confirmed by the same prober: a restated history of the review, a pagination effect the check only establishes by presence, and "CI has jq".

Suites: test-documented-git-commands.sh 174 passed; every scripts/test-*.sh green; sync-skill-references.sh --check clean; pinned shellcheck clean. The review stamp is at c017a42.

@chrislacey89
chrislacey89 merged commit f2e649f into prod Sep 3, 2026
5 checks passed
@chrislacey89
chrislacey89 deleted the execute-issue-326 branch September 3, 2026 11:51
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.

[improve-pipeline] A field a skill writes is load-bearing only if a later step reads or writes it — add the criterion, and fire Deletion Completeness on the diff, not a header nothing writes

1 participant