/** * Performance & Scalability Integration Tests * * Tests for system performance under various conditions. */ import { supabase } from '@/lib/supabaseClient'; import type { TestSuite, TestResult } from '../testRunner'; import { TestDataTracker } from '../TestDataTracker'; export const performanceTestSuite: TestSuite = { id: 'performance', name: 'Performance & Scalability', description: 'Tests for system performance and query efficiency', tests: [ { id: 'perf-001', name: 'Entity Query Performance', description: 'Measures query performance for entity lists', run: async (): Promise => { const startTime = Date.now(); try { // Test parks query performance const parksStart = Date.now(); const { data: parks, error: parksError } = await supabase .from('parks') .select('id, name, slug, park_type, status') .limit(50); const parksDuration = Date.now() - parksStart; if (parksError) throw new Error(`Parks query failed: ${parksError.message}`); // Test rides query performance const ridesStart = Date.now(); const { data: rides, error: ridesError } = await supabase .from('rides') .select('id, name, slug, category, status, park_id') .limit(50); const ridesDuration = Date.now() - ridesStart; if (ridesError) throw new Error(`Rides query failed: ${ridesError.message}`); // Test companies query performance const companiesStart = Date.now(); const { data: companies, error: companiesError } = await supabase .from('companies') .select('id, name, slug, company_type') .limit(50); const companiesDuration = Date.now() - companiesStart; if (companiesError) throw new Error(`Companies query failed: ${companiesError.message}`); // Set performance thresholds (in milliseconds) const threshold = 1000; // 1 second const warnings: string[] = []; if (parksDuration > threshold) { warnings.push(`Parks query slow: ${parksDuration}ms`); } if (ridesDuration > threshold) { warnings.push(`Rides query slow: ${ridesDuration}ms`); } if (companiesDuration > threshold) { warnings.push(`Companies query slow: ${companiesDuration}ms`); } const totalDuration = Date.now() - startTime; return { id: 'perf-001', name: 'Entity Query Performance', suite: 'Performance & Scalability', status: warnings.length === 0 ? 'pass' : 'fail', duration: totalDuration, timestamp: new Date().toISOString(), error: warnings.length > 0 ? warnings.join('; ') : undefined, details: { parksDuration, ridesDuration, companiesDuration, threshold, parksCount: parks?.length || 0, ridesCount: rides?.length || 0, companiesCount: companies?.length || 0 } }; } catch (error) { return { id: 'perf-001', name: 'Entity Query Performance', suite: 'Performance & Scalability', status: 'fail', duration: Date.now() - startTime, error: error instanceof Error ? error.message : String(error), timestamp: new Date().toISOString() }; } } }, { id: 'perf-002', name: 'Version History Query Performance', description: 'Measures performance of version history queries', run: async (): Promise => { const startTime = Date.now(); const tracker = new TestDataTracker(); let parkId: string | null = null; try { // Create test park const parkSlug = `test-park-perf-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`; const { data: park, error: parkError } = await supabase .from('parks') .insert({ name: 'Test Park Performance', slug: parkSlug, park_type: 'theme_park', status: 'operating', is_test_data: true }) .select('id') .single(); if (parkError) throw parkError; parkId = park.id; tracker.track('parks', parkId); // Create multiple versions (updates) for (let i = 0; i < 10; i++) { await supabase .from('parks') .update({ description: `Version ${i + 1}` }) .eq('id', parkId); // Small delay to ensure versions are created await new Promise(resolve => setTimeout(resolve, 50)); } // Measure version history query const versionStart = Date.now(); const { data: versions, error: versionError } = await supabase .from('park_versions') .select('version_id, version_number, change_type, created_at') .eq('park_id', parkId) .order('version_number', { ascending: false }); const versionDuration = Date.now() - versionStart; if (versionError) throw new Error(`Version query failed: ${versionError.message}`); // Performance threshold: 500ms for version history const threshold = 500; const isSlow = versionDuration > threshold; const totalDuration = Date.now() - startTime; return { id: 'perf-002', name: 'Version History Query Performance', suite: 'Performance & Scalability', status: isSlow ? 'fail' : 'pass', duration: totalDuration, timestamp: new Date().toISOString(), error: isSlow ? `Version query took ${versionDuration}ms (threshold: ${threshold}ms)` : undefined, details: { versionDuration, threshold, versionsFound: versions?.length || 0, isSlow } }; } catch (error) { return { id: 'perf-002', name: 'Version History Query Performance', suite: 'Performance & Scalability', status: 'fail', duration: Date.now() - startTime, error: error instanceof Error ? error.message : String(error), timestamp: new Date().toISOString() }; } finally { await tracker.cleanup(); const remaining = await tracker.verifyCleanup(); if (remaining.length > 0) { console.warn('perf-002 cleanup incomplete:', remaining); } } } }, { id: 'perf-003', name: 'Database Function Performance', description: 'Measures performance of database functions', run: async (): Promise => { const startTime = Date.now(); try { const { data: userData } = await supabase.auth.getUser(); if (!userData.user) throw new Error('No authenticated user'); // Test is_moderator function performance const modStart = Date.now(); const { data: isMod, error: modError } = await supabase .rpc('is_moderator', { _user_id: userData.user.id }); const modDuration = Date.now() - modStart; if (modError) throw modError; // Test is_user_banned function performance const banStart = Date.now(); const { data: isBanned, error: banError } = await supabase .rpc('is_user_banned', { p_user_id: userData.user.id }); const banDuration = Date.now() - banStart; if (banError) throw banError; // Performance threshold: 200ms for simple functions const threshold = 200; const warnings: string[] = []; if (modDuration > threshold) { warnings.push(`is_moderator slow: ${modDuration}ms`); } if (banDuration > threshold) { warnings.push(`is_user_banned slow: ${banDuration}ms`); } const totalDuration = Date.now() - startTime; return { id: 'perf-003', name: 'Database Function Performance', suite: 'Performance & Scalability', status: warnings.length === 0 ? 'pass' : 'fail', duration: totalDuration, timestamp: new Date().toISOString(), error: warnings.length > 0 ? warnings.join('; ') : undefined, details: { isModerator: isMod, isBanned, modDuration, banDuration, threshold, allFast: warnings.length === 0 } }; } catch (error) { return { id: 'perf-003', name: 'Database Function Performance', suite: 'Performance & Scalability', status: 'fail', duration: Date.now() - startTime, error: error instanceof Error ? error.message : String(error), timestamp: new Date().toISOString() }; } } } ] };