test(dcl): strengthen DCL002 derace — 30s AwaitCondition + non-parallel collection for full-suite load (#234)

This commit is contained in:
Joseph Doherty
2026-06-19 01:04:36 -04:00
parent 6a4c9a85b8
commit 78360eb6a7
2 changed files with 15 additions and 2 deletions
@@ -0,0 +1,12 @@
namespace ZB.MOM.WW.ScadaBridge.DataConnectionLayer.Tests;
/// <summary>
/// Marks DataConnectionManagerActorTests as non-parallel with any other tests in the
/// same collection. This prevents CPU-contention-induced timing flakiness in DCL002
/// (and neighbours) where actor message dispatch + async I/O must complete before an
/// AwaitCondition deadline. xUnit runs all tests in the same [Collection] sequentially
/// within the assembly; the generous 30 s AwaitCondition ceiling handles cross-assembly
/// contention when the full solution test suite runs in parallel.
/// </summary>
[CollectionDefinition("DataConnectionManagerActor", DisableParallelization = true)]
public class DataConnectionManagerActorCollection { }
@@ -12,6 +12,7 @@ namespace ZB.MOM.WW.ScadaBridge.DataConnectionLayer.Tests;
/// <summary>
/// WP-34: Tests for DataConnectionManagerActor routing and lifecycle.
/// </summary>
[Collection("DataConnectionManagerActor")]
public class DataConnectionManagerActorTests : TestKit
{
private readonly IDataConnectionFactory _mockFactory;
@@ -108,7 +109,7 @@ public class DataConnectionManagerActorTests : TestKit
// completes under CPU contention.
AwaitCondition(
() => mockAdapter.ReceivedCalls().Any(c => c.GetMethodInfo().Name == "ConnectAsync"),
TimeSpan.FromSeconds(5));
TimeSpan.FromSeconds(30));
// Register a subscription.
manager.Tell(new SubscribeTagsRequest("c1", "inst1", "conn1", ["tag1"], DateTimeOffset.UtcNow));
@@ -122,7 +123,7 @@ public class DataConnectionManagerActorTests : TestKit
// actor processes the message under CPU load.
AwaitCondition(
() => mockAdapter.ReceivedCalls().Any(c => c.GetMethodInfo().Name == "WriteAsync"),
TimeSpan.FromSeconds(5));
TimeSpan.FromSeconds(30));
// After the crash the subscription state must survive: the health report
// still shows the subscribed/resolved tag. With Restart it would be 0.