import { pool } from '../db'; /** * Migration System for God Mode * Handles transactional execution of SQL migration files */ export interface MigrationResult { success: boolean; migrationsRun: number; error?: string; rolledBack?: boolean; } /** * Run multiple SQL commands in a single transaction * Automatically rolls back if ANY command fails */ export async function runMigrations(sqlCommands: string[]): Promise { const client = await pool.connect(); let migrationsRun = 0; try { await client.query('BEGIN'); console.log('🔱 [Migration] Starting transaction...'); for (const command of sqlCommands) { // Skip empty commands or comments const trimmed = command.trim(); if (!trimmed || trimmed.startsWith('--')) { continue; } console.log(`[Migration] Executing: ${trimmed.substring(0, 100)}...`); await client.query(trimmed); migrationsRun++; } await client.query('COMMIT'); console.log(`✅ [Migration] Successfully committed ${migrationsRun} migrations`); return { success: true, migrationsRun }; } catch (error: any) { await client.query('ROLLBACK'); console.error('❌ [Migration] Error - Rolling back all changes:', error.message); return { success: false, migrationsRun, error: error.message, rolledBack: true }; } finally { client.release(); } } /** * Run a single large SQL file (like migrations) * Splits by semicolon and runs each statement in transaction */ export async function runMigrationFile(sqlContent: string): Promise { // Split by semicolon, but be smart about it const statements = sqlContent .split(';') .map(s => s.trim()) .filter(s => s.length > 0); return runMigrations(statements); } /** * Check if migrations have been run */ export async function getMigrationStatus(): Promise<{ tables: string[]; lastMigration?: Date; }> { try { const result = await pool.query(` SELECT table_name FROM information_schema.tables WHERE table_schema = 'public' ORDER BY table_name `); return { tables: result.rows.map((r: { table_name: string }) => r.table_name) }; } catch (error) { return { tables: [] }; } }