#!/usr/bin/env node /** * Script de tests de production pour Veza V5 Ultra * Objectif: 100% tests passés, 0 bugs critiques */ const { execSync } = require('child_process'); const fs = require('fs'); const path = require('path'); console.log('🧪 VEZA V5 ULTRA - Production Tests'); console.log('===================================\n'); // Configuration des tests const testConfig = { unit: { command: 'npm run test:unit', coverage: 80, timeout: 30000, }, e2e: { command: 'npm run test:e2e', timeout: 60000, }, lighthouse: { command: 'npm run lighthouse:ci', score: 100, }, performance: { command: 'npm run test:perf', fcp: 0.8, // First Contentful Paint < 0.8s tti: 1.5, // Time to Interactive < 1.5s cls: 0.1, // Cumulative Layout Shift < 0.1 }, accessibility: { command: 'npm run test:a11y', score: 100, }, }; // Fonction pour exécuter un test function runTest(name, config) { console.log(`\n🔍 Running ${name}...`); try { const startTime = Date.now(); const result = execSync(config.command, { encoding: 'utf8', timeout: config.timeout || 30000, stdio: 'pipe' }); const duration = (Date.now() - startTime) / 1000; console.log(`✅ ${name} passed in ${duration.toFixed(2)}s`); // Analyser les résultats spécifiques if (name === 'Unit Tests' && config.coverage) { const coverageMatch = result.match(/(\d+)%/); if (coverageMatch) { const coverage = parseInt(coverageMatch[1]); if (coverage >= config.coverage) { console.log(`✅ Coverage: ${coverage}% (target: ${config.coverage}%)`); } else { console.log(`⚠️ Coverage: ${coverage}% (target: ${config.coverage}%)`); } } } if (name === 'Lighthouse' && config.score) { const scoreMatch = result.match(/Performance: (\d+)/); if (scoreMatch) { const score = parseInt(scoreMatch[1]); if (score >= config.score) { console.log(`✅ Lighthouse Score: ${score}/100`); } else { console.log(`⚠️ Lighthouse Score: ${score}/100 (target: ${config.score})`); } } } return { success: true, duration, result }; } catch (error) { console.log(`❌ ${name} failed:`, error.message); return { success: false, error: error.message }; } } // Fonction pour vérifier les métriques de performance function checkPerformanceMetrics() { console.log('\n📊 Checking Performance Metrics...'); const metrics = { bundleSize: checkBundleSize(), buildTime: checkBuildTime(), memoryUsage: checkMemoryUsage(), }; return metrics; } function checkBundleSize() { const distPath = path.join(__dirname, '..', 'dist'); if (!fs.existsSync(distPath)) { return { error: 'No dist folder found' }; } let totalSize = 0; let jsFiles = []; function scanDir(dir) { const files = fs.readdirSync(dir); files.forEach(file => { const filePath = path.join(dir, file); if (fs.statSync(filePath).isDirectory()) { scanDir(filePath); } else if (file.endsWith('.js')) { const size = fs.statSync(filePath).size; totalSize += size; jsFiles.push({ name: file, size }); } }); } scanDir(distPath); const initialBundle = jsFiles.find(f => f.name.includes('index'))?.size || 0; const maxChunk = Math.max(...jsFiles.map(f => f.size)); return { total: totalSize, initial: initialBundle, maxChunk, files: jsFiles.length, target: 150 * 1024, // 150KB }; } function checkBuildTime() { const startTime = Date.now(); try { execSync('npm run build', { stdio: 'pipe' }); return Date.now() - startTime; } catch (error) { return { error: error.message }; } } function checkMemoryUsage() { const usage = process.memoryUsage(); return { rss: Math.round(usage.rss / 1024 / 1024), // MB heapUsed: Math.round(usage.heapUsed / 1024 / 1024), // MB heapTotal: Math.round(usage.heapTotal / 1024 / 1024), // MB }; } // Fonction pour générer le rapport de tests function generateTestReport(results) { const report = { timestamp: new Date().toISOString(), summary: { total: Object.keys(testConfig).length, passed: Object.values(results).filter(r => r.success).length, failed: Object.values(results).filter(r => !r.success).length, }, results, performance: checkPerformanceMetrics(), }; const reportPath = path.join(__dirname, '..', 'test-report-production.json'); fs.writeFileSync(reportPath, JSON.stringify(report, null, 2)); console.log(`\n📄 Test report saved to: ${reportPath}`); return report; } // Exécuter tous les tests async function runAllTests() { console.log('🚀 Starting Production Test Suite...\n'); const results = {}; // Tests unitaires results.unit = runTest('Unit Tests', testConfig.unit); // Tests E2E results.e2e = runTest('E2E Tests', testConfig.e2e); // Tests Lighthouse results.lighthouse = runTest('Lighthouse', testConfig.lighthouse); // Tests de performance results.performance = runTest('Performance Tests', testConfig.performance); // Tests d'accessibilité results.accessibility = runTest('Accessibility Tests', testConfig.accessibility); // Générer le rapport const report = generateTestReport(results); // Afficher le résumé console.log('\n📋 TEST SUMMARY'); console.log('================'); console.log(`Total Tests: ${report.summary.total}`); console.log(`Passed: ${report.summary.passed} ✅`); console.log(`Failed: ${report.summary.failed} ❌`); console.log(`Success Rate: ${((report.summary.passed / report.summary.total) * 100).toFixed(1)}%`); // Métriques de performance console.log('\n📊 PERFORMANCE METRICS'); console.log('======================'); if (report.performance.bundleSize) { const bundle = report.performance.bundleSize; console.log(`Bundle Size: ${(bundle.initial / 1024).toFixed(2)} KB (target: < 150 KB)`); console.log(`Max Chunk: ${(bundle.maxChunk / 1024).toFixed(2)} KB (target: < 50 KB)`); console.log(`Total Files: ${bundle.files}`); } if (report.performance.buildTime) { console.log(`Build Time: ${(report.performance.buildTime / 1000).toFixed(2)}s`); } if (report.performance.memoryUsage) { const mem = report.performance.memoryUsage; console.log(`Memory Usage: ${mem.heapUsed}MB / ${mem.heapTotal}MB`); } // Recommandations console.log('\n💡 RECOMMENDATIONS'); console.log('=================='); if (report.summary.failed > 0) { console.log('❌ Fix failing tests before production deployment'); } if (report.performance.bundleSize?.initial > report.performance.bundleSize?.target) { console.log('⚠️ Bundle size too large - consider code splitting'); } if (report.performance.buildTime > 30000) { console.log('⚠️ Build time too slow - consider optimization'); } if (report.summary.passed === report.summary.total) { console.log('🎉 All tests passed! Ready for production deployment'); } return report.summary.passed === report.summary.total; } // Exécuter les tests runAllTests().then(success => { process.exit(success ? 0 : 1); }).catch(error => { console.error('❌ Test suite failed:', error); process.exit(1); });