package benchmarks import ( "testing" "github.com/jfraeys/fetch_ml/internal/queue" ) // BenchmarkNativeQueueRebuildIndex profiles the native binary queue index. // Tier 1 C++ candidate: binary format vs JSON // Expected: 5x speedup, 99% allocation reduction func BenchmarkNativeQueueRebuildIndex(b *testing.B) { if !queue.UseNativeQueue { b.Skip("Native queue not enabled (set FETCHML_NATIVE_LIBS=1 or build with -tags native_libs)") } tmpDir := b.TempDir() q, err := queue.NewNativeQueue(tmpDir) if err != nil { b.Fatal(err) } defer q.Close() // Seed with tasks for i := 0; i < 100; i++ { task := &queue.Task{ ID: "task-" + string(rune('0'+i/10)) + string(rune('0'+i%10)), JobName: "job-" + string(rune('0'+i/10)), Priority: int64(100 - i), } if err := q.AddTask(task); err != nil { b.Fatal(err) } } b.ResetTimer() b.ReportAllocs() // Benchmark just the add (native uses binary index, no JSON rebuild) for i := 0; i < b.N; i++ { task := &queue.Task{ ID: "bench-task-" + string(rune('0'+i%10)), JobName: "bench-job", Priority: int64(i), } if err := q.AddTask(task); err != nil { b.Fatal(err) } } } // BenchmarkNativeQueueClaimNext profiles task claiming from binary heap func BenchmarkNativeQueueClaimNext(b *testing.B) { if !queue.UseNativeQueue { b.Skip("Native queue not enabled (set FETCHML_NATIVE_LIBS=1 or build with -tags native_libs)") } tmpDir := b.TempDir() q, err := queue.NewNativeQueue(tmpDir) if err != nil { b.Fatal(err) } defer q.Close() // Seed with tasks for i := 0; i < 100; i++ { task := &queue.Task{ ID: "task-" + string(rune('0'+i/10)) + string(rune('0'+i%10)), JobName: "job-" + string(rune('0'+i/10)), Priority: int64(100 - i), } if err := q.AddTask(task); err != nil { b.Fatal(err) } } b.ResetTimer() b.ReportAllocs() for i := 0; i < b.N; i++ { // Binary heap pop - no JSON parsing _, _ = q.PeekNextTask() } } // BenchmarkNativeQueueGetAllTasks profiles full task scan from binary index func BenchmarkNativeQueueGetAllTasks(b *testing.B) { if !queue.UseNativeQueue { b.Skip("Native queue not enabled (set FETCHML_NATIVE_LIBS=1 or build with -tags native_libs)") } tmpDir := b.TempDir() q, err := queue.NewNativeQueue(tmpDir) if err != nil { b.Fatal(err) } defer q.Close() // Seed with tasks for i := 0; i < 100; i++ { task := &queue.Task{ ID: "task-" + string(rune('0'+i/10)) + string(rune('0'+i%10)), JobName: "job-" + string(rune('0'+i/10)), Priority: int64(100 - i), } if err := q.AddTask(task); err != nil { b.Fatal(err) } } b.ResetTimer() b.ReportAllocs() for i := 0; i < b.N; i++ { _, err := q.GetAllTasks() if err != nil { b.Fatal(err) } } }