[FEATURE] Support disable-model-invocation in agent frontmatter (plugin agents load descriptions unconditionally)

Open 💬 0 comments Opened Jul 14, 2026 by uwuclxdy

Preflight Checklist

  • [x] I have searched existing requests and this feature hasn't been requested yet
  • [x] This is a single feature request (not multiple features)

The closest prior request is #63116, which asked for exactly this. It got the stale label on 2026-06-14 and the author closed it himself on 2026-06-22, with no maintainer response on the thread. Re-filing with a current repro on v2.1.209 rather than reopening someone else's issue.

Problem Statement

Skills can opt out of automatic invocation with disable-model-invocation: true. The description then stays out of context entirely and the skill remains reachable through /name. Agents have no equivalent. Every agent in an enabled plugin loads its description into the system prompt on every request, whether or not it is ever selected by description matching.

That is a real cost for plugins whose agents are invoked by name rather than discovered. I maintain a plugin that ships 13 agents. Its rendered agent block is 3,056 characters, roughly 740 tokens (tiktoken cl100k_base gives 741, o200k_base gives 744, so Claude's tokenizer will land near there). That is paid on every request in every session with the plugin enabled.

The asymmetry is the part that is hard to work around. Skills and agents are both selected by description matching and both carry the same context cost, but only one of them can opt out.

Proposed Solution

Support disable-model-invocation: true in agent .md frontmatter, with the semantics it already has for skills:

  • the description is not loaded into context
  • Claude does not auto-select the agent
  • the agent stays invocable by explicit name, via @plugin:agent-name and via the Agent tool when a skill or another agent names it
---
name: probe-agent
description: Runs commands, returns a pass/fail probe. Never mutates.
disable-model-invocation: true
---

Alternative Solutions

Each existing lever has either the wrong granularity or the wrong owner:

| Lever | Why it doesn't cover this |
|---|---|
| defaultEnabled: false in plugin.json (v2.1.154+) | Plugin granularity. Shipping 13 opt-in agents means 13 marketplace entries and 13 manual enables, which is worse for users than one enabled plugin. |
| permissions.deny: ["Agent(name)"] | User-side. A plugin author can't ship it as the default. |
| Plugin root settings.json | Reads only agent and subagentStatusLine, so a plugin can't gate its own components. |
| skillOverrides | Skills only. Per the docs it doesn't apply to plugin skills either. |
| Trimming descriptions | Degrades the matching that the auto-selected agents in the same plugin depend on. |

Priority

Medium - Would be very helpful

Feature Category

Configuration and settings

Use Case Example

  1. A plugin ships a mix of agents: a few meant for Claude to pick up automatically, plus several internal ones that are always spawned by name from a skill or an orchestrator agent.
  2. Today all of them advertise. The internal ones can't be usefully selected, but they cost context on every request and they dilute selection for the ones that should match.
  3. With the flag, the internal ones get marked disable-model-invocation: true, drop out of the system prompt, and stay spawnable by name.

Additional Context

Current agent frontmatter surface, for reference: name, description, model, effort, maxTurns, tools, disallowedTools, skills, memory, background, isolation (https://code.claude.com/docs/en/plugins-reference). No field covers this.

Version 2.1.209, Linux.

🤖 Generated with Claude Code

View original on GitHub ↗