UNPKG

gitdb-database

Version:

A production-ready CLI tool for managing a NoSQL database using GitHub repositories as storage

333 lines 12.4 kB
import { promises as fs } from 'fs'; import path from 'path'; export class AutoFix { fixPatterns = new Map(); constructor() { this.initializeFixPatterns(); } /** * Initialize common fix patterns */ initializeFixPatterns() { // Versioning test fixes this.fixPatterns.set('version', [ { type: 'error', message: 'Version test expects v1.0.0 but gets commit hash', fix: 'Update test to expect commit-based versioning instead of semantic versioning', confidence: 0.9, category: 'logic' }, { type: 'warning', message: 'Version rollback test may fail due to missing collection', fix: 'Ensure collection exists before testing rollback functionality', confidence: 0.8, category: 'logic' } ]); // Query syntax fixes this.fixPatterns.set('query', [ { type: 'error', message: 'Invalid JSON query syntax', fix: 'Use proper JSON format: {"field": "value"} or {"field": {"$gte": 25}}', confidence: 0.9, category: 'syntax' }, { type: 'warning', message: 'Query may be inefficient for large datasets', fix: 'Add indexes or use SuperMode for better performance', confidence: 0.7, category: 'performance' } ]); // Collection fixes this.fixPatterns.set('collection', [ { type: 'error', message: 'Collection not selected', fix: 'Use "use <collection>" before running commands', confidence: 0.9, category: 'logic' }, { type: 'warning', message: 'Collection does not exist', fix: 'Create collection first with "create-collection <name>"', confidence: 0.8, category: 'logic' } ]); // Connection fixes this.fixPatterns.set('connection', [ { type: 'error', message: 'Not connected to database', fix: 'Use "connect" to establish database connection', confidence: 0.9, category: 'logic' }, { type: 'warning', message: 'Token may be invalid or expired', fix: 'Check token permissions and regenerate if needed', confidence: 0.7, category: 'security' } ]); // Performance fixes this.fixPatterns.set('performance', [ { type: 'info', message: 'Large dataset detected', fix: 'Enable SuperMode with "supermode enable" for better performance', confidence: 0.8, category: 'performance' }, { type: 'warning', message: 'Multiple queries detected', fix: 'Use batch operations or enable caching', confidence: 0.7, category: 'performance' } ]); } /** * Analyze error and suggest fixes */ async analyzeError(error, context) { const suggestions = []; const normalizedError = error.toLowerCase(); // Check for version-related errors if (normalizedError.includes('version') || normalizedError.includes('v1.0.0')) { suggestions.push(...this.fixPatterns.get('version') || []); } // Check for query syntax errors if (normalizedError.includes('json') || normalizedError.includes('syntax') || normalizedError.includes('parse')) { suggestions.push(...this.fixPatterns.get('query') || []); } // Check for collection errors if (normalizedError.includes('collection') || normalizedError.includes('use')) { suggestions.push(...this.fixPatterns.get('collection') || []); } // Check for connection errors if (normalizedError.includes('connect') || normalizedError.includes('token') || normalizedError.includes('auth')) { suggestions.push(...this.fixPatterns.get('connection') || []); } // Check for performance issues if (normalizedError.includes('slow') || normalizedError.includes('timeout') || normalizedError.includes('performance')) { suggestions.push(...this.fixPatterns.get('performance') || []); } // Add context-specific suggestions if (context) { suggestions.push(...this.generateContextSpecificFixes(error, context)); } return suggestions.sort((a, b) => b.confidence - a.confidence); } /** * Generate context-specific fixes */ generateContextSpecificFixes(error, context) { const suggestions = []; // Check if user is trying to use AI commands if (error.includes('ai') && context.lastCommand?.includes('ai')) { suggestions.push({ type: 'info', message: 'AI command needs more specific parameters', fix: 'Try: ai "show me all users" or ai "find users over 25"', confidence: 0.8, category: 'syntax' }); } // Check for missing parameters in common commands if (error.includes('usage') && context.lastCommand) { const command = context.lastCommand.split(' ')[0]; suggestions.push({ type: 'error', message: `Missing parameters for ${command}`, fix: this.getUsageExample(command), confidence: 0.9, category: 'syntax' }); } // Check for empty database issues if (error.includes('404') || error.includes('not found')) { suggestions.push({ type: 'info', message: 'Database appears to be empty', fix: 'Create collections and add documents to get started', confidence: 0.8, category: 'logic' }); } return suggestions; } /** * Get usage example for command */ getUsageExample(command) { const examples = { 'use': 'use <collection> - Example: use users', 'insert': 'insert <json> - Example: insert {"name":"John","age":25}', 'findone': 'findone <json-query> - Example: findone {"name":"John"}', 'update': 'update <id> <json> - Example: update abc123 {"age":26}', 'delete': 'delete <id> - Example: delete abc123', 'count': 'count [json-query] - Example: count {"age":{"$gte":25}}', 'create-collection': 'create-collection <name> - Example: create-collection users', 'rollback': 'rollback <collection> - Example: rollback users', 'ai': 'ai "natural language query" - Example: ai "show me all users"' }; return examples[command] || `Check "help" for ${command} usage`; } /** * Auto-fix test failures */ async fixTestFailure(testResult) { const fixes = []; if (!testResult.passed && testResult.error) { const suggestions = await this.analyzeError(testResult.error, { testName: testResult.testName }); for (const suggestion of suggestions) { if (suggestion.confidence > 0.7) { fixes.push(`${suggestion.message}\n💡 Fix: ${suggestion.fix}`); } } } return fixes; } /** * Suggest performance improvements */ async suggestPerformanceImprovements(metrics) { const suggestions = []; // Check query performance if (metrics.averageQueryTime > 100) { suggestions.push({ type: 'warning', message: 'Slow query performance detected', fix: 'Enable SuperMode or add indexes for frequently queried fields', confidence: 0.8, category: 'performance' }); } // Check cache hit rate if (metrics.cacheHitRate < 0.5) { suggestions.push({ type: 'info', message: 'Low cache hit rate', fix: 'Enable caching or optimize query patterns', confidence: 0.7, category: 'performance' }); } // Check storage efficiency if (metrics.storageEfficiency < 0.8) { suggestions.push({ type: 'info', message: 'Storage efficiency can be improved', fix: 'Enable compression or clean up unused data', confidence: 0.6, category: 'performance' }); } return suggestions; } /** * Suggest security improvements */ async suggestSecurityImprovements() { return [ { type: 'warning', message: 'Token permissions should be reviewed', fix: 'Ensure token has minimal required permissions (repo scope)', confidence: 0.8, category: 'security' }, { type: 'info', message: 'Consider using environment variables for tokens', fix: 'Store tokens in .env file or use gitdb set token <token>', confidence: 0.7, category: 'security' } ]; } /** * Generate command from natural language */ async generateCommand(prompt, context) { const normalizedPrompt = prompt.toLowerCase(); // Simple command mapping const commandMap = { 'show all': 'show docs', 'list all': 'show docs', 'find users': 'findone {"name":"user"}', 'add user': 'insert {"name":"user","age":25}', 'update user': 'update <id> {"field":"value"}', 'delete user': 'delete <id>', 'count users': 'count', 'show collections': 'show collections', 'use users': 'use users', 'create users': 'create-collection users', 'rollback': 'rollback <collection>', 'enable performance': 'supermode enable', 'generate summary': 'summarize', 'check health': 'doctor' }; for (const [key, command] of Object.entries(commandMap)) { if (normalizedPrompt.includes(key)) { return command; } } return 'help'; } /** * Learn from user corrections */ async learnFromCorrection(originalQuery, userCorrection) { try { const learningPath = path.join(process.env.HOME || process.env.USERPROFILE || '', '.gitdb', 'ai-learning.json'); const learningData = await this.loadLearningData(learningPath); learningData.corrections.push({ original: originalQuery, correction: userCorrection, timestamp: new Date().toISOString() }); await this.saveLearningData(learningPath, learningData); } catch (error) { console.warn('Failed to save learning data:', error); } } /** * Load learning data */ async loadLearningData(path) { try { const data = await fs.readFile(path, 'utf8'); return JSON.parse(data); } catch (error) { return { corrections: [] }; } } /** * Save learning data */ async saveLearningData(filePath, data) { try { const dir = path.dirname(filePath); await fs.mkdir(dir, { recursive: true }); await fs.writeFile(filePath, JSON.stringify(data, null, 2)); } catch (error) { console.warn('Failed to save learning data:', error); } } } //# sourceMappingURL=auto-fix.js.map