package traefikoidc import ( "os" "strconv" "testing" "time" ) // TestConfig manages test execution configuration and performance settings type TestConfig struct { MemoryThreshold float64 MaxConcurrency int MaxIterations int DefaultTimeout time.Duration GoroutineGrowth int CacheSize int CleanupInterval time.Duration LongTests bool QuickMode bool ExtendedTests bool MemoryStressTest bool ConcurrencyTest bool LeakDetection bool } // NewTestConfig creates a test configuration based on flags and environment func NewTestConfig() *TestConfig { config := &TestConfig{ // Default quick mode settings - very conservative for 30s target ExtendedTests: false, LongTests: false, QuickMode: true, MaxConcurrency: 2, // Reduced for quick mode MaxIterations: 1, // Minimal iterations for quick smoke tests DefaultTimeout: 5 * time.Second, // Shorter timeout MemoryThreshold: 1.0, // Strict memory limit GoroutineGrowth: 1, // Very strict goroutine limit CacheSize: 10, // Small cache size CleanupInterval: 50 * time.Millisecond, // Faster cleanup MemoryStressTest: false, ConcurrencyTest: false, LeakDetection: false, // Disable by default in quick mode for speed } // Check for extended test flag if os.Getenv("RUN_EXTENDED_TESTS") == "1" || os.Getenv("RUN_EXTENDED_TESTS") == "true" { config.EnableExtendedTests() } // Check for long test flag if os.Getenv("RUN_LONG_TESTS") == "1" || os.Getenv("RUN_LONG_TESTS") == "true" { config.EnableLongTests() } // Check for stress tests if os.Getenv("RUN_STRESS_TESTS") == "1" || os.Getenv("RUN_STRESS_TESTS") == "true" { config.EnableStressTests() } // Check for memory leak detection override if os.Getenv("DISABLE_LEAK_DETECTION") == "1" || os.Getenv("DISABLE_LEAK_DETECTION") == "true" { config.LeakDetection = false } // Parse custom concurrency limit if concStr := os.Getenv("TEST_MAX_CONCURRENCY"); concStr != "" { if conc, err := strconv.Atoi(concStr); err == nil && conc > 0 { config.MaxConcurrency = conc } } // Parse custom iteration limit if iterStr := os.Getenv("TEST_MAX_ITERATIONS"); iterStr != "" { if iter, err := strconv.Atoi(iterStr); err == nil && iter > 0 { config.MaxIterations = iter } } // Parse memory threshold if memStr := os.Getenv("TEST_MEMORY_THRESHOLD_MB"); memStr != "" { if mem, err := strconv.ParseFloat(memStr, 64); err == nil && mem > 0 { config.MemoryThreshold = mem } } return config } // EnableExtendedTests switches to extended test mode func (c *TestConfig) EnableExtendedTests() { c.ExtendedTests = true c.QuickMode = false c.MaxConcurrency = 20 c.MaxIterations = 10 c.DefaultTimeout = 30 * time.Second c.MemoryThreshold = 10.0 c.GoroutineGrowth = 5 c.CacheSize = 200 c.CleanupInterval = 50 * time.Millisecond c.ConcurrencyTest = true } // EnableLongTests switches to long-running test mode func (c *TestConfig) EnableLongTests() { c.LongTests = true c.QuickMode = false c.MaxConcurrency = 50 c.MaxIterations = 100 c.DefaultTimeout = 60 * time.Second c.MemoryThreshold = 50.0 c.GoroutineGrowth = 10 c.CacheSize = 1000 c.CleanupInterval = 10 * time.Millisecond c.ConcurrencyTest = true c.MemoryStressTest = true } // EnableStressTests switches to stress test mode func (c *TestConfig) EnableStressTests() { c.ExtendedTests = true c.LongTests = true c.QuickMode = false c.MaxConcurrency = 100 c.MaxIterations = 500 c.DefaultTimeout = 120 * time.Second c.MemoryThreshold = 100.0 c.GoroutineGrowth = 20 c.CacheSize = 2000 c.CleanupInterval = 5 * time.Millisecond c.ConcurrencyTest = true c.MemoryStressTest = true } // ShouldSkipTest determines if a test should be skipped based on config func (c *TestConfig) ShouldSkipTest(t *testing.T, testType TestType) bool { // Always respect testing.Short() - skip everything except basic quick tests if testing.Short() { switch testType { case TestTypeQuick: return false // Allow quick tests case TestTypeExtended, TestTypeLong, TestTypeMemoryStress, TestTypeConcurrencyStress: t.Skip("Skipping extended test in short mode") return true case TestTypeLeakDetection: // Skip leak detection in short mode unless explicitly enabled if !c.LeakDetection { t.Skip("Skipping leak detection test in short mode (use RUN_EXTENDED_TESTS=1 to enable)") return true } } } // Check specific test type flags switch testType { case TestTypeExtended: if !c.ExtendedTests { t.Skip("Skipping extended test (use RUN_EXTENDED_TESTS=1 to enable)") return true } case TestTypeLong: if !c.LongTests { t.Skip("Skipping long test (use RUN_LONG_TESTS=1 to enable)") return true } case TestTypeMemoryStress: if !c.MemoryStressTest { t.Skip("Skipping memory stress test (use RUN_STRESS_TESTS=1 to enable)") return true } case TestTypeConcurrencyStress: if !c.ConcurrencyTest { t.Skip("Skipping concurrency stress test (use RUN_EXTENDED_TESTS=1 to enable)") return true } case TestTypeLeakDetection: if !c.LeakDetection { t.Skip("Skipping leak detection test (DISABLE_LEAK_DETECTION=1 set)") return true } } return false } // AdjustMemoryLeakTestCase adjusts a memory leak test case based on configuration func (c *TestConfig) AdjustMemoryLeakTestCase(testCase *MemoryLeakTestCase) { // Adjust iterations if testCase.Iterations > c.MaxIterations { testCase.Iterations = c.MaxIterations } // Ensure minimum of 1 iteration if testCase.Iterations < 1 { testCase.Iterations = 1 } // Adjust memory threshold if testCase.MaxMemoryGrowthMB > c.MemoryThreshold && c.QuickMode { testCase.MaxMemoryGrowthMB = c.MemoryThreshold } // Adjust goroutine growth if testCase.MaxGoroutineGrowth > c.GoroutineGrowth && c.QuickMode { testCase.MaxGoroutineGrowth = c.GoroutineGrowth } // Adjust timeout if testCase.Timeout > c.DefaultTimeout && c.QuickMode { testCase.Timeout = c.DefaultTimeout } else if testCase.Timeout == 0 { testCase.Timeout = c.DefaultTimeout } } // AdjustConcurrencyParams adjusts concurrency parameters for tests func (c *TestConfig) AdjustConcurrencyParams(requested int) int { if requested > c.MaxConcurrency { return c.MaxConcurrency } return requested } // GetCacheSize returns appropriate cache size for tests func (c *TestConfig) GetCacheSize() int { return c.CacheSize } // GetCleanupInterval returns appropriate cleanup interval for tests func (c *TestConfig) GetCleanupInterval() time.Duration { return c.CleanupInterval } // TestType represents different categories of tests type TestType int const ( TestTypeQuick TestType = iota TestTypeExtended TestTypeLong TestTypeMemoryStress TestTypeConcurrencyStress TestTypeLeakDetection ) // String returns string representation of test type func (tt TestType) String() string { switch tt { case TestTypeQuick: return "quick" case TestTypeExtended: return "extended" case TestTypeLong: return "long" case TestTypeMemoryStress: return "memory-stress" case TestTypeConcurrencyStress: return "concurrency-stress" case TestTypeLeakDetection: return "leak-detection" default: return "unknown" } } // Global test configuration instance var globalTestConfig *TestConfig // GetTestConfig returns the global test configuration func GetTestConfig() *TestConfig { if globalTestConfig == nil { globalTestConfig = NewTestConfig() } return globalTestConfig } // SetTestConfig sets the global test configuration (useful for testing) func SetTestConfig(config *TestConfig) { globalTestConfig = config }