"Use when creating a skill for this kit, editing one, or deciding whether a wording change to a behavior-shaping skill will actually change behavior. Also use when amending curated prose the kit ships: a skill, an agent charter, the output style, a README, a plan doc, or a doc under docs/. Triggers: adding a new SKILL.md, reworking a skill's rules, correcting a claim a curated document states, a skill that reads well but agents ignore under pressure, or a kaizen change to the kit's own skills."
Resources
1Install
npx skillscat add sapplefeld/claude-kit/writing-skills Install via the SkillsCat registry.
Writing Skills
A skill is behavior-shaping prose, not documentation. If it does not change what an agent does under pressure, it is decoration.
When to Create a Skill
- Create when the technique is non-obvious, recurs across efforts, and is general. A single project's convention goes in that project's CLAUDE.md.
- Do not create for a one-off, a restatement of standard practice, or anything a hook or regex can enforce. Automate the mechanical and keep skills for judgment.
- The kit stays lean. A new skill must beat one more paragraph in an existing skill. When in doubt, fold it in rather than add a file.
- The size budget is a ledger rather than a ceiling. In the kit's own repository,
test/size-budget.jsonholds the caps andtest/size-ratchet.test.jsmakes growth visible, not forbidden. A file that grows raises its cap in the same change, and one that shrinks lowers it. Move the caps withnode <plugin-root>/scripts/kit-size.js sync --repo <the project's root> <path>..., naming the files the change touched. A new curated file, tracked or not, gets its first cap the same way. The bare form with no paths moves every cap and belongs to an audit over a clean tree. The net is read on the Chapter's Delta line. A raise is never a finding by itself, and a reviewer weighs only whether the added words earn their place. A rewording takes the shrink where one is available.
Anatomy
- One SKILL.md in the kit's voice: direct, opinionated, anti-dogma. Add a reference file only when the body outgrows the kit's other skills, gated the way csharp-style and sql-style gate theirs.
- Frontmatter: always quote the description.
nameanddescriptionare the two fields that matter. - Body: the principle, the rules that carry judgment, the antipatterns. Tables and lists for what gets scanned, prose for the why. A flowchart only for a decision the agent might genuinely get wrong, never for linear steps.
- One owner per rule. The doctrine's one-owner bullet (
skills/operating-instructions/SKILL.mdunder the kit plugin root) owns the principle and the forms a mention may take. The ownership map it names gives each moment's owner. When editing a rule, grep its key phrases across the kit and fix the owner, not the nearest copy. - The plan-doc header and structure belong to
curating-docs/SKILL.md's "Plan Doc Machine Contract" section. Point at it rather than restating any of its lines.
Description Field
The description is how a future session decides whether to load the skill. Write it as "Use when..." plus the symptoms that pull it in, and stop. Do not summarize the skill's process there.
Rule Forms by Failure
Name the failure first, then pick the form that fixes it. The form that fixes one failure backfires on another.
| What fails? | What fixes it? | What backfires? |
|---|---|---|
| Knows the rule, skips it under pressure | Prohibition, rationalization table and red-flags list | Soft "prefer..." guidance |
| Complies, but the output is wrong-shaped (bloated, buried, restated) | Positive recipe: what the output IS, its parts in order | Prohibition list ("don't restate") |
| Omits a required element | Structural slot: a REQUIRED field in the template it fills | Prose reminder near the template |
| Behavior should depend on a condition | Conditional on an observable predicate ("if the brief exists, reference it") | Unconditional rule plus exemption clauses |
Three rules govern any rule you write:
- No nuance clauses. "Don't X unless it matters" reopens the negotiation. Write a real exception as its own conditional on something observable.
- Exemption clauses do not scope. Where part of the output must be exempt, restructure so the rule cannot reach it.
- Close every enumeration with its class. Where the list ends, state its class ("the table is instances, not the boundary"; "the set is closed"), so a novel variant meets the rule.
Checkable Facts
- Of two true framings of a fact, ship the one the reader can verify from where they sit. Name the file, command, observable event or artifact the fact lives in, and pick the framing that makes it findable.
- A list drawn from observed instances is stated as open unless a contract closes it. Closure comes from a contract (a schema, an enum, a validated surface with a published shape), never from the sample agreeing with itself. So write the list as open and say what would close it, or cite the contract that already does.
Those two are instances rather than the boundary. Any fact a rule rests on that the reader cannot check, or whose edges they cannot see, is inside the rule.
What a Sentence Must Earn
Whether a sentence belongs at all is the doctrine's call, in its "Documents ship the current state; the journey lives in git" bullet. How an accepted lesson enters standing prose is the kaizen skill's disposition step (skills/kaizen/SKILL.md under the kit plugin root): the owning passage is rewritten with the lesson in mind, never appended to. The bars below shape the surviving sentences at authoring, read over that rewrite's result.
Curated prose in the kit's own voice meets three sentence-shape bars:
- One idea. A sentence is one idea, about twenty words. A rule and the bound that limits it are two sentences, the bound right after the rule. They share one sentence only where the split would leave the rule readable alone. A count past twenty is the diagnostic that finds a second idea, not the bar itself. Uniform length is its own defect, so the count is read per sentence and never as a target. A paragraph makes one point, or says why its parts must be read together.
- The literal phrase. Where a literal phrase for the thing exists, the sentence uses it. A metaphor stands only where it is the established term. Elsewhere it is mannered prose: metaphor and flourish in place of direct statement, written to display the writer, carrying connotations the writer did not choose. The fix is the literal phrase. The packed sentence, the nested qualification and the reasoning-first order are the same defect in other shapes, and the doctrine's plain-prose bullet names each.
- A pointer where another site owns the rule. Anatomy's one-owner rule points at the doctrine's bullet for the forms a mention may take. This bar adds no form and no exception.
The three are instances of one class: prose that costs the reader more to read than it changes for them. A form none of them names is inside the bar.
Correcting a Curated Claim
When an amendment corrects a claim a curated document states, the edit unit is the paragraph, never the sentence. Re-derive the whole paragraph from the corrected claim. Then check the claim's other carriers: the neighbouring clauses that qualified or restated it, and any sibling surface stating the same behavior. The unit is the claim on every surface carrying it, whether or not anything here names that surface. Carriers this kit keeps producing include a doctrine parity copy, the output style's register block, an agent charter, a test's assertion message, a memory record and a README's payload map, and that list is not the boundary. An amendment that corrects no claim, such as a typo fix, an added bullet or a label rename, takes whatever edit it needs.
An insertion anchored on a block's tail, or on the next entry's first line, restores every byte of that anchor in the replacement. It then re-greps the neighbour's lead-in, with a control at HEAD proving the pattern matches the intact form.
A carrier on another surface is not automatically yours to edit in place. The four dispositions below are instances rather than the boundary, and a carrier fitting none is named as such and routed deliberately, never edited in place by default.
- Where the one-owner rule applies, fix the owner rather than the nearest copy.
- A deliberate byte-identical set lands every copy in one edit or none. A partial edit reds the parity pin by design. The set is as large as the pin says, not the pair you first thought of.
- A deliberate restatement across surfaces the section's scope already covers lands on all of them in the same edit.
- A carrier in a file the section's
Files in scope:never listed takes the fix-round step's route inskills/executing-work/SKILL.mdunder the kit plugin root, never an in-place edit.
The rule binds every writer amending curated prose. Assume no downstream backstop, since what stands downstream differs by surface. Which pass reads which surface is finishing-work's and executing-work's to state (skills/finishing-work/SKILL.md and skills/executing-work/SKILL.md under the kit plugin root).
Testing a Skill
An untested skill is a guess. Test it by watching an agent's behavior with and without the wording:
- RED: give a fresh subagent a realistic task that tempts the failure, without the new guidance. Watch it fail and record the rationalization verbatim. If it does not fail, there is nothing to fix, so stop.
- GREEN: add the minimal guidance for that specific failure, and re-run until the agent complies.
- REFACTOR: counter each new loophole and re-run until it holds. For discipline rules, combine pressures such as time, sunk cost and authority, since single pressures are weak tests.
Run several reps, since one sample lies. Read every flagged result yourself, since template echoes masquerade as both failures and successes. This standard covers any change to behavior-shaping content, the kit's own skills included.
Probe Runner Pair
In the kit's own repository, a change to a passage a probe's scenario turns on, in a file that probe's shape under test/probes/ names, runs the probe runner's before-and-after pair. Match the changed and untracked paths since the before leg's <sha> against the shapes' files: lists, then the changed hunks against those probes' scenarios. A hunk no scenario turns on runs nothing, and that is recorded where the reading is.
For a ruled probe, the pair stands in for the reps above as the RED and GREEN. For a proposed probe, only the after leg runs, recorded as evidence for the operator's rulings batch, and the reps still run. A before leg that matches is not step 1's nothing-to-fix case.
A pair reads exactly one of four ways. A match on a moment the change did not mean to move is a reading that held. A before-leg mismatch the after leg matches is the repair. A mismatch both legs carry is the corpus's, recorded as such. An after-leg mismatch the before leg lacks takes the intent test, as does a match on a moment the change meant to move, which is a finding rather than a reading that held.
An errored or unparsed pair, or one with a leg recorded unavailable, is none of these and is re-run as finishing-work's step 6 directs. If it errors again it stands in for nothing, and the reps run. A designed shape's rows and a designed-agreed row are none of these either and take step 6's dispositions. Rows from a shape naming no changed file are no reading at all.
The before leg is node tools/probe-corpus/run.mjs --only <moments> --before <sha>. The after leg is the same command without --before. The after leg's <moments> is every moment the check above kept, comma-joined, and the before leg's is that list narrowed to the ruled ones. <sha> is the parent of the change's first commit resolved to a sha, or HEAD for an uncommitted change. A root-commit change takes the <sha> finishing-work's pre-step-1 derivation yields, which leaves the before leg unrun as step 6 records it.
The pair runs once at the section's close over its whole change, never at each fix round. Inside a finishing pass, only finishing-work's step 6 runs the set. tools/probe-corpus/README.md owns what each leg reads, in its "What the runner reads" section, and what each row status means. Finishing-work's step 6 owns the run's process standing, how it is spawned, when a leg is re-run and what each row counts for.
The intent test covers a ruled probe's after-leg mismatch the before leg lacks. A move the change intended is a re-ruling to ask the operator for, and any other is a finding.
A change whose only shape-named files are the repo's home/*.md files is seen by neither leg, so it takes the reps with the cache staging below. A matching leg pair is one sample. Read the raw replies the runner keeps as you read flagged results. Record the reading, or both where a pair ran, on the line executing-work's Chapter template holds for it in Decisions / Surprises, or in the close-out status where no section Chapter exists.
Doctrine Probes
A doctrine edit is invisible to same-session subagents. A GREEN probe for a doctrine change runs in a fresh session (a headless claude -p), never as a subagent of the session that made the edit. Do not stage probe wording in ~/.claude/claude-kit-doctrine.md. Where the probe pair does not supply the GREEN, stage the candidate wording in the installed plugin cache's copy of the operating-instructions skill for the probe run and restore it after. The real change ships through the normal commit and goes live when the plugin updates.
Doctrine-adjacent rules have a contaminated RED. Where the harness's subagent inheritance is off, a RED is genuine. Where it is on, the contamination is production-faithful rather than a test defect. Absence of failure there is weak evidence, not proof the rule is dead weight. Judge such a rule on its distinct value: point-of-action encoding survives compaction and reaches contexts the doctrine does not (a headless worker mid-loop, a session whose doctrine was summarized away). If you ship a rule whose RED did not reproduce, record that it stands on that rationale, not on a demonstrated failure. A rule with neither a reproduced RED nor that rationale is the guidance-from-imagination antipattern, so leave it out.
Antipatterns
- A narrative ("the time we fixed X") instead of a reusable technique.
- A harness-injection fact stated as unconditional ("subagents load X") when it hinges on a user setting. A settings flip falsifies it silently, and no test catches that. State the safe assumption, and where the fact must be stated, name the setting it depends on.
- Guidance written from imagination instead of an observed failure.