Files
mcp-tool/update-documentation.js
nasir@endelospay.com 8c74b0e23f first
2025-07-11 20:22:12 +05:00

297 lines
12 KiB
JavaScript

/**
* @fileoverview Update MCP-TOOLS-REFERENCE.md with new endpoints
* Generates comprehensive documentation for all MCP tools including new ones from api-docs.json
*/
import fs from 'fs';
import path from 'path';
/**
* Update the MCP tools reference documentation
*/
function updateDocumentation() {
try {
console.log('=== UPDATING MCP-TOOLS-REFERENCE.md DOCUMENTATION ===');
console.log('');
// Read the categorized endpoints
const categorizedPath = path.join(process.cwd(), 'categorized-endpoints.json');
const categorizedContent = fs.readFileSync(categorizedPath, 'utf8');
const categorized = JSON.parse(categorizedContent);
// Read the existing documentation
const docPath = path.join(process.cwd(), 'MCP-TOOLS-REFERENCE.md');
const existingDoc = fs.readFileSync(docPath, 'utf8');
console.log('Read existing documentation');
console.log('Read categorized endpoints');
console.log('');
// Calculate new totals
const newCounts = {
public: categorized.public.length,
provider: categorized.provider.length,
patient: categorized.patient.length,
partner: categorized.partner.length,
affiliate: categorized.affiliate.length,
network: categorized.network.length
};
const totalNew = Object.values(newCounts).reduce((sum, count) => sum + count, 0);
console.log('New endpoint counts:');
Object.keys(newCounts).forEach(type => {
console.log(` ${type.toUpperCase()}: ${newCounts[type]} endpoints`);
});
console.log(` TOTAL: ${totalNew} endpoints`);
console.log('');
// Generate updated documentation
const updatedDoc = generateUpdatedDocumentation(existingDoc, categorized, newCounts, totalNew);
// Write the updated documentation
const outputPath = path.join(process.cwd(), 'MCP-TOOLS-REFERENCE-UPDATED.md');
fs.writeFileSync(outputPath, updatedDoc);
console.log(`Updated documentation saved to: ${outputPath}`);
console.log('');
console.log('=== UPDATE SUMMARY ===');
console.log(`Added ${totalNew} new endpoints to documentation`);
console.log('- Updated overview section with new totals');
console.log('- Updated tool statistics');
console.log('- Added new tool entries for each authentication type');
console.log('- Maintained professional 6-section structure');
console.log('');
console.log('Review the updated file and then replace the original MCP-TOOLS-REFERENCE.md');
return { success: true, outputPath, totalNew };
} catch (error) {
console.error('Error updating documentation:', error);
throw error;
}
}
/**
* Generate updated documentation content
*/
function generateUpdatedDocumentation(existingDoc, categorized, newCounts, totalNew) {
let updatedDoc = existingDoc;
// Update the overview section
updatedDoc = updateOverviewSection(updatedDoc, newCounts, totalNew);
// Update tool statistics
updatedDoc = updateToolStatistics(updatedDoc, newCounts, totalNew);
// Add new tool sections
updatedDoc = addNewToolSections(updatedDoc, categorized);
return updatedDoc;
}
/**
* Update the overview section with new totals
*/
function updateOverviewSection(doc, newCounts, totalNew) {
// Update the main description
const oldOverview = /This document provides a comprehensive reference for all MCP \(Model Context Protocol\) tools available in the Laravel Healthcare MCP Server\. The server generates \*\*650\+ total tools\*\*/;
const newOverview = `This document provides a comprehensive reference for all MCP (Model Context Protocol) tools available in the Laravel Healthcare MCP Server. The server generates **${650 + totalNew}+ total tools** (including ${totalNew} new tools from api-docs.json)`;
return doc.replace(oldOverview, newOverview);
}
/**
* Update tool statistics section
*/
function updateToolStatistics(doc, newCounts, totalNew) {
// Find and update the tool statistics section
const statsSection = /## Tool Statistics[\s\S]*?- \*\*Network Tools\*\*: \d+ tools \(network operations\)/;
const newStatsSection = `## Tool Statistics
- **Total Tools**: ${101 + totalNew} (comprehensive healthcare API coverage including ${totalNew} new endpoints)
- **Public Tools**: ${26 + newCounts.public} (no authentication required - login, registration, password management)
- **Provider Tools**: ${52 + newCounts.provider} (provider/EMR authentication required - clinical data, HIPAA-compliant)
- **Patient Tools**: ${7 + newCounts.patient} (patient portal authentication required)
- **Partner Tools**: ${6 + newCounts.partner} (partner business authentication required)
- **Affiliate Tools**: ${5 + newCounts.affiliate} (affiliate business authentication required)
- **Network Tools**: ${5 + newCounts.network} (network business authentication required)`;
return doc.replace(statsSection, newStatsSection);
}
/**
* Add new tool sections for each authentication type
*/
function addNewToolSections(doc, categorized) {
let updatedDoc = doc;
// Add new public tools
if (categorized.public.length > 0) {
updatedDoc = addPublicToolsSection(updatedDoc, categorized.public);
}
// Add new provider tools
if (categorized.provider.length > 0) {
updatedDoc = addProviderToolsSection(updatedDoc, categorized.provider);
}
// Add new patient tools
if (categorized.patient.length > 0) {
updatedDoc = addPatientToolsSection(updatedDoc, categorized.patient);
}
// Add new affiliate tools
if (categorized.affiliate.length > 0) {
updatedDoc = addAffiliateToolsSection(updatedDoc, categorized.affiliate);
}
return updatedDoc;
}
/**
* Add new public tools section
*/
function addPublicToolsSection(doc, publicTools) {
const publicSection = /---\n\n## Provider Tools \(\d+ tools\)/;
let newPublicToolsTable = `\n### New Public Tools from API-Docs.json (${publicTools.length} tools)\n\n`;
newPublicToolsTable += `| Tool Name | Method | Endpoint | Description | Key Parameters |\n`;
newPublicToolsTable += `| --------- | ------ | -------- | ----------- | -------------- |\n`;
publicTools.slice(0, 20).forEach(tool => { // Show first 20 tools
const toolName = tool.toolName || generateToolName(tool, 'public');
const params = extractKeyParameters(tool);
newPublicToolsTable += `| \`${toolName}\` | ${tool.method} | \`${tool.path}\` | ${tool.summary || tool.description} | ${params} |\n`;
});
if (publicTools.length > 20) {
newPublicToolsTable += `\n*... and ${publicTools.length - 20} more public tools*\n`;
}
newPublicToolsTable += `\n---\n`;
return doc.replace(publicSection, newPublicToolsTable + '\n## Provider Tools');
}
/**
* Add new provider tools section
*/
function addProviderToolsSection(doc, providerTools) {
const patientSection = /---\n\n## Patient Tools \(\d+ tools\)/;
let newProviderToolsTable = `\n### New Provider Tools from API-Docs.json (${providerTools.length} tools)\n\n`;
newProviderToolsTable += `| Tool Name | Method | Endpoint | Description | Key Parameters |\n`;
newProviderToolsTable += `| --------- | ------ | -------- | ----------- | -------------- |\n`;
providerTools.slice(0, 25).forEach(tool => { // Show first 25 tools
const toolName = tool.toolName || generateToolName(tool, 'provider');
const params = extractKeyParameters(tool);
newProviderToolsTable += `| \`${toolName}\` | ${tool.method} | \`${tool.path}\` | ${tool.summary || tool.description} | ${params} |\n`;
});
if (providerTools.length > 25) {
newProviderToolsTable += `\n*... and ${providerTools.length - 25} more provider tools*\n`;
}
newProviderToolsTable += `\n---\n`;
return doc.replace(patientSection, newProviderToolsTable + '\n## Patient Tools');
}
/**
* Add new patient tools section
*/
function addPatientToolsSection(doc, patientTools) {
const partnerSection = /---\n\n## Partner Tools \(\d+ tools\)/;
let newPatientToolsTable = `\n### New Patient Tools from API-Docs.json (${patientTools.length} tools)\n\n`;
newPatientToolsTable += `| Tool Name | Method | Endpoint | Description | Key Parameters |\n`;
newPatientToolsTable += `| --------- | ------ | -------- | ----------- | -------------- |\n`;
patientTools.forEach(tool => {
const toolName = tool.toolName || generateToolName(tool, 'patient');
const params = extractKeyParameters(tool);
newPatientToolsTable += `| \`${toolName}\` | ${tool.method} | \`${tool.path}\` | ${tool.summary || tool.description} | ${params} |\n`;
});
newPatientToolsTable += `\n---\n`;
return doc.replace(partnerSection, newPatientToolsTable + '\n## Partner Tools');
}
/**
* Add new affiliate tools section
*/
function addAffiliateToolsSection(doc, affiliateTools) {
const networkSection = /---\n\n## Network Tools \(\d+ tools\)/;
let newAffiliateToolsTable = `\n### New Affiliate Tools from API-Docs.json (${affiliateTools.length} tools)\n\n`;
newAffiliateToolsTable += `| Tool Name | Method | Endpoint | Description | Key Parameters |\n`;
newAffiliateToolsTable += `| --------- | ------ | -------- | ----------- | -------------- |\n`;
affiliateTools.forEach(tool => {
const toolName = tool.toolName || generateToolName(tool, 'affiliate');
const params = extractKeyParameters(tool);
newAffiliateToolsTable += `| \`${toolName}\` | ${tool.method} | \`${tool.path}\` | ${tool.summary || tool.description} | ${params} |\n`;
});
newAffiliateToolsTable += `\n---\n`;
return doc.replace(networkSection, newAffiliateToolsTable + '\n## Network Tools');
}
/**
* Generate tool name from endpoint
*/
function generateToolName(endpoint, authType) {
const method = endpoint.method.toLowerCase();
const path = endpoint.path.toLowerCase();
let pathParts = path.split('/').filter(part => part && !part.startsWith('{') && !part.endsWith('}'));
pathParts = pathParts.filter(part => !['api', 'emr', 'emr-api'].includes(part));
let action = method === 'get' ? 'get' : method === 'post' ? 'create' : method === 'put' ? 'update' : method === 'delete' ? 'delete' : method;
let resource = pathParts.join('_').replace(/-/g, '_').replace(/[^a-z0-9_]/g, '');
if (!resource) {
resource = endpoint.operationId || 'unknown';
}
return `${authType}_${action}_${resource}`;
}
/**
* Extract key parameters from endpoint
*/
function extractKeyParameters(endpoint) {
const params = [];
if (endpoint.parameters && endpoint.parameters.length > 0) {
endpoint.parameters.slice(0, 3).forEach(param => {
const required = param.required ? '**Required:**' : '**Optional:**';
params.push(`${required} ${param.name} (${param.type})`);
});
}
if (endpoint.requestBody && endpoint.requestBody.content) {
const jsonContent = endpoint.requestBody.content['application/json'];
if (jsonContent && jsonContent.schema && jsonContent.schema.properties) {
const propNames = Object.keys(jsonContent.schema.properties).slice(0, 2);
propNames.forEach(propName => {
params.push(`**Body:** ${propName}`);
});
}
}
return params.length > 0 ? params.join(', ') : 'No parameters';
}
// Run the update
if (import.meta.url === `file://${process.argv[1]}`) {
updateDocumentation();
}
export { updateDocumentation };