import mysql from 'mysql2/promise'; import dotenv from 'dotenv'; import path from 'path'; import { fileURLToPath } from 'url'; // __dirname für ES-Module const __filename = fileURLToPath(import.meta.url); const __dirname = path.dirname(__filename); // Umgebungsvariablen aus dem Root-Verzeichnis laden //const envPath = path.join(__dirname, '..', '.env'); //console.log('🔍 Lade .env-Datei von:', envPath); dotenv.config(); // Debug: Zeige geladene Umgebungsvariablen console.log('🔍 Geladene Umgebungsvariablen:'); console.log(' DB_HOST:', process.env.DB_HOST); console.log(' DB_USER:', process.env.DB_USER); console.log(' DB_NAME:', process.env.DB_NAME); console.log(' DB_PASSWORD:', process.env.DB_PASSWORD ? '***gesetzt***' : 'nicht gesetzt'); // Datenbankverbindung const dbConfig = { host: process.env.DB_HOST || 'localhost', user: process.env.DB_USER || 'root', password: process.env.DB_PASSWORD || '', database: process.env.DB_NAME || 'trainingsdiary' }; console.log('🔍 Datenbankverbindung:'); console.log(' Host:', dbConfig.host); console.log(' User:', dbConfig.user); console.log(' Database:', dbConfig.database); console.log(' Password:', dbConfig.password ? '***gesetzt***' : 'nicht gesetzt'); async function cleanupKeys() { let connection; try { console.log('🔌 Verbinde mit der Datenbank...'); connection = await mysql.createConnection(dbConfig); // 1. Status vor dem Cleanup console.log('\n📊 STATUS VOR DEM CLEANUP:'); const [tablesBefore] = await connection.execute(` SELECT TABLE_NAME, COUNT(*) as key_count FROM INFORMATION_SCHEMA.STATISTICS WHERE TABLE_SCHEMA = ? GROUP BY TABLE_NAME ORDER BY key_count DESC `, [dbConfig.database]); tablesBefore.forEach(table => { console.log(` ${table.TABLE_NAME}: ${table.key_count} Keys`); }); // 2. Alle INDEX der Problem-Tabellen anzeigen const problemTables = ['member', 'diary_tags', 'season']; for (const tableName of problemTables) { console.log(`\n🔍 INDEX für Tabelle '${tableName}':`); try { const [indexes] = await connection.execute(`SHOW INDEX FROM \`${tableName}\``); if (indexes.length === 0) { console.log(` Keine INDEX gefunden für Tabelle '${tableName}'`); continue; } indexes.forEach(index => { console.log(` - ${index.Key_name} (${index.Column_name}) - ${index.Non_unique === 0 ? 'UNIQUE' : 'NON-UNIQUE'}`); }); // 3. Überflüssige INDEX entfernen (alle außer PRIMARY und UNIQUE) console.log(`\n🗑️ Entferne überflüssige INDEX aus '${tableName}':`); for (const index of indexes) { // Behalte PRIMARY KEY und UNIQUE constraints if (index.Key_name === 'PRIMARY' || index.Non_unique === 0) { console.log(` ✅ Behalte: ${index.Key_name} (${index.Column_name})`); continue; } // Entferne alle anderen INDEX try { await connection.execute(`DROP INDEX \`${index.Key_name}\` ON \`${tableName}\``); console.log(` ❌ Entfernt: ${index.Key_name} (${index.Column_name})`); } catch (error) { if (error.code === 'ER_CANT_DROP_FIELD_OR_KEY') { console.log(` ⚠️ Kann nicht entfernen: ${index.Key_name} (${index.Column_name}) - ${error.message}`); } else { console.log(` ❌ Fehler beim Entfernen von ${index.Key_name}: ${error.message}`); } } } } catch (error) { console.log(` ⚠️ Fehler beim Zugriff auf Tabelle '${tableName}': ${error.message}`); } } // 4. Status nach dem Cleanup console.log('\n📊 STATUS NACH DEM CLEANUP:'); const [tablesAfter] = await connection.execute(` SELECT TABLE_NAME, COUNT(*) as key_count FROM INFORMATION_SCHEMA.STATISTICS WHERE TABLE_SCHEMA = ? GROUP BY TABLE_NAME ORDER BY key_count DESC `, [dbConfig.database]); tablesAfter.forEach(table => { const before = tablesBefore.find(t => t.TABLE_NAME === table.TABLE_NAME); const beforeCount = before ? before.key_count : 0; const diff = beforeCount - table.key_count; const status = table.key_count <= 5 ? '✅' : table.key_count <= 10 ? '⚠️' : '❌'; console.log(` ${status} ${table.TABLE_NAME}: ${table.key_count} Keys (${diff > 0 ? `-${diff}` : `+${Math.abs(diff)}`})`); }); // 5. Gesamtanzahl der Keys const [totalKeys] = await connection.execute(` SELECT COUNT(*) as total_keys FROM INFORMATION_SCHEMA.STATISTICS WHERE TABLE_SCHEMA = ? `, [dbConfig.database]); console.log(`\n📈 GESAMTANZAHL KEYS: ${totalKeys[0].total_keys}`); // 6. Zusammenfassung console.log('\n🎯 ZUSAMMENFASSUNG:'); const problemTablesAfter = tablesAfter.filter(t => t.key_count > 10); if (problemTablesAfter.length === 0) { console.log(' ✅ Alle Tabellen haben jetzt weniger als 10 Keys!'); } else { console.log(' ⚠️ Folgende Tabellen haben immer noch zu viele Keys:'); problemTablesAfter.forEach(table => { console.log(` - ${table.TABLE_NAME}: ${table.key_count} Keys`); }); } } catch (error) { console.error('❌ Fehler beim Cleanup:', error); } finally { if (connection) { await connection.end(); console.log('\n🔌 Datenbankverbindung geschlossen.'); } } } // Script ausführen console.log('🚀 Starte intelligentes INDEX-Cleanup...\n'); cleanupKeys().then(() => { console.log('\n✨ Cleanup abgeschlossen!'); process.exit(0); }).catch(error => { console.error('\n💥 Fehler beim Cleanup:', error); process.exit(1); });