This guide explains how to create and maintain MCP tools in the CodeRide MCP server, following best practices for tool search alignment and discoverability.
- Tool Definition Overview
- Naming Convention
- Tool Description Guidelines
- Input Schema Best Practices
- Metadata Fields
- Complete Example
- Recommended Category Values
- Testing Your Tool
All tools in the CodeRide MCP server extend the BaseTool abstract class and follow a consistent structure designed for optimal discoverability by AI assistants and tool search systems.
Every tool must implement:
name: Unique tool identifier following naming conventiondescription: Clear explanation of what the tool does and when to use itzodSchema: Zod schema for runtime input validationmetadata: Optional categorization and search metadata (recommended)execute(): Tool execution logicgetMCPToolDefinition(): MCP-compliant tool definition
Tool names follow the action_target pattern for clarity and natural language consistency.
{action}_{target}[_{qualifier}]
get_task- Fetch a specific taskupdate_task- Modify task propertieslist_projects- List all projectsnext_task- Get next sequential task
✅ DO:
- Use descriptive action verbs:
get,update,list,create,delete - Use clear target nouns:
task,project,prompt - Keep names concise but unambiguous
- Use lowercase with underscores (snake_case)
❌ DON'T:
- Use generic one-word names:
run,execute,tool1 - Use abbreviations without clear meaning:
gtp,upd - Include the domain in the name:
task_get_task(usemetadata.categoryinstead)
Descriptions should follow the "what + when" pattern to maximize discoverability and usability.
description: "{What the tool does}. Use this when {when to use it / typical scenarios}."description: "Retrieves detailed information for a specific task using its unique task number (e.g., 'CRD-1'). Use this when you need to understand task requirements, check current status, or gather context before starting work on a task."✅ DO:
- Start with a concrete statement of what the tool does
- Add a second sentence explaining when/why to use it
- Use specific examples where helpful (e.g.,
'CRD-1') - Focus on user value and typical workflows
❌ DON'T:
- Repeat argument details (those belong in
inputSchemadescriptions) - Use overly generic text like "Performs operations on code"
- Write excessively long descriptions (aim for 1-2 sentences)
Input schemas should be self-documenting with clear property names and detailed descriptions.
Use descriptive, semantic property names:
✅ Good: file_path, task_number, language, test_framework
❌ Bad: f, str, arg1, x
Each property should include:
- Format specifications (e.g., 'ABC-123' pattern)
- Constraint details (e.g., max character limits)
- Usage guidance (when and why to use)
- Relationship context (how it relates to other tools/properties)
inputSchema: {
type: "object",
properties: {
number: {
type: "string",
pattern: "^[A-Za-z]{3}-\\d+$",
description: "The unique task number identifier in format 'ABC-123' where ABC is the three-letter project code and 123 is the task sequence number (e.g., 'CRD-1', 'CDB-42'). Case insensitive - will be converted to uppercase internally."
},
status: {
type: "string",
enum: ["to-do", "in-progress", "done"],
description: "The desired status for the task. Use 'to-do' for tasks that haven't started, 'in-progress' for active work, and 'done' when completed. Updating to 'in-progress' signals active work to other team members."
}
},
required: ["number"],
additionalProperties: false
}The optional metadata field enhances tool discoverability without changing MCP protocol compatibility.
interface MCPToolMetadata {
/**
* High-level functional area of the tool.
* Primarily for organization and documentation.
*/
category?: 'task' | 'project' | string;
/**
* Free-form tags to aid indexing and search.
* Example: ["typescript", "jest", "refactor"]
*/
tags?: string[];
/**
* Short guidance on when to use this tool.
* Example: "Use when you need to generate unit tests for an existing file."
*/
usage?: string;
/**
* Rough importance/visibility hint for UIs and docs.
*/
priority?: 'primary' | 'advanced' | 'internal';
}Broad functional domain of the tool. Use for grouping related tools.
CodeRide MCP Categories:
'task'- Task-level operations (get_task, update_task, list_tasks)'project'- Project-level operations (get_project, update_project, list_projects)
Searchable keywords for tool discovery (4-6 tags recommended).
Good tags:
- Action verbs:
'fetch','update','create' - Data types:
'task','project','prompt' - Operations:
'read','write','list' - Workflow:
'workflow','automation','sequence'
Practical guidance on when to use the tool (1-2 sentences).
Example:
usage: 'Use when you need to understand task requirements, check current status, or gather context before starting work on a task'Visibility and importance level.
'primary'- Common user-facing tools'advanced'- Specialized or less frequent use'internal'- Development/debugging tools
Here's a complete tool implementation following all guidelines:
import { z } from 'zod';
import { BaseTool, MCPToolDefinition, ToolAnnotations } from '../utils/base-tool.js';
import { SecureApiClient } from '../utils/secure-api-client.js';
/**
* Schema for the get-task tool input
*/
const GetTaskSchema = z.object({
number: z.string()
.regex(/^[A-Za-z]{3}-\d+$/, {
message: "Task number must be in the format ABC-123 (e.g., CRD-1 or crd-1). Case insensitive."
})
.describe("Task number identifier (e.g., 'CRD-1')"),
}).strict();
type GetTaskInput = z.infer<typeof GetTaskSchema>;
/**
* Get Task Tool Implementation
*/
export class GetTaskTool extends BaseTool<typeof GetTaskSchema> {
readonly name = 'get_task';
readonly description = "Retrieves detailed information for a specific task using its unique task number (e.g., 'CRD-1'). Use this when you need to understand task requirements, check current status, or gather context before starting work on a task.";
readonly zodSchema = GetTaskSchema;
readonly annotations: ToolAnnotations = {
title: "Get Task",
readOnlyHint: true,
openWorldHint: true,
};
readonly metadata = {
category: 'task' as const,
tags: ['task', 'fetch', 'details', 'read'],
usage: 'Use when you need to understand task requirements, check current status, or gather context before starting work on a task',
priority: 'primary' as const
};
constructor(apiClient?: SecureApiClient) {
super(apiClient);
}
getMCPToolDefinition(): MCPToolDefinition {
return {
name: this.name,
description: this.description,
annotations: this.annotations,
metadata: this.metadata,
inputSchema: {
type: "object",
properties: {
number: {
type: "string",
pattern: "^[A-Za-z]{3}-\\d+$",
description: "The unique task number identifier in format 'ABC-123' where ABC is the three-letter project code and 123 is the task sequence number (e.g., 'CRD-1', 'CDB-42'). Case insensitive - will be converted to uppercase internally."
}
},
required: ["number"],
additionalProperties: false
}
};
}
async execute(input: GetTaskInput): Promise<unknown> {
// Implementation details...
}
}Based on the current CodeRide MCP tool set:
| Category | Use Case | Example Tools |
|---|---|---|
task |
Task-level operations | get_task, update_task, get_prompt, list_tasks, next_task |
project |
Project-level operations | get_project, update_project, start_project, list_projects |
For other MCP servers, consider these additional categories:
code-edit- Code editing, refactoring, formattingtesting- Running tests, generating testsnavigation- File tree, project structure, searchrepo- Git operations, branchesai-assist- AI-assisted code generation/manipulation
Before submitting a new tool, verify:
cd /Users/federiconeri/github/coderide-mcp
npm run buildnpx tsc --noEmitEnsure your tool is registered in src/index.ts:
const tools: MCPToolDefinition[] = [
// ... existing tools
new YourNewTool(apiClient).getMCPToolDefinition(),
];Use the MCP Inspector or your preferred MCP client to:
- Verify tool appears in tool list
- Test with valid inputs
- Test with invalid inputs (validation)
- Verify error messages are helpful
- Check that metadata is exposed correctly
- Tool is listed in README.md with example
- Input schema is documented
- Example use cases are provided
All metadata fields are optional. This ensures:
- ✅ Existing tools work without modification
- ✅ Clients ignoring metadata continue to function
- ✅ No breaking changes to tool invocation
- ✅ Gradual adoption of metadata across tools
When adding new tools or updating existing ones, metadata is recommended but not required.
- Naming: Use
action_targetpattern with clear, descriptive names - Description: Follow "what + when" pattern (1-2 sentences)
- Properties: Use semantic names with detailed descriptions
- Metadata: Add category, tags, usage, and priority for discoverability
- Testing: Verify compilation, type safety, and runtime behavior
- Documentation: Update README.md with examples and use cases
- Review existing tools in
src/tools/for examples - Check the MCP specification for protocol details
- Open an issue if you need clarification on guidelines
This guide reflects the tool search alignment implementation completed in 2026-01-31, based on Anthropic's tool search best practices.