A skill is an interface between a person who knows how work should be done and an agent that has to recognize the moment, choose a path, and stop at the right boundary.
That interface can live in Markdown and still behave like code. A small wording change can alter file selection, tool use, or the definition of done. Treating the file as casual prose makes those changes hard to reason about and harder to test.
Instructions are an interface
Useful interfaces answer a few concrete questions. When does this apply? What decision does it own? Which actions are required? Which actions are out of bounds? What evidence shows that the work is complete?
Many skill files answer only the middle question. They describe a preferred technique at length but leave activation and completion vague. The agent has to infer the contract. Different sessions produce different inferences.
A contract does not mean rigid prose. It means the author has made the important boundaries inspectable.
Define the boundary
The first paragraph should help the agent decide whether to use the skill. Name the trigger in terms that can appear in the session: a task, a file shape, a failure mode, or a requested decision.
"Use for code quality" is too broad. "Use when deciding where a module boundary belongs or when a module exposes several implementation details" gives the agent something it can match.
The boundary also says what the skill does not own. An evaluation can then include positive cases and nearby cases where the correct behavior is to stay quiet.
Write observable rules
Rules should leave evidence in the trace or output. "Think carefully" cannot be checked. "Name the module and the decision it owns before proposing files" can.
Observable rules make failures diagnosable. If the agent edits provider-specific code outside the adapter, the reviewer can point to the violated boundary. If the agent never states the module decision, the trace shows the omission.
| Weak instruction | Observable contract |
|---|---|
| Keep the design clean. | Name the module and the decision it owns. |
| Avoid unnecessary complexity. | Do not add a second path unless the contract requires both. |
| Test thoroughly. | Run the narrow contract test, then the package suite. |
Examples need a job
Examples consume attention. Each one should resolve an ambiguity that a rule cannot resolve on its own. A good example shows the boundary between two plausible choices.
Do not add five examples that repeat the same shape. The agent may copy the surface details and miss the decision. One contrast between "belongs here" and "belongs behind the adapter" teaches more than a gallery of finished code.
Examples also become part of the versioned behavior. If an example contains a command, file name, or provider, include cases that reveal whether the agent copied it when it should have generalized.
Version the whole bundle
The skill file is rarely the complete instruction. Referenced documents, scripts, templates, and examples all shape the run. A fair comparison freezes the entire bundle for both versions.
Hash every file at the start of the evaluation. Record the source path and the recovery method. If the runtime loaded an installed copy that no longer exists, ask the reviewer to provide it. Do not substitute today's file and call it the baseline.
skill_bundle/
SKILL.md
references/
adapter-contract.md
scripts/
check-boundary.sh
bundle_id = sha256(path + content + mode)This gives the judgment a stable object. Months later, a reviewer can see exactly what X and Y contained.
A small contract
A practical skill contract can be short. State the trigger. Name the decision. List the non-negotiable constraints. Describe the evidence expected before completion. Link deeper material only when the task calls for it.
Then test the contract against real sessions. The goal is not to make the file longer. It is to make the agent's choices easier to predict and the failures easier to explain.