From cec0744bb2d5421c41f85facccad55e56fd79b5e Mon Sep 17 00:00:00 2001 From: Tom Longhurst <30480171+thomhurst@users.noreply.github.com> Date: Mon, 12 Jan 2026 00:37:18 +0000 Subject: [PATCH] perf: skip Discovered messages during test execution - Remove Discovered message loop from HandleRunRequestAsync - Only send Discovered messages during discovery requests - Change DynamicTestQueue.EnqueueAsync to sync Enqueue - Dynamic tests created at runtime don't need discovery notifications This saves time and allocations when running tests since Discovered messages are only needed for test explorer discovery, not execution. Co-Authored-By: Claude Opus 4.5 --- TUnit.Engine/Framework/TestRequestHandler.cs | 7 ++----- TUnit.Engine/Interfaces/IDynamicTestQueue.cs | 5 ++--- TUnit.Engine/Services/DynamicTestQueue.cs | 5 +++-- TUnit.Engine/Services/TestRegistry.cs | 2 +- 4 files changed, 8 insertions(+), 11 deletions(-) diff --git a/TUnit.Engine/Framework/TestRequestHandler.cs b/TUnit.Engine/Framework/TestRequestHandler.cs index b431468cd7..6ca42cf218 100644 --- a/TUnit.Engine/Framework/TestRequestHandler.cs +++ b/TUnit.Engine/Framework/TestRequestHandler.cs @@ -65,11 +65,8 @@ private async Task HandleRunRequestAsync( var allTests = discoveryResult.Tests.ToArray(); - foreach (var test in allTests) - { - context.CancellationToken.ThrowIfCancellationRequested(); - await serviceProvider.MessageBus.Discovered(test.Context); - } + // Skip sending Discovered messages during execution - they're only needed for discovery requests + // This saves significant time and allocations when running tests await serviceProvider.TestSessionCoordinator.ExecuteTests( allTests, diff --git a/TUnit.Engine/Interfaces/IDynamicTestQueue.cs b/TUnit.Engine/Interfaces/IDynamicTestQueue.cs index 4dfc42f872..501336a0c2 100644 --- a/TUnit.Engine/Interfaces/IDynamicTestQueue.cs +++ b/TUnit.Engine/Interfaces/IDynamicTestQueue.cs @@ -10,11 +10,10 @@ namespace TUnit.Engine.Interfaces; internal interface IDynamicTestQueue { /// - /// Enqueues a test for execution and notifies the message bus. Thread-safe. + /// Enqueues a test for execution. Thread-safe. /// /// The test to enqueue - /// Task that completes when the test is enqueued and discovery is notified - Task EnqueueAsync(AbstractExecutableTest test); + void Enqueue(AbstractExecutableTest test); /// /// Attempts to dequeue the next test. Thread-safe. diff --git a/TUnit.Engine/Services/DynamicTestQueue.cs b/TUnit.Engine/Services/DynamicTestQueue.cs index 16d157365c..714a1d309c 100644 --- a/TUnit.Engine/Services/DynamicTestQueue.cs +++ b/TUnit.Engine/Services/DynamicTestQueue.cs @@ -29,7 +29,7 @@ public DynamicTestQueue(ITUnitMessageBus messageBus) }); } - public async Task EnqueueAsync(AbstractExecutableTest test) + public void Enqueue(AbstractExecutableTest test) { Interlocked.Increment(ref _pendingCount); @@ -39,7 +39,8 @@ public async Task EnqueueAsync(AbstractExecutableTest test) throw new InvalidOperationException("Failed to enqueue test to dynamic test queue."); } - await _messageBus.Discovered(test.Context); + // Skip sending Discovered message - dynamic tests are created during execution, + // and Discovered messages are only needed for discovery requests } public bool TryDequeue(out AbstractExecutableTest? test) diff --git a/TUnit.Engine/Services/TestRegistry.cs b/TUnit.Engine/Services/TestRegistry.cs index 4e75f2d07b..0fd6ee844f 100644 --- a/TUnit.Engine/Services/TestRegistry.cs +++ b/TUnit.Engine/Services/TestRegistry.cs @@ -101,7 +101,7 @@ private async Task ProcessPendingDynamicTests() foreach (var test in builtTests) { - await _dynamicTestQueue.EnqueueAsync(test); + _dynamicTestQueue.Enqueue(test); } }