Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 8 additions & 2 deletions docs/PLUGIN-PHILOSOPHY.md
Original file line number Diff line number Diff line change
Expand Up @@ -339,7 +339,10 @@ config file or an external tool and whose manifest carries only a kill switch.
The uniform contract: the skill is named `setup`, sets `disable-model-invocation: true` — matching
upstream's own rule for the flag, "for workflows with side effects that you want to trigger
manually" ([best practices](https://code.claude.com/docs/en/best-practices), verified 2026-08-10) —
and offers `check` (read-only inspect and verify) and `apply` (idempotent configure) actions. The
and offers `check` (read-only inspect and verify) and `apply` (idempotent configure) actions. This
contract is exception class (ii) of the fleet's invocation-mode rubric
([`docs/conventions/invocation-mode/`](conventions/invocation-mode/README.md)), which owns the
default and the other reasons a skill may set the flag. The
rest of the shape is house doctrine, and says so: upstream documents native *initialization*
surfaces (below) but takes no position on a consumer-facing `setup` skill, so the `check`/`apply`
split and the criteria above rest on the reasoning given here rather than on upstream backing. This
Expand Down Expand Up @@ -491,6 +494,7 @@ doc before a second plugin adopts it. Fleet audits check conformance per row.
| Repository standards index | [`docs/conventions/standards/`](conventions/standards/README.md) |
| Skill layout contract and evals schema | `skill-quality` plugin (contract gate + bundled schema) |
| Review severity vocabulary | `review` plugin (`context/severity.md`) |
| Skill invocation-mode rubric | [`docs/conventions/invocation-mode/`](conventions/invocation-mode/README.md) |
| Seam phrasing (presence-gated fallbacks) | [`docs/conventions/seam-phrasing/`](conventions/seam-phrasing/README.md) |
| Loop-lane topology, escalation, capability tiers, loop invariants | [`docs/conventions/loop-lane/`](conventions/loop-lane/README.md) |
| Shell test-helper duplication and exit-code divergence | [`docs/conventions/shell-test-helpers/`](conventions/shell-test-helpers/README.md) |
Expand Down Expand Up @@ -553,7 +557,9 @@ per concern, cross-platform operation, and stress-testing before presentation.

Every standing instruction this marketplace ships — a CLAUDE.md line, a hook that corrects model
behavior, a skill's always-loaded listing text — is a per-session tax on every consumer, paid
whether or not the instruction ever fires. Official doctrine is explicit: "CLAUDE.md is loaded
whether or not the instruction ever fires. (Whether a skill's description enters that
always-loaded listing at all is the invocation-mode choice — owned by the rubric at
[`docs/conventions/invocation-mode/`](conventions/invocation-mode/README.md).) Official doctrine is explicit: "CLAUDE.md is loaded
every session, so only include things that apply broadly… For each line, ask: 'Would removing this
cause Claude to make mistakes?' If not, cut it," and "If Claude already does something correctly
without the instruction, delete it or convert it to a hook"
Expand Down
126 changes: 126 additions & 0 deletions docs/conventions/invocation-mode/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
# Skill invocation-mode rubric

Owner doc for choosing a skill's **invocation mode** — whether the model may invoke it
(`disable-model-invocation: false`, the fleet default) or only a human may
(`disable-model-invocation: true`). Consumed by skill authors at design time
(`playbooks:skill-authoring`), by the fleet gate (`skill-quality:check`), and by audits grading
existing skills. One home per the convention registry
([`docs/PLUGIN-PHILOSOPHY.md`](../../PLUGIN-PHILOSOPHY.md) "Convention registry"); this doc decides,
other surfaces point here.

Provenance: AI Hero course steering lane 8
([#2910](https://github.com/melodic-software/claude-code-plugins/issues/2910), 2026-08-17) —
an evidence-driven re-derivation, assuming correct neither upstream's user-invoked default
(mattpocock/skills `SKILL-MECHANICS.md`) nor this fleet's de facto model-invoked posture.

## The default, and why

**Model-invoked (`disable-model-invocation: false`) is the default.** Every exception must name
one of the three classes below. The key is written **explicitly** on every skill — the official
default for an absent key is `false` (docs table row, code.claude.com/docs/en/skills, verified
2026-08-17), but an explicit key makes the choice auditable and is enforced by a
`skill-quality:check` criterion.

Evidence behind the default (verified 2026-08-17 against current official docs unless noted):

- **A `true` skill is model-invisible everywhere.** `disable-model-invocation: true` removes the
skill from Claude's context entirely — the description never enters the listing, no other
skill can reach it mid-session, subagent preload is blocked, and (v2.1.196+) scheduled-task
prompts cannot name it. Only the human `/name` path remains. Hiding a skill from the model is
therefore a *total* trade, not a listing-budget optimization.
- **Surface coverage:** Claude desktop/web surfaces drop user-invoked skills from the listing
(upstream issue mattpocock/skills#693) — a user-invoked default would make skills invisible on
those surfaces.
- **Cloud scope:** remote sessions never load `~/.claude` user scope; project/marketplace skills
are the only steering that reaches cloud sessions, so marketplace skills carry the full
discoverability burden there.
- **Multi-repo product:** consumers do not memorize 200+ skill names; model-side discoverability
is part of what this marketplace sells. This inverts upstream's solo-operator premise.
- **Listing budget is manageable, not a forcing function:** every skill name is always listed;
only descriptions are dropped (least-invoked first) under the ~1%-of-context budget
(`skillListingBudgetFraction`), with a per-entry cap (`skillListingMaxDescChars`, 1,536 chars).
The per-skill `skillOverrides: "name-only"` lever reaches project/user skills only — plugin
skills are explicitly exempt ("Plugin skills are not affected by `skillOverrides`. Manage
those through `/plugin` instead"), so for this marketplace's fleet the applicable levers are
trimming descriptions at the source and plugin enablement via `/plugin`.
`skill-quality:check listing-budget` is the standing measurement instrument.

## Exception classes (the only reasons to write `true`)

1. **(i) Side-effect / manual-timing workflows.** The skill mutates state whose timing must be a
deliberate human choice (fleet sync, batched deletion, machine-level session control), or its
triggering signal is private to the human (e.g. `discipline:wait-what` — only the human knows
comprehension broke), or it enters a persistent session-consuming mode the human should choose
deliberately (e.g. `education:teach`).
2. **(ii) Setup skills.** Per the PLUGIN-PHILOSOPHY setup contract ("Setup is explicit and
repeatable"): `setup` skills are named `setup` and carry `disable-model-invocation: true`.
3. **(iii) Maintainer-only skills.** Operate on this marketplace's working tree (vendored-content
sync, drift checks); meaningless or harmful for consumers to reach via the model.

A skill claiming `true` under none of these classes is wrongly graded: flip it to `false` (or make
the case for a new class *in this doc* first — the class list, not the skill, is the unit of
extension).

## The invocation-reach invariant

A `disable-model-invocation: true` skill **cannot be invoked by any other skill** — cross-skill
reach requires model invocation. CONFIRMED against current official docs 2026-08-17 (see the
tracked strand in [`docs/upstream/mattpocock-skills.md`](../../upstream/mattpocock-skills.md)).
Consequences: any skill another skill chains to MUST be `false` (this is the rubric's
cross-skill-reach axis), and no skill body may instruct model invocation of a `true` target —
the audit-side trigger that guards this lives in the SSOT strand.

## Splitting by invocation

When one skill serves both an autonomous-reach audience and a manual-timing audience, split it so
each half takes its honest mode (upstream's "splitting by invocation", adopted via this rubric).
The write-side authoring skill (`docs-hygiene:write-for-agents`, #2962) points here for its
when-to-split doctrine.

## Router-skill verdict: REJECTED (2026-08-17)

Upstream's router pattern — a model-invoked skill whose job is routing the agent to user-invoked
skills — is rejected for this fleet: under the model-invoked default, the always-in-context
listing already does that job, and this fleet's `true` set is *deliberately* model-invisible, so
a router reaching into it would defeat the exception classes. The human-side cognitive-load
problem is answered by `docs/SKILL-CHEAT-SHEET.md` and `claude-ops:inventory`.
**Carve-out:** domain-scoped *composition* routers (`discipline:sweep-all` — membership derived
from corrector metadata) are a distinct, admitted pattern; they compose model-invoked skills
rather than recovering discoverability for hidden ones.

## Fleet grade — 2026-08-17 (ADR 0005-bounded)

Bounding question: *do the 10 non-setup `disable-model-invocation: true` skills fall into an
exception class?* (Fleet measurement, re-counted 2026-08-17 at the chain-close merge: 215
top-level skills = 141 `false` / 17 missing key / 57 `true` = 47 `*:setup` + these 10. The 47
setup skills are class (ii) by contract; the 141
`false` skills conform to the default and are not swept, per
Comment thread
kyle-sexton marked this conversation as resolved.
[ADR 0005](../../adr/0005-bound-instruction-surface-work-by-question-not-population.md).)

| Skill | Class | Verdict |
|---|---|---|
| `claude-ops:lanes` | (i) machine-level session mutation, manual timing | KEEP `true` |
| `claude-ops:plugins` | (i) mutating fleet sync | KEEP `true` |
| `discipline:wait-what` | (i) trigger is human-internal | KEEP `true` |
| `disk-hygiene:clean` | (i) destructive-capable, manual-only by design | KEEP `true` |
| `dometrain:sync` | (iii) maintainer-only | KEEP `true` |
| `education:teach` | (i) deliberate mode-entry, persistent coaching state | KEEP `true` |
| `firecrawl:update` | (iii) maintainer-only | KEEP `true` |
| `planning:questionnaire` | none — no side effects, not setup, not maintainer-only | **FLIP → `false`** (filed as [#2969](https://github.com/melodic-software/claude-code-plugins/issues/2969)) |
| `playbooks:update` | (iii) maintainer-only | KEEP `true` |
| `repo-fleet-hygiene:apply` | (i) mutating fleet apply incl. branch deletion | KEEP `true` |

The 17 missing-key skills are normalized to explicit `false` (all sit in the default class) —
filed with the enforcement criterion as
[#2968](https://github.com/melodic-software/claude-code-plugins/issues/2968) rather than edited
in-lane.

## Cross-references

- PLUGIN-PHILOSOPHY: setup contract (class ii source), Instruction economy (listing-cost
doctrine), Convention registry (this doc's row).
- `skill-quality:check`: `listing-budget` (measurement) and the explicit-key criterion
(enforcement, filed as #2968).
- `playbooks:skill-authoring`: authoring-time pointer here (filed as #2968).
- Steering-lane provenance and lesson decision rows:
`docs/upstream/aihero-steering-lanes.md` (lane 8).
Loading