prprompts-flutter-generator
Version:
AI-powered Flutter development with full automation + official extension support - Generate 32 security-audited guides & auto-implement in 2-3 hours. NEW v5.1: Official Claude Code plugin with hooks, Gemini TOML commands, Qwen MCP settings. Features: Comp
208 lines (180 loc) • 5.68 kB
JavaScript
/**
* AI-Powered Code Enhancer
* Takes generated Flutter code and applies AI-driven improvements
*/
class CodeEnhancer {
constructor(aiClient, logger = console) {
this.aiClient = aiClient;
this.logger = logger;
}
/**
* Enhance generated Flutter code
* @param {string} code - Generated Flutter code
* @param {Object} context - Conversion context (reactCode, componentName, feature, etc.)
* @returns {Promise<Object>} { enhancedCode, changelog, confidence }
*/
async enhance(code, context = {}) {
try {
this.logger.log('🎨 Enhancing code with AI...');
const result = await this.aiClient.enhance(code, context);
// Validate enhancement result
if (!result.enhanced_code || result.enhanced_code.length === 0) {
this.logger.warn('⚠️ AI enhancement returned empty code, using original');
return {
enhancedCode: code,
changelog: [{
type: 'warning',
description: 'AI enhancement skipped',
reason: 'Empty result from AI'
}],
confidence: 0.0
};
}
// Check if enhancement actually made changes
if (result.enhanced_code === code) {
this.logger.log('✓ No changes needed');
return {
enhancedCode: code,
changelog: [{
type: 'info',
description: 'Code already optimal',
reason: 'AI found no improvements needed'
}],
confidence: result.confidence || 1.0
};
}
// Apply safe transformations
const safeCode = this._applySafeTransformations(result.enhanced_code);
this.logger.log(`✓ Enhanced code (${result.changes?.length || 0} changes, confidence: ${(result.confidence * 100).toFixed(0)}%)`);
return {
enhancedCode: safeCode,
changelog: result.changes || [],
confidence: result.confidence || 0.8
};
} catch (error) {
this.logger.error(`❌ Enhancement failed: ${error.message}`);
// Return original code on failure
return {
enhancedCode: code,
changelog: [{
type: 'error',
description: 'Enhancement failed',
reason: error.message
}],
confidence: 0.0
};
}
}
/**
* Apply safe transformations to enhanced code
* Prevents AI from introducing breaking changes
* @private
*/
_applySafeTransformations(code) {
let safeCode = code;
// Ensure proper imports are preserved
if (!safeCode.includes('import \'package:flutter/material.dart\';')) {
safeCode = 'import \'package:flutter/material.dart\';\n' + safeCode;
}
// Remove any potential hardcoded secrets (defensive)
safeCode = this._removeHardcodedSecrets(safeCode);
// Ensure null safety is maintained
safeCode = this._ensureNullSafety(safeCode);
return safeCode;
}
/**
* Remove hardcoded secrets from code
* @private
*/
_removeHardcodedSecrets(code) {
// Replace obvious API keys, tokens, passwords
const secretPatterns = [
/apiKey\s*=\s*['"][A-Za-z0-9_-]{20,}['"]/g,
/token\s*=\s*['"][A-Za-z0-9_-]{20,}['"]/g,
/password\s*=\s*['"][^'"]+['"]/g,
/secret\s*=\s*['"][A-Za-z0-9_-]{20,}['"]/g
];
let safeCode = code;
secretPatterns.forEach(pattern => {
safeCode = safeCode.replace(pattern, match => {
const key = match.split('=')[0].trim();
this.logger.warn(`⚠️ Removed potential hardcoded secret: ${key}`);
return `${key} = 'REMOVED_FOR_SECURITY'`;
});
});
return safeCode;
}
/**
* Ensure null safety is maintained
* @private
*/
_ensureNullSafety(code) {
// Basic check: ensure required fields are marked
// This is a simple heuristic, not a full analyzer
return code;
}
/**
* Format changelog for display
* @param {Array} changelog - Array of change objects
* @returns {string} Formatted changelog
*/
formatChangelog(changelog) {
if (!changelog || changelog.length === 0) {
return 'No changes made';
}
const sections = {
naming: [],
performance: [],
error_handling: [],
idiomatic: [],
comments: [],
security: [],
other: []
};
changelog.forEach(change => {
const type = change.type || 'other';
if (sections[type]) {
sections[type].push(change);
} else {
sections.other.push(change);
}
});
let output = '';
Object.entries(sections).forEach(([section, changes]) => {
if (changes.length > 0) {
output += `\n${this._getSectionIcon(section)} ${this._capitalizeFirst(section.replace('_', ' '))}:\n`;
changes.forEach(change => {
output += ` - ${change.description}\n`;
if (change.reason) {
output += ` Why: ${change.reason}\n`;
}
});
}
});
return output;
}
/**
* Get emoji icon for section
* @private
*/
_getSectionIcon(section) {
const icons = {
naming: '📝',
performance: '⚡',
error_handling: '🛡️',
idiomatic: '✨',
comments: '💬',
security: '🔒',
other: '🔧'
};
return icons[section] || '📌';
}
/**
* Capitalize first letter
* @private
*/
_capitalizeFirst(str) {
return str.charAt(0).toUpperCase() + str.slice(1);
}
}
module.exports = CodeEnhancer;