Prompts
Prompts are user-controlled instruction templates that enable structured, consistent interactions through parameterized workflows.
For the complete documentation index, see llms.txt. Markdown variants of every page are available by appending .md to the URL.xmcp detects files under the /src/prompts/ directory and registers them as prompts. This path can be configured in the xmcp.config.ts file.
The prompt file should export three elements:
- Schema: The input parameters using Zod schemas.
- Metadata: The prompt's identity and behavior hints.
- Default: The prompt handler function.
If you're returning a string or number only, you can shortcut the return value to be the string or number directly.
We encourage to use this shortcut for readability, and restrict the usage of the content object type only for complex responses, like images, audio or videos.
Multi-message prompts
Return a PromptMessage[] to provide a conversation, such as examples followed
by a new question. Each message must have a user or assistant role and a
content object. xmcp validates every message and preserves their order and roles.
metadata.role only applies when returning a single content object, string, or
number; its default remains assistant.
Return a full GetPromptResult when you also need a description or result
metadata. Both types are available from xmcp, and async handlers can return
either shape.
Messages can contain text, images, audio, resource links, or embedded resources.
An invalid result throws an error identifying the field, such as
messages.1.role. Empty message arrays are allowed. Full results retain their
description and metadata.
The HTTP transport example
includes a runnable classify-sentiment prompt and a request to try it.
References
Schema (optional)
The schema object defines the prompt's parameters with:
- Key: Parameter name.
- Value: Zod schema with
.describe()for documentation and prompt inspection. This will be visible through the inspector. - Purpose: Type validation and automatic parameter documentation.
This is the exact same as the schema object for tools.
Metadata (optional)
The metadata object provides:
- Name: Unique identifier for the prompt
- Title: Human-readable title for the prompt
- Description: Brief explanation of what the prompt does
- Role: The role for single content, string, or number returns. Can be either
userorassistant; defaults toassistant. Message arrays and full results use each message's explicit role.
Icons, tags, and availability
PromptMetadata accepts optional icons, tags, and enabled fields:
Icons are forwarded to MCP clients. Each icon requires src (a URL or data URI)
and may include mimeType, sizes, and theme ("light" or "dark").
Tags appear in listings under _meta["xmcp/tags"]; other metadata is preserved.
When both tags and _meta["xmcp/tags"] are supplied, tags takes precedence.
Tags alone do not change availability. Use
component visibility rules to include or exclude
components by name or tag in xmcp.config.ts.
Prompts are enabled by default. Set enabled: false to skip registration: the
prompt is absent from prompts/list, and prompts/get returns a not-found error.
Custom metadata._meta values are also exposed in prompts/list.
Availability is evaluated during server setup; modules are still imported. Rebuild and restart the server after changing metadata in production.
The HTTP transport example demonstrates icons, tags, and a disabled experimental tool.
Implementation (required)
The default export function that performs the actual work.
- Parameters: Automatically typed from your schema using the built-in
InferSchema. - Returns: A string, number, content object,
PromptMessage[], or fullGetPromptResult. - Async: Supports async operations for API calls, file I/O, etc.
Troubleshooting
Prompt Loading Errors
When xmcp starts, it loads every file under your prompts directory.
- Empty prompt files are skipped with a friendly warning
- Files without a
defaultexport are skipped with a friendly warning - Real syntax or import errors still fail normally so you can see the full stack trace
For example, if src/prompts/draft.ts is empty, startup will log:
If the file exists but does not export a default handler, startup will log:
Friendly handling is intentionally limited to empty files and missing default exports. Invalid implementations and real import/syntax errors still surface as normal runtime errors.
