Replay Engine
Deterministic event playback with configurable market scenarios — test queue saturation, measure burst handling, and simulate exchange disconnects
● IDLE
Why Replay Engines Matter in Trading
Every production trading system needs a replay capability. Engineers use replay to:
- Validate behavior under load: "What happens to our gateway when NASDAQ opens and sends 50K msgs/sec?"
- Test failure modes: "How does the system behave when CME disconnects for 5 seconds mid-feed?"
- Measure queue saturation: "At what rate do we start dropping messages? Is our backpressure tuned correctly?"
- Benchmark changes: "Did this optimization actually reduce p99 latency under burst traffic?"
- Reproduce production incidents: Deterministic replay of recorded feeds lets engineers reproduce exact failure conditions.
Traffic Profiles
Each scenario uses a different traffic shape. These model real market conditions:
Constant — Steady State
Uniform rate throughout. Models a normal trading session (no events, no news).
Burst — Periodic Spikes
Low baseline with periodic 10x spikes. Models options expiry, earnings releases, or batch auction results.
Flash Crash — Calm → Explosion → Aftermath
20% baseline → 500% spike → gradual decay. Models 2010 Flash Crash or circuit-breaker events.
Ramp — Linear Saturation Test
Linear ramp from 0 to max rate. Finds the exact saturation point of the queue processor.
Available Scenarios
Loading...
What to Observe During Replay
While a scenario runs, switch to the other pages to observe system behavior:
| PAGE | WHAT TO WATCH |
|---|---|
| Live Terminal | Signal feed scroll rate, dropped message counter, queue depth |
| Performance | p99 latency during bursts, GC collections during high allocation, allocation rate spikes |
| Concurrency | Understand why the architecture handles these scenarios without locks |
Implementation
REPLAY ENGINE — RATE-CONTROLLED EVENT INJECTIONprivate async Task RunScenarioAsync(ReplayScenario scenario, CancellationToken ct)
{
while (!ct.IsCancellationRequested && elapsed < duration)
{
// Calculate rate based on traffic profile curve
var effectiveRate = CalculateEffectiveRate(scenario, elapsed);
// Simulate exchange disconnect window
if (scenario.SimulateDisconnect && IsInDisconnectWindow(elapsed))
{
// Feed pauses — queue drains, UI shows disconnect
await Task.Delay(100, ct);
continue;
}
// Generate batch sized for target rate
var batchSize = (int)(effectiveRate * batchInterval / 1000.0);
for (int i = 0; i < batchSize; i++)
{
// Enqueue with latency measurement
var sw = Stopwatch.StartNew();
_queueProcessor.EnqueueAsync(signal);
_metrics.RecordLatency(sw.ElapsedTicks);
}
await Task.Delay(batchInterval, ct);
}
}