defect-inspection-tools-mcp-server
Version:
Defect inspection tools server handling defect detection, analysis, and reporting with AI/ML capabilities for quality control
262 lines • 11.1 kB
JavaScript
import { ValidationMiddleware } from './validation-middleware.js';
import { SanitizationMiddleware } from './sanitization-middleware.js';
import { ErrorHandler } from './error-handler.js';
import { logger } from '../utils/logger.js';
export class MiddlewareManager {
constructor() { }
static getInstance() {
if (!MiddlewareManager.instance) {
MiddlewareManager.instance = new MiddlewareManager();
}
return MiddlewareManager.instance;
}
// Main middleware execution pipeline
async processToolCall(toolName, arguments_, userId) {
const requestId = ErrorHandler.generateRequestId();
const startTime = Date.now();
try {
// Create error context for the entire request
const errorContext = ErrorHandler.createErrorContext(toolName, arguments_, userId, requestId);
logger.info(`Processing tool call: ${toolName}`, {
toolName,
requestId,
userId,
argumentKeys: Object.keys(arguments_)
});
// Step 1: Input validation
const validationResult = await this.validateInput(toolName, arguments_, errorContext);
if (!validationResult.success) {
return validationResult;
}
// Step 2: Sanitization
const sanitizedArgs = await this.sanitizeInput(validationResult.sanitizedArgs, errorContext);
// Step 3: Final validation of sanitized arguments
const finalValidation = await this.validateSanitizedInput(toolName, sanitizedArgs, errorContext);
if (!finalValidation.success) {
return finalValidation;
}
const processingTime = Date.now() - startTime;
logger.info(`Middleware processing completed for ${toolName}`, {
toolName,
requestId,
processingTime,
userId
});
return {
success: true,
sanitizedArgs: finalValidation.sanitizedArgs,
requestId
};
}
catch (error) {
logger.error('Middleware processing failed', {
toolName,
requestId,
error: SanitizationMiddleware.sanitizeForLogging(error),
userId
});
const errorContext = ErrorHandler.createErrorContext(toolName, arguments_, userId, requestId);
const standardError = ErrorHandler.handleError(error, errorContext);
return {
success: false,
error: standardError,
requestId
};
}
}
// Process tool response through middleware
async processToolResponse(toolName, response, requestId) {
try {
logger.debug(`Processing tool response for ${toolName}`, {
toolName,
requestId,
responseType: typeof response
});
// Sanitize the response
const sanitizedResponse = SanitizationMiddleware.sanitizeToolResponse(response);
logger.debug(`Tool response processed successfully for ${toolName}`, {
toolName,
requestId
});
return sanitizedResponse;
}
catch (error) {
logger.error('Tool response processing failed', {
toolName,
requestId,
error: SanitizationMiddleware.sanitizeForLogging(error)
});
const errorContext = ErrorHandler.createErrorContext(toolName, {}, undefined, requestId);
const standardError = ErrorHandler.handleError(error, errorContext);
return ErrorHandler.formatErrorForToolResponse(standardError);
}
}
// Execute tool with full middleware protection
async executeToolWithMiddleware(toolName, arguments_, toolFunction, userId) {
const middlewareResult = await this.processToolCall(toolName, arguments_, userId);
if (!middlewareResult.success) {
throw new Error(`Middleware validation failed: ${middlewareResult.error?.message}`);
}
const errorContext = ErrorHandler.createErrorContext(toolName, arguments_, userId, middlewareResult.requestId);
try {
// Execute the tool function with retry and timeout
const result = await ErrorHandler.executeWithRetry(() => ErrorHandler.executeWithTimeout(() => toolFunction(middlewareResult.sanitizedArgs), 30000, // 30 second timeout
errorContext), errorContext);
// Process the response through middleware
const processedResult = await this.processToolResponse(toolName, result, middlewareResult.requestId);
return processedResult;
}
catch (error) {
logger.error(`Tool execution failed for ${toolName}`, {
toolName,
requestId: middlewareResult.requestId,
error: SanitizationMiddleware.sanitizeForLogging(error),
userId
});
const standardError = ErrorHandler.handleError(error, errorContext);
throw new Error(standardError.message);
}
}
// Private helper methods
async validateInput(toolName, arguments_, errorContext) {
try {
const validationResult = ValidationMiddleware.validateInput(toolName, arguments_);
if (!validationResult.isValid) {
logger.warn(`Validation failed for ${toolName}`, {
toolName,
requestId: errorContext.requestId,
errors: validationResult.errors
});
const standardError = ErrorHandler.handleError(new Error(`Validation failed: ${validationResult.errors.map(e => e.message).join(', ')}`), errorContext);
return {
success: false,
error: standardError,
requestId: errorContext.requestId
};
}
return {
success: true,
sanitizedArgs: validationResult.sanitizedArgs,
requestId: errorContext.requestId
};
}
catch (error) {
logger.error('Input validation error', {
toolName,
requestId: errorContext.requestId,
error: SanitizationMiddleware.sanitizeForLogging(error)
});
const standardError = ErrorHandler.handleError(error, errorContext);
return {
success: false,
error: standardError,
requestId: errorContext.requestId
};
}
}
async sanitizeInput(arguments_, errorContext) {
try {
const sanitizedArgs = SanitizationMiddleware.sanitizeToolArguments(arguments_);
logger.debug('Input sanitization completed', {
toolName: errorContext.toolName,
requestId: errorContext.requestId,
originalKeys: Object.keys(arguments_),
sanitizedKeys: Object.keys(sanitizedArgs)
});
return sanitizedArgs;
}
catch (error) {
logger.error('Input sanitization failed', {
toolName: errorContext.toolName,
requestId: errorContext.requestId,
error: SanitizationMiddleware.sanitizeForLogging(error)
});
throw error;
}
}
async validateSanitizedInput(toolName, sanitizedArgs, errorContext) {
try {
// Perform a final validation on the sanitized arguments
const finalValidation = ValidationMiddleware.validateInput(toolName, sanitizedArgs);
if (!finalValidation.isValid) {
logger.warn(`Final validation failed for ${toolName}`, {
toolName,
requestId: errorContext.requestId,
errors: finalValidation.errors
});
const standardError = ErrorHandler.handleError(new Error(`Final validation failed: ${finalValidation.errors.map(e => e.message).join(', ')}`), errorContext);
return {
success: false,
error: standardError,
requestId: errorContext.requestId
};
}
return {
success: true,
sanitizedArgs: finalValidation.sanitizedArgs,
requestId: errorContext.requestId
};
}
catch (error) {
logger.error('Final validation error', {
toolName,
requestId: errorContext.requestId,
error: SanitizationMiddleware.sanitizeForLogging(error)
});
const standardError = ErrorHandler.handleError(error, errorContext);
return {
success: false,
error: standardError,
requestId: errorContext.requestId
};
}
}
// Health check for middleware components
async healthCheck() {
const components = {
validation: true,
sanitization: true,
errorHandler: true
};
try {
// Test validation
const testValidation = ValidationMiddleware.validateInput('test', {});
components.validation = testValidation !== undefined;
}
catch (error) {
components.validation = false;
logger.error('Validation component health check failed', { error });
}
try {
// Test sanitization
const testSanitization = SanitizationMiddleware.sanitizeToolArguments({});
components.sanitization = testSanitization !== undefined;
}
catch (error) {
components.sanitization = false;
logger.error('Sanitization component health check failed', { error });
}
try {
// Test error handler
const testError = ErrorHandler.generateRequestId();
components.errorHandler = testError !== undefined;
}
catch (error) {
components.errorHandler = false;
logger.error('Error handler component health check failed', { error });
}
const healthyCount = Object.values(components).filter(Boolean).length;
const status = healthyCount === 3 ? 'healthy' :
healthyCount === 2 ? 'degraded' : 'unhealthy';
return {
status,
components,
timestamp: new Date()
};
}
}
// Export middleware components for direct use if needed
export { ValidationMiddleware, SanitizationMiddleware, ErrorHandler };
// Export default instance
export const middlewareManager = MiddlewareManager.getInstance();
//# sourceMappingURL=index.js.map