Diffing each retrofitted SKILL.md against its replacement references/ files found rules that existed on main and now existed nowhere — relocated in intent, deleted in fact. A trim that loses a rule is not progressive disclosure, it is data loss with a smaller word count. Three had no survivor. The least-privilege guidance for `tools` kept its mechanics and lost the "restrict to what the agent needs" half, so the remaining text read as encouragement to omit the field. The improve flow lost its regression check, so nothing compared the closing audit against the pre-edit state and a PASS quietly becoming a SUGGESTION went unnoticed — restored on both halves of the author pair, since agent-author had dropped its equivalent too. And agent bodies lost "would the agent get this wrong without it?", which mattered more than it looks: ADR-0020 deliberately sets no body word gate for agents, three of the four already sit between 933 and 1,199 words, and the delegation check only fires on procedure a skill already owns. That heuristic was the only brake left. Two more were reachable only from the wrong scope. agent-author tells the reader to load only the file for the resolved scope, but the mcp__ glob syntax for disallowedTools and the five tools no subagent ever receives had both landed in project-user-scope.md. disallowedTools is the ONLY permitted fence at plugin/APM scope, so the scope that needs the syntax most could not reach it, and a plugin-scope run could write a body telling the agent to ask the user a question. Two documents were actively wrong rather than merely thin. agent-audit told auditors that validate.sh resolves boundary targets for skills only; it runs at both scopes, so the auditor was hand-resolving what the script had already decided and could contradict it. And skill-audit routed to its script-troubleshooting reference whenever validate.sh "fails" — but it exits 1 on ordinary content FAILs, the normal outcome for the whole #99 population, so 1,302 words loaded on nearly every audit. A context-budget regression inside the skill that enforces the context budget. Finally, two illustrations taught the shape the gate ERRORs on, unfenced, while an adjacent rubric called it a hard ERROR. LESSONS.md records the reference-chain depth rule flipping from "one level deep" to "two hops, never three". ADR-0020 is silent on it and the reversal rode entirely on the diff; the looser rule is what mandatory dispatch requires. Refs: #99 ADR: 0020 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_015W3iwF9ncfRZddGBxsMCYi
skill-author
Author and refine skills conforming to the agentskills.io specification — create new skills from scratch or apply improvement signals to existing ones.
What it does
Routes to one of two flows based on context: if no skill directory exists at the target path, it scaffolds the directory from annotated templates, fills in SKILL.md and supporting files, and validates the result. If an existing skill directory and improvement signals are both present, it groups those signals by root cause and applies targeted edits, then re-validates. In both flows, bumps the skill's metadata.version when present (minor for create, patch for improve).
SKILL.md itself carries only the dispatch table, the invocation-axis decision, the contract gates and the shared close; each flow lives in its own self-contained reference file, per ADR-0020.
The contract it teaches
Authored skills are held to the ADR-0020 context budget. A description carries a trigger clause, at most one capability clause, and a boundary clause of the form Not <thing> -> <skill-name> whose target must resolve to a real skill or agent — 250 characters target, 400 hard ceiling. A body carries the decision procedure only — 600 words target, 900 hard ceiling, counting the body alone, which is a separate measurement from the 2,770-word / 500-line whole-file spec backstop. Skills with two or more mutually exclusive flows must dispatch. references/contract.md holds the full rules; assets/templates/SKILL.md encodes them as a fill-in skeleton.
Before a description is written, the skill asks whether the target is model-invoked or hand-invoked. A hand-invoked skill sets disable-model-invocation: true and carries one plain human-facing sentence with no trigger list.
Before you start
- Run
/grill-meto resolve design decisions before creating a new skill - Collect domain research, examples, and constraints
- Know the skill name (kebab-case) and destination path
Placement
scripts/new-skill.sh resolves the mode automatically by walking up from the given path — see references/create.md Step 1 for the full algorithm.
| Mode | Path | Chosen when |
|---|---|---|
| Standalone | <path>/<name>/ |
No apm.yml with a top-level type: field is found walking up from <path>, before hitting .git or the filesystem root |
| Package (APM) | <package-root>/.apm/skills/<name>/ |
A type-bearing apm.yml is found at or above <path> — <path> just needs to be somewhere inside the package |
If the destination resolves inside an APM package, read references/deployment-modes.md — self-containment rules apply to apm compile output the same way they applied to plugin cache isolation.
Usage
/skill-author
Files
| File | Purpose |
|---|---|
README.md |
Human-readable overview of the skill and its files |
SKILL.md |
Skill instructions for agents |
scripts/new-skill.sh |
Walks up from the given path to resolve package vs standalone mode, then copies annotated templates to the resolved destination |
references/create.md |
The create flow end to end — prerequisites, package-intent gate, scaffold, frontmatter, scripts, references, sources (loaded on demand) |
references/improve.md |
The improve flow end to end — signal verification, root-cause grouping, announcement, edits (loaded on demand) |
references/contract.md |
The ADR-0020 description and body contract, the Gotchas constraint, the two size gates, body patterns, and org-policy embedding (loaded on demand) |
references/retrofit.md |
Bringing a pre-ADR-0020 skill into contract — ordered cut procedure, the mutually-exclusive-flows test, reference-file conventions, the collateral checklist, and a worked description retrofit (loaded from the improve flow when a budget is exceeded) |
references/deployment-modes.md |
APM package vs standalone differences and self-containment/cache-isolation rules (loaded on demand) |
references/scripts.md |
Package runners, inline dependency patterns, and full script contract (loaded on demand) |
references/sources.md |
Upstream research sources and which skill files each contributed to |
assets/templates/SKILL.md |
Annotated SKILL.md template — emits an ADR-0020-compliant description and body skeleton |
assets/templates/README.md |
Annotated README template for the new skill |
assets/templates/scripts/README.md |
Placeholder for bundled scripts |
assets/templates/references/README.md |
Placeholder for reference docs |
assets/templates/references/sources.md |
Sources provenance template for new skills |
assets/templates/assets/README.md |
Placeholder for static assets |
assets/templates/tests/README.md |
Placeholder for test files |
tests/new-skill.bats |
(source-only) Bats test suite for scripts/new-skill.sh |
tests/README.md |
(source-only) Setup instructions for bats-support and bats-assert test dependencies |
Rows marked (source-only) exist in the authoring source (.apm/skills/skill-author/) but are
not present in an installed plugin: scripts/sync-plugin-content.sh strips
<category>/<name>/tests when it generates the flat mirror, because these are dev-time fixtures no
plugin host needs to discover (ADR-0017). Run them from a repo checkout, not from an install. The
assets/templates/tests/README.md row above is not source-only — the exclusion is depth-scoped
to <category>/<name>/tests, so the scaffolding template tree ships intact, which
scripts/new-skill.sh depends on at runtime.