Summary
The framework already discovers MCP prompts on connect (_mcp_prompts) but never exposes them to operators. There is also no way for an operator or tenant to add their own commands at runtime without rebuilding the agent's container image. This issue proposes two small REST endpoints and a commands/ directory convention that together give operators a first-class slash-command surface — extending the agent without code or rebuilds.
Motivation
Slash commands are how operators get leverage. Today, every gateway and UI in the stack reinvents its own command parsing (typed text matching, prefixes, autocomplete) on top of the agent's chat-completion API. That pushes operator-extensibility onto the gateway/UI layer when the right home is the agent itself — the agent already knows what MCP prompts are available, what local prompts exist, and what the session state is.
Real use cases:
- A tenant-specific shorthand:
/runbook RB-1234 → expands a tenant-specific runbook-search prompt without redeploying the agent.
- A domain workflow:
/triage <symptoms> for a healthcare triage agent, expanding to a structured triage prompt with the operator's free-text input substituted in.
- An operator UX:
/compact, /fork, /revert shortcuts for the auto-compaction and fork/revert features (separate issues), invoked from the chat surface without going to a separate API console.
- A workshop or demo: instructor pre-loads
commands/demo-step-1.md, demo-step-2.md, etc., and runs through a scripted sequence by typing /demo-step-1 etc.
Without a runtime command surface, these all require either a gateway-side lookup table (which then needs to know what each agent supports) or a rebuild of the agent image.
Proposed approach
Two new REST endpoints
GET /v1/commands — list all available commands with name, description, source (mcp_prompt | local_template | builtin), argument schema.
POST /v1/commands/{name} — invoke. Body has arguments: dict | list[str] and an optional session_id. The server expands the command into a chat-completion request and runs the agent loop.
Three command sources
- MCP prompts — already discovered by
connect_mcp() and stored in _mcp_prompts. Exposed via get_mcp_prompt() and forwarded as the user message.
- Local templates — Markdown files with YAML frontmatter under a
commands/ directory, mirroring the existing prompts/ shape. Mountable as a ConfigMap so tenants can customise without rebuilding. Substitution: $1..$N for positional arguments, $ARGUMENTS for the full argument string.
- Builtin commands —
/compact, /fork, /revert, etc., when those features are enabled. These are not file-based; they are server-side handlers.
commands/ directory shape
commands/
runbook.md # /runbook
triage.md # /triage
demo-step-1.md # /demo-step-1
A command file:
---
name: runbook
description: \"Search the runbook database by ID.\"
arguments:
- name: runbook_id
required: true
description: \"The runbook identifier (e.g. RB-1234).\"
---
Find runbook $1 and summarise the steps for the operator.
Highlight any preconditions, required permissions, and rollback steps.
The frontmatter is identical to the existing prompts/ convention, which keeps the cognitive overhead low.
Mounting at runtime
The commands/ directory is opt-in. The chart accepts a ConfigMap-mounted volume at /app/commands (or similar). When the directory exists, the server scans on startup and exposes the commands; when it does not, only MCP prompts and builtins are listed.
Open design questions
- Who can create commands at runtime. Tenant operators only? Authenticated users? The framework should accept identity from kagenti and apply policy — but the policy itself is deployment-specific. Default: read-only (commands are mounted via ConfigMap by an operator with cluster-write rights; the agent itself does not write commands).
- Composition with the gateway's command surface. If
gateway-template already parses /foo syntax, does it route to the agent's commands endpoint, or does it have its own catalog? Likely the gateway should call GET /v1/commands on the agent and forward whatever it finds. Coordinate with that repo's owners.
- Name collision between MCP prompts and local commands. If both a connected MCP server and the local
commands/ directory define a command named triage, who wins? Lean toward local-wins-with-warning, since locals are deployment-scoped and explicit.
- Argument schema fidelity. MCP prompts have their own argument schemas; local commands have frontmatter argument descriptions. Should
GET /v1/commands normalise to a common shape, or surface both as-is? Lean toward normalised shape to reduce client complexity.
- Streaming.
POST /v1/commands/{name} should support SSE streaming (same as chat completions) for operators who want to see the agent work. Easiest path: command invocation is sugar over a chat-completion call; the SSE stream is identical.
- Builtin command auth.
/fork, /revert, /compact map to existing endpoints. Should the slash command go through the same permission checks as the underlying endpoint? Yes — the slash command is a UX shortcut, not a privilege escalation.
Dependencies
Out of scope
- A command marketplace.
- Cross-agent command sharing (each agent's command surface is its own).
- A web UI for editing commands at runtime (the model is mount-via-ConfigMap; UI is
ui-template's problem if anyone wants one).
- Command parameterisation by anything other than positional /
$ARGUMENTS substitution. Richer templating belongs in MCP prompts, which already support it.
Related
Summary
The framework already discovers MCP prompts on connect (
_mcp_prompts) but never exposes them to operators. There is also no way for an operator or tenant to add their own commands at runtime without rebuilding the agent's container image. This issue proposes two small REST endpoints and acommands/directory convention that together give operators a first-class slash-command surface — extending the agent without code or rebuilds.Motivation
Slash commands are how operators get leverage. Today, every gateway and UI in the stack reinvents its own command parsing (typed text matching, prefixes, autocomplete) on top of the agent's chat-completion API. That pushes operator-extensibility onto the gateway/UI layer when the right home is the agent itself — the agent already knows what MCP prompts are available, what local prompts exist, and what the session state is.
Real use cases:
/runbook RB-1234→ expands a tenant-specific runbook-search prompt without redeploying the agent./triage <symptoms>for a healthcare triage agent, expanding to a structured triage prompt with the operator's free-text input substituted in./compact,/fork,/revertshortcuts for the auto-compaction and fork/revert features (separate issues), invoked from the chat surface without going to a separate API console.commands/demo-step-1.md,demo-step-2.md, etc., and runs through a scripted sequence by typing/demo-step-1etc.Without a runtime command surface, these all require either a gateway-side lookup table (which then needs to know what each agent supports) or a rebuild of the agent image.
Proposed approach
Two new REST endpoints
GET /v1/commands— list all available commands with name, description, source (mcp_prompt | local_template | builtin), argument schema.POST /v1/commands/{name}— invoke. Body hasarguments: dict | list[str]and an optionalsession_id. The server expands the command into a chat-completion request and runs the agent loop.Three command sources
connect_mcp()and stored in_mcp_prompts. Exposed viaget_mcp_prompt()and forwarded as the user message.commands/directory, mirroring the existingprompts/shape. Mountable as a ConfigMap so tenants can customise without rebuilding. Substitution:$1..$Nfor positional arguments,$ARGUMENTSfor the full argument string./compact,/fork,/revert, etc., when those features are enabled. These are not file-based; they are server-side handlers.commands/directory shapeA command file:
The frontmatter is identical to the existing
prompts/convention, which keeps the cognitive overhead low.Mounting at runtime
The
commands/directory is opt-in. The chart accepts a ConfigMap-mounted volume at/app/commands(or similar). When the directory exists, the server scans on startup and exposes the commands; when it does not, only MCP prompts and builtins are listed.Open design questions
gateway-templatealready parses/foosyntax, does it route to the agent's commands endpoint, or does it have its own catalog? Likely the gateway should callGET /v1/commandson the agent and forward whatever it finds. Coordinate with that repo's owners.commands/directory define a command namedtriage, who wins? Lean toward local-wins-with-warning, since locals are deployment-scoped and explicit.GET /v1/commandsnormalise to a common shape, or surface both as-is? Lean toward normalised shape to reduce client complexity.POST /v1/commands/{name}should support SSE streaming (same as chat completions) for operators who want to see the agent work. Easiest path: command invocation is sugar over a chat-completion call; the SSE stream is identical./fork,/revert,/compactmap to existing endpoints. Should the slash command go through the same permission checks as the underlying endpoint? Yes — the slash command is a UX shortcut, not a privilege escalation.Dependencies
connect_mcp(),_mcp_prompts,get_mcp_prompt()).prompts/convention (Markdown + YAML frontmatter).Out of scope
ui-template's problem if anyone wants one).$ARGUMENTSsubstitution. Richer templating belongs in MCP prompts, which already support it.Related
connect_mcp().prompts/directory convention./compactbuiltin./fork,/revertbuiltins.gateway-template— coordinate routing.