Prompts have names, descriptions, and argument schemas
Why it matters
Prompt templates without argument definitions leave clients guessing at what inputs to supply. A prompt named review with no description gives the client no basis for surfacing it to the user at the right moment or pre-filling arguments. Duplicate prompt names cause non-deterministic selection. These failures map directly to MCP Spec noncompliance: the prompts/list response becomes misleading, and clients that rely on argument descriptions to build UI will silently omit required context.
Severity rationale
Medium because undescribed or argument-free prompts degrade discoverability and usability without causing immediate security or data failures.
Remediation
Add a description and a Zod argument schema to every server.prompt() registration.
// src/prompts/index.ts
server.prompt(
'review-code',
'Generate a targeted code review for a specific file. Focuses on bugs, security issues, and style violations.',
{
filePath: z.string().describe('Path to the file to review relative to project root'),
focusArea: z.enum(['bugs', 'security', 'style', 'all']).optional()
.describe('Area to focus on; defaults to all'),
},
async ({ filePath, focusArea }) => ({
messages: [{
role: 'user',
content: { type: 'text', text: `Review ${filePath} for ${focusArea ?? 'all issues'}...` }
}]
})
)
Detection
-
ID:
prompt-templates -
Severity:
medium -
What to look for: Count all prompt templates defined in the server. Enumerate which have complete argument definitions vs. which lack them. Examine all prompt registrations (
server.prompt()or prompt handler definitions). Check that each prompt has aname, adescriptionexplaining when to use it, and anargumentsarray withname,description, andrequiredfields for each argument. Check that promptGetPromptResultreturns well-structured messages with appropriate roles. -
Pass criteria: Every registered prompt has a descriptive name, a description explaining its purpose, and properly defined arguments with names, descriptions, and required flags. At least 90% of prompt templates must have argument definitions with descriptions.
-
Fail criteria: Any prompt is missing a description, or arguments lack descriptions, or the prompt name is vague or duplicated.
-
Skip (N/A) when: The server registers no prompts (tool-only or resource-only server). All checks skip when no MCP server is detected.
-
Cross-reference: For tool descriptions that complement prompts, see
tool-descriptions. -
Detail on fail:
"Prompt 'review' has no description — clients cannot determine when to suggest it. Argument 'code' has no description — unclear whether to pass a file path, code snippet, or diff"or"Prompt 'summarize' and 'summary' appear to do the same thing — consolidate into one" -
Remediation: Prompts are reusable templates that clients can offer to users. Make them discoverable:
// src/prompts/index.ts — prompt with arguments { name: "summarize", arguments: [{ name: "text", description: "Text to summarize", required: true }] }server.prompt( 'review-code', 'Generate a code review for a specific file, focusing on bugs, security issues, and style', { filePath: z.string().describe('Path to the file to review'), focusArea: z.enum(['bugs', 'security', 'style', 'all']).optional() .describe('Area to focus the review on, defaults to all'), }, async ({ filePath, focusArea }) => ({ messages: [{ role: 'user', content: { type: 'text', text: `Review ${filePath} focusing on ${focusArea ?? 'all areas'}...` } }] }) )
External references
- external · mcp-spec-prompts — MCP Specification — Prompts
Taxons
History
- 2026-04-18·v1.0.0·Initial import from mcp-server·automated