<PackageReference Include="Polly" Version="8.4.2" />

AdvancedCircuitController<TResult>

sealed class AdvancedCircuitController<TResult> : CircuitStateController<TResult>
using Polly.Utilities; using System; namespace Polly.CircuitBreaker { internal sealed class AdvancedCircuitController<TResult> : CircuitStateController<TResult> { private const short NumberOfWindows = 10; internal static readonly long ResolutionOfCircuitTimer = TimeSpan.FromMilliseconds(20).Ticks; private readonly IHealthMetrics _metrics; private readonly double _failureThreshold; private readonly int _minimumThroughput; public AdvancedCircuitController(double failureThreshold, TimeSpan samplingDuration, int minimumThroughput, TimeSpan durationOfBreak, Action<DelegateResult<TResult>, CircuitState, TimeSpan, Context> onBreak, Action<Context> onReset, Action onHalfOpen) : base(durationOfBreak, onBreak, onReset, onHalfOpen) { object metrics; if (samplingDuration.Ticks >= ResolutionOfCircuitTimer * 10) { IHealthMetrics healthMetrics = new RollingHealthMetrics(samplingDuration, 10); metrics = healthMetrics; } else { IHealthMetrics healthMetrics = new SingleHealthMetrics(samplingDuration); metrics = healthMetrics; } _metrics = (IHealthMetrics)metrics; _failureThreshold = failureThreshold; _minimumThroughput = minimumThroughput; } public override void OnCircuitReset(Context context) { using (TimedLock.Lock(Lock)) { _metrics?.Reset_NeedsLock(); ResetInternal_NeedsLock(context); } } public override void OnActionSuccess(Context context) { using (TimedLock.Lock(Lock)) { CircuitState internalCircuitState = InternalCircuitState; switch ((int)internalCircuitState) { case 2: OnCircuitReset(context); break; default: throw new InvalidOperationException("Unhandled CircuitState."); case 0: case 1: case 3: break; } _metrics.IncrementSuccess_NeedsLock(); } } public override void OnActionFailure(DelegateResult<TResult> outcome, Context context) { using (TimedLock.Lock(Lock)) { LastOutcome = outcome; CircuitState internalCircuitState = InternalCircuitState; switch ((int)internalCircuitState) { case 2: Break_NeedsLock(context); break; case 0: { _metrics.IncrementFailure_NeedsLock(); HealthCount healthCount_NeedsLock = _metrics.GetHealthCount_NeedsLock(); int total = healthCount_NeedsLock.Total; if (total >= _minimumThroughput && (double)healthCount_NeedsLock.Failures / (double)total >= _failureThreshold) Break_NeedsLock(context); break; } case 1: case 3: _metrics.IncrementFailure_NeedsLock(); break; default: throw new InvalidOperationException("Unhandled CircuitState."); } } } } }