Files
thrilltrack-explorer/src-old/lib/integrationTests/suites/performanceTests.ts

276 lines
9.2 KiB
TypeScript

/**
* 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<TestResult> => {
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<TestResult> => {
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<TestResult> => {
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()
};
}
}
}
]
};