UNPKG

wrekenfile-converter

Version:

Convert OpenAPI and Postman specs into Wrekenfiles, with chunking for vector database storage

120 lines 4.89 kB
"use strict"; /** * Conversion quality metrics for Wrekenfile generation. * Analyzes a generated Wrekenfile object and reports statistics * so users understand what was converted and what was lost. */ Object.defineProperty(exports, "__esModule", { value: true }); exports.computeConversionStats = computeConversionStats; exports.formatConversionStats = formatConversionStats; /** * Compute conversion stats from a parsed Wrekenfile object. * Call this after generating the wrekenfile but before serializing to YAML. * * @param wrekenfile - The wrekenfile object (with VERSION, METHODS, STRUCTS, etc.) * @param preFilterStructCount - Number of structs before filterStructsByUsage (optional) */ function computeConversionStats(wrekenfile, preFilterStructCount) { var _a, _b; const methods = wrekenfile.METHODS || {}; const structs = wrekenfile.STRUCTS || {}; const warnings = []; let methodCount = 0; let methodsWithReturns = 0; let methodsWithVoidReturns = 0; let methodsWithErrors = 0; let methodsWithAuth = 0; let methodsWithInputs = 0; const httpMethodCounts = {}; for (const [methodId, methodData] of Object.entries(methods)) { methodCount++; // HTTP method counts const httpMethod = ((_a = methodData.HTTP) === null || _a === void 0 ? void 0 : _a.METHOD) || 'UNKNOWN'; httpMethodCounts[httpMethod] = (httpMethodCounts[httpMethod] || 0) + 1; // Returns analysis if (Array.isArray(methodData.RETURNS) && methodData.RETURNS.length > 0) { methodsWithReturns++; } else { methodsWithVoidReturns++; // Only warn for GET methods with no returns — that's almost always a bug if (httpMethod === 'GET') { warnings.push(`${methodId}: GET endpoint has no RETURNS`); } } // Errors if (Array.isArray(methodData.ERRORS) && methodData.ERRORS.length > 0) { methodsWithErrors++; } // Auth (case-insensitive header match — Wrekenfile headers can be emitted // in any case by user-edited files or other converters) const headers = ((_b = methodData.HTTP) === null || _b === void 0 ? void 0 : _b.HEADERS) || {}; const normalizedHeaderKeys = Object.keys(headers).map((k) => k.toLowerCase()); if (normalizedHeaderKeys.includes('authorization') || normalizedHeaderKeys.includes('x-api-key')) { methodsWithAuth++; } // Inputs if (Array.isArray(methodData.INPUTS) && methodData.INPUTS.length > 0) { methodsWithInputs++; } } const structCount = Object.keys(structs).length; const structsPruned = preFilterStructCount !== undefined ? preFilterStructCount - structCount : 0; if (structsPruned > 0) { warnings.push(`${structsPruned} unused struct(s) pruned`); } if (methodCount > 0 && methodsWithReturns === 0) { warnings.push('No methods have response types — LLMs will not be able to parse API responses'); } if (methodCount > 0 && methodsWithAuth === 0 && methodCount > 3) { warnings.push('No methods have authentication headers — verify if this API requires auth'); } return { methodCount, methodsWithReturns, methodsWithVoidReturns, methodsWithErrors, structCount, structsPruned, httpMethodCounts, methodsWithAuth, methodsWithInputs, warnings, }; } /** * Format conversion stats as a human-readable summary string. */ function formatConversionStats(stats) { const lines = []; lines.push(`Conversion Summary:`); lines.push(` Methods: ${stats.methodCount}`); const httpParts = Object.entries(stats.httpMethodCounts) .map(([method, count]) => `${method}: ${count}`) .join(', '); if (httpParts) { lines.push(` HTTP methods: ${httpParts}`); } lines.push(` With response types: ${stats.methodsWithReturns}/${stats.methodCount}`); if (stats.methodsWithVoidReturns > 0) { lines.push(` Void (no response type): ${stats.methodsWithVoidReturns}`); } lines.push(` With error handling: ${stats.methodsWithErrors}/${stats.methodCount}`); lines.push(` With auth headers: ${stats.methodsWithAuth}/${stats.methodCount}`); lines.push(` With inputs: ${stats.methodsWithInputs}/${stats.methodCount}`); lines.push(` Structs: ${stats.structCount}`); if (stats.structsPruned > 0) { lines.push(` Structs pruned (unused): ${stats.structsPruned}`); } if (stats.warnings.length > 0) { lines.push(` Warnings:`); for (const warning of stats.warnings) { lines.push(` - ${warning}`); } } return lines.join('\n'); } //# sourceMappingURL=conversion-stats.js.map