Create test data cleanup utility

Adds a new test data cleanup utility to safely remove test fixtures after integration test suites. Includes type-safe cleanup functions for parks, rides, companies, ride_models, locations, and submissions, with safety checks (is_test_data filters) and progress logging. Integrates cleanup invocation post-run to prevent database bloat and preserves safety against prod data deletion.
This commit is contained in:
gpt-engineer-app[bot]
2025-11-10 19:28:13 +00:00
parent ea22ab199f
commit f51d9dcba2
2 changed files with 528 additions and 2 deletions

View File

@@ -9,6 +9,7 @@ import { moderationTestSuite } from './suites/moderationTests';
import { moderationLockTestSuite } from './suites/moderationLockTests';
import { moderationDependencyTestSuite } from './suites/moderationDependencyTests';
import { approvalPipelineTestSuite } from './suites/approvalPipelineTests';
import { cleanupTestData, type CleanupSummary } from './testCleanup';
/**
* Registry of all available test suites
@@ -52,10 +53,17 @@ export class IntegrationTestRunner {
private shouldStop = false;
private onProgress?: (result: TestResult) => void;
private delayBetweenTests: number;
private cleanupEnabled: boolean;
private cleanupSummary?: CleanupSummary;
constructor(onProgress?: (result: TestResult) => void, delayBetweenTests: number = 8000) {
constructor(
onProgress?: (result: TestResult) => void,
delayBetweenTests: number = 8000,
cleanupEnabled: boolean = true
) {
this.onProgress = onProgress;
this.delayBetweenTests = delayBetweenTests; // Default 8 seconds to prevent rate limiting
this.cleanupEnabled = cleanupEnabled;
}
/**
@@ -277,6 +285,59 @@ export class IntegrationTestRunner {
}
}
// Run cleanup after all tests complete (if enabled)
if (this.cleanupEnabled && !this.shouldStop) {
const cleanupStartResult: TestResult = {
id: `cleanup-start-${Date.now()}`,
name: '🧹 Starting test data cleanup...',
suite: 'System',
status: 'running',
duration: 0,
timestamp: new Date().toISOString(),
details: { reason: 'Removing test fixtures to prevent database bloat' }
};
if (this.onProgress) {
this.onProgress(cleanupStartResult);
}
try {
this.cleanupSummary = await cleanupTestData();
const cleanupCompleteResult: TestResult = {
id: `cleanup-complete-${Date.now()}`,
name: `✅ Cleanup complete: ${this.cleanupSummary.totalDeleted} records deleted`,
suite: 'System',
status: this.cleanupSummary.success ? 'pass' : 'fail',
duration: this.cleanupSummary.totalDuration,
timestamp: new Date().toISOString(),
details: {
totalDeleted: this.cleanupSummary.totalDeleted,
results: this.cleanupSummary.results,
success: this.cleanupSummary.success
}
};
if (this.onProgress) {
this.onProgress(cleanupCompleteResult);
}
} catch (error) {
const cleanupErrorResult: TestResult = {
id: `cleanup-error-${Date.now()}`,
name: '❌ Cleanup failed',
suite: 'System',
status: 'fail',
duration: 0,
timestamp: new Date().toISOString(),
error: error instanceof Error ? error.message : String(error)
};
if (this.onProgress) {
this.onProgress(cleanupErrorResult);
}
}
}
this.isRunning = false;
return this.results;
}
@@ -305,6 +366,7 @@ export class IntegrationTestRunner {
skipped: number;
running: number;
totalDuration: number;
cleanup?: CleanupSummary;
} {
const total = this.results.length;
const passed = this.results.filter(r => r.status === 'pass').length;
@@ -313,7 +375,15 @@ export class IntegrationTestRunner {
const running = this.results.filter(r => r.status === 'running').length;
const totalDuration = this.results.reduce((sum, r) => sum + r.duration, 0);
return { total, passed, failed, skipped, running, totalDuration };
return {
total,
passed,
failed,
skipped,
running,
totalDuration,
cleanup: this.cleanupSummary
};
}
/**
@@ -330,5 +400,20 @@ export class IntegrationTestRunner {
this.results = [];
this.isRunning = false;
this.shouldStop = false;
this.cleanupSummary = undefined;
}
/**
* Get cleanup summary
*/
getCleanupSummary(): CleanupSummary | undefined {
return this.cleanupSummary;
}
/**
* Enable or disable automatic cleanup
*/
setCleanupEnabled(enabled: boolean): void {
this.cleanupEnabled = enabled;
}
}