<PackageReference Include="Polly.Core" Version="8.3.1" />

RollingHealthMetrics

using System; using System.Collections.Generic; using System.Runtime.CompilerServices; namespace Polly.CircuitBreaker.Health { [System.Runtime.CompilerServices.NullableContext(1)] [System.Runtime.CompilerServices.Nullable(0)] internal sealed class RollingHealthMetrics : HealthMetrics { [System.Runtime.CompilerServices.NullableContext(0)] private sealed class HealthWindow { public int Successes { get; set; } public int Failures { get; set; } public DateTimeOffset StartedAt { get; set; } } private readonly TimeSpan _samplingDuration; private readonly TimeSpan _windowDuration; private readonly Queue<HealthWindow> _windows; [System.Runtime.CompilerServices.Nullable(2)] private HealthWindow _currentWindow; public RollingHealthMetrics(TimeSpan samplingDuration, short numberOfWindows, TimeProvider timeProvider) : base(timeProvider) { _samplingDuration = samplingDuration; _windowDuration = TimeSpan.FromTicks(_samplingDuration.Ticks / numberOfWindows); _windows = new Queue<HealthWindow>(); } public override void IncrementSuccess() { UpdateCurrentWindow().Successes++; } public override void IncrementFailure() { UpdateCurrentWindow().Failures++; } public override void Reset() { _currentWindow = null; _windows.Clear(); } public override HealthInfo GetHealthInfo() { UpdateCurrentWindow(); int num = 0; int num2 = 0; foreach (HealthWindow window in _windows) { num += window.Successes; num2 += window.Failures; } return HealthInfo.Create(num, num2); } private HealthWindow UpdateCurrentWindow() { DateTimeOffset utcNow = base.TimeProvider.GetUtcNow(); if (_currentWindow == null || utcNow - _currentWindow.StartedAt >= _windowDuration) { _currentWindow = new HealthWindow { StartedAt = utcNow }; _windows.Enqueue(_currentWindow); } while (utcNow - _windows.Peek().StartedAt >= _samplingDuration) { _windows.Dequeue(); } return _currentWindow; } } }