UNPKG

bottlenecks-mcp-server

Version:

Model Context Protocol server for Bottlenecks database - enables AI agents like Claude to interact with bottleneck data

317 lines 15 kB
/** * MCP Discovery Tools * Provides AI agents with comprehensive guidance on using the Bottlenecks system */ /** * Primary entry point for AI agents * Returns comprehensive workflow, capabilities, and examples */ export function createAgentsStartHereTool(client) { return { type: 'call_tool', name: 'agents_start_here', description: 'Get comprehensive guidance on using the Bottlenecks MCP server. This is the recommended first call for any AI agent.', inputSchema: { type: 'object', properties: { include_examples: { type: 'boolean', description: 'Whether to include detailed usage examples', default: true, }, focus_area: { type: 'string', description: 'Specific area of interest (optional)', enum: [ 'authentication', 'bottlenecks', 'files', 'search', 'workflow', ], }, }, required: [], }, handler: async (args) => { try { const response = await client.request('/api/mcp/agents-start-here', { method: 'GET', requireAuth: false, }); if (!response.success) { return { content: [ { type: 'text', text: `Error getting agent guidance: ${response.error}`, }, ], isError: true, }; } const data = response.data; let content = ''; // Safely access nested properties with fallbacks const welcome = data?.welcome || {}; const workflow = data?.workflow || {}; const authentication = data?.authentication || {}; // Add welcome message content += `# ${welcome.title || 'Bottlenecks MCP Server'}\n\n`; content += `${welcome.description || 'AI-powered bottleneck research system'}\n\n`; content += `**Version:** ${welcome.version || '1.0.0'}\n`; if (welcome.updateAvailable) { content += `⚠️ **Update available:** ${welcome.updateNotice || `A newer version is available (latest: ${welcome.latestVersion}).`}\n`; } const capabilities = data.capabilities || {}; const totalCapabilities = Object.values(capabilities).flat().length; content += `**Capabilities:** ${totalCapabilities > 0 ? `${totalCapabilities} features available` : 'Available'}\n\n`; // Add workflow if not focusing on specific area if (!args.focus_area || args.focus_area === 'workflow') { content += `## 🚀 Recommended Workflow\n\n`; const steps = workflow.steps || []; if (Array.isArray(steps)) { steps.forEach((step, index) => { content += `### Step ${step.step || index + 1}: ${step.action || 'Unknown'}\n`; content += `${step.description || 'No description'}\n`; if (step.tool) content += `**Tool:** \`${step.tool}\`\n`; if (step.endpoint) content += `**Endpoint:** \`${step.endpoint}\`\n`; if (step.required) content += `**Required:** Yes\n`; content += '\n'; }); } else { content += `No workflow steps available\n\n`; } } // Add authentication info if requested if (!args.focus_area || args.focus_area === 'authentication') { content += `## 🔐 Authentication\n\n`; content += `**Method:** ${authentication.method || 'API Key Authentication'}\n`; if (authentication.description) { content += `${authentication.description}\n\n`; } content += `**Authentication Flow:**\n`; const authFlow = authentication.flow || []; if (Array.isArray(authFlow)) { authFlow.forEach((step, index) => { content += `${index + 1}. ${step}\n`; }); } else { content += `1. Get API key from authorization endpoint\n2. Include in Authorization header\n3. Format: Bearer bk_your_key_here\n`; } if (authentication.key_format) { content += `\n**Key Format:** ${authentication.key_format}\n`; } if (authentication.header_format) { content += `**Header Format:** ${authentication.header_format}\n`; } const scopes = authentication.scopes || {}; if (Object.keys(scopes).length > 0) { content += `\n**Access Levels:**\n`; Object.entries(scopes).forEach(([scope, description]) => { content += `- **${scope}**: ${description}\n`; }); } content += '\n'; } // Add data structure if requested if (!args.focus_area || args.focus_area === 'bottlenecks') { content += `## 📊 Bottleneck Data Structure\n\n`; const dataStructure = data.data_structure || {}; content += '```json\n'; content += JSON.stringify(dataStructure, null, 2); content += '\n```\n\n'; } // Add file support if requested if (!args.focus_area || args.focus_area === 'files') { content += `## 📁 File Support\n\n`; const capabilities = data.capabilities || {}; const fileOperations = capabilities.file_operations || []; if (Array.isArray(fileOperations) && fileOperations.length > 0) { content += `File operations available:\n\n`; fileOperations.forEach((op) => { content += `- ${op}\n`; }); content += `\n`; } else { content += `File support available\n\n`; } const rateLimits = data.rate_limits || {}; content += `**Supported Types:** PDF, DOC, DOCX, CSV, XLSX, JSON, Images\n`; content += `**Max Size:** ${rateLimits.large_files || '500MB total per day'}\n`; content += `**Processing:** File storage and attachment (no OCR or text extraction currently)\n\n`; } // Add examples if requested if (args.include_examples !== false && (!args.focus_area || args.focus_area === 'workflow')) { content += `## 💡 Example Usage\n\n`; const examples = data.examples || {}; const typicalWorkflow = examples.typical_workflow || {}; if (typicalWorkflow.scenario) { content += `### ${typicalWorkflow.scenario}\n\n`; const steps = typicalWorkflow.steps || []; if (Array.isArray(steps) && steps.length > 0) { steps.forEach((step) => { content += `- ${step}\n`; }); content += `\n`; } } else { content += `Complete examples available for typical workflows.\n\n`; } } // Add available tools content += `## 🛠️ Available Tools\n\n`; const availableTools = data.available_tools || {}; if (typeof availableTools === 'object' && Object.keys(availableTools).length > 0) { Object.entries(availableTools).forEach(([category, tools]) => { if (Array.isArray(tools) && tools.length > 0) { content += `### ${category.charAt(0).toUpperCase() + category.slice(1)} (${tools.length} tools)\n\n`; tools.forEach((tool) => { content += `- **${tool.name}**: ${tool.description}\n`; if (tool.use_when) { content += ` *Use when: ${tool.use_when}*\n`; } content += '\n'; }); } }); } else { content += `Tools available across discovery, research, creation, files, and metadata operations.\n`; } return { content: [ { type: 'text', text: content, }, ], }; } catch (error) { return { content: [ { type: 'text', text: `Error in agents_start_here: ${error instanceof Error ? error.message : 'Unknown error'}`, }, ], isError: true, }; } }, }; } /** * Get server capabilities and status */ export function createGetCapabilitiesTool(client) { return { type: 'call_tool', name: 'get_capabilities', description: 'Get detailed information about server capabilities, rate limits, and current status', inputSchema: { type: 'object', properties: { include_limits: { type: 'boolean', description: 'Include rate limiting information', default: true, }, }, required: [], }, handler: async (args) => { try { // Get basic capabilities from the discovery endpoint const response = await client.request('/api/mcp/agents-start-here', { method: 'GET', requireAuth: false, }); if (!response.success) { return { content: [ { type: 'text', text: `Error getting capabilities: ${response.error}`, }, ], isError: true, }; } const data = response.data; let content = `# Server Capabilities\n\n`; // Safely access nested properties with fallbacks const welcome = data?.welcome || {}; const availableTools = data?.available_tools || []; const fileSupport = data?.file_support || {}; content += `**Server:** ${welcome.title || 'Unknown'}\n`; content += `**Version:** ${welcome.version || '1.0.0'}\n`; if (welcome.updateAvailable) { content += `⚠️ **Update available:** ${welcome.updateNotice || `A newer version is available (latest: ${welcome.latestVersion}).`}\n`; } content += `**Status:** Online\n\n`; content += `## Core Capabilities\n`; const capabilities = welcome.capabilities || []; if (Array.isArray(capabilities)) { capabilities.forEach((cap) => { content += `- ${cap}\n`; }); } else { content += `- No capabilities available\n`; } content += `\n## Available Tools (${availableTools.length})\n`; if (Array.isArray(availableTools)) { availableTools.forEach((tool) => { content += `- **${tool.name || 'Unknown'}**: ${tool.description || 'No description'}\n`; }); } else { content += `- No tools available\n`; } content += `\n## File Support\n`; const supportedTypes = fileSupport.supported_types || []; const processingCapabilities = fileSupport.processing_capabilities || []; content += `- **Types:** ${Array.isArray(supportedTypes) ? supportedTypes.join(', ') : 'None'}\n`; content += `- **Max Size:** ${fileSupport.max_size || 'Unknown'}\n`; content += `- **Processing:** ${Array.isArray(processingCapabilities) ? processingCapabilities.join(', ') : 'None'}\n`; if (args.include_limits) { content += `\n## Rate Limits\n`; content += `- **Default:** 100 requests/hour\n`; content += `- **Premium:** 1000 requests/hour\n`; content += `- **Admin:** Unlimited\n`; } return { content: [ { type: 'text', text: content, }, ], }; } catch (error) { return { content: [ { type: 'text', text: `Error in get_capabilities: ${error instanceof Error ? error.message : 'Unknown error'}`, }, ], isError: true, }; } }, }; } //# sourceMappingURL=discovery.js.map