App-vNext/Polly · error · ArgumentOutOfRangeException
The retry backoff type is not supported.
Error message
The retry backoff type is not supported.
What it means
In the jitter branch of RetryHelper.GetRetryDelayCore, the switch over DelayBackoffType throws ArgumentOutOfRangeException for any value outside Constant/Linear/Exponential. It is a defensive exhaustiveness check: the public enum only defines those three members, so this fires if an invalid cast or future enum member is passed, or if reflection supplies an undefined enum value.
Source
Thrown at src/Polly.Core/Retry/RetryHelper.cs:127
return TimeSpan.FromTicks(ticks);
}
private static TimeSpan GetRetryDelayCore(DelayBackoffType type, bool jitter, int attempt, TimeSpan baseDelay, ref double state, Func<double> randomizer)
{
if (baseDelay == TimeSpan.Zero)
{
return baseDelay;
}
if (jitter)
{
return type switch
{
DelayBackoffType.Constant => ApplyJitter(baseDelay, randomizer),
DelayBackoffType.Linear => ApplyJitter(TimeSpan.FromMilliseconds((attempt + 1) * baseDelay.TotalMilliseconds), randomizer),
DelayBackoffType.Exponential => DecorrelatedJitterBackoffV2(attempt, baseDelay, ref state, randomizer),
_ => throw new ArgumentOutOfRangeException(nameof(type), type, "The retry backoff type is not supported.")
};
}
return type switch
{
DelayBackoffType.Constant => baseDelay,
#if !NETCOREAPP
DelayBackoffType.Linear => TimeSpan.FromMilliseconds((attempt + 1) * baseDelay.TotalMilliseconds),
DelayBackoffType.Exponential => TimeSpan.FromMilliseconds(Math.Pow(ExponentialFactor, attempt) * baseDelay.TotalMilliseconds),
#else
DelayBackoffType.Linear => (attempt + 1) * baseDelay,
DelayBackoffType.Exponential => Math.Pow(ExponentialFactor, attempt) * baseDelay,
#endif
_ => throw new ArgumentOutOfRangeException(nameof(type), type, "The retry backoff type is not supported.")
};
}
}
View on GitHub (pinned to d0e46bdb1e)
Solutions
- Use one of the documented DelayBackoffType members (Constant, Linear, Exponential) when configuring RetryStrategyOptions.BackoffType.
- Validate configuration-bound enum values with Enum.IsDefined before assigning.
- If parsing from config, map string keys to the enum explicitly and reject unknown strings.
Example fix
// before options.BackoffType = (DelayBackoffType)99; // undefined options.UseJitter = true; // after options.BackoffType = DelayBackoffType.Exponential; options.UseJitter = true;
Defensive patterns
Strategy: validation
Validate before calling
if (!Enum.IsDefined(typeof(DelayBackoffType), value)) {
throw new ArgumentOutOfRangeException(nameof(value), "Undefined DelayBackoffType.");
}
options.BackoffType = value; Prevention
- Assign only Constant/Linear/Exponential to RetryStrategyOptions.BackoffType.
- Validate config-bound enums with Enum.IsDefined before assignment.
- Map config strings to enum values explicitly and reject unknown names.
When it happens
Trigger: Passing an undefined DelayBackoffType value (e.g. (DelayBackoffType)99) into RetryStrategyOptions.BackoffType and enabling jitter, then triggering a retry. Normally the options validator rejects invalid enum values first; this throw is the last line of defense.
Common situations: Reading backoff type from configuration with a typo that fails to parse and defaults oddly; casting an int to DelayBackoffType without validation; reflection/serialization round-trip producing an undefined value.
Related errors
- Invalid delay specified.
- Value must be greater than or equal to zero.
- This instance of 'CircuitBreakerStateProvider' is already in
- TaskExecution is not initialized.
- Unable to accept outcome for a task that is not completed.
AI-assisted analysis of App-vNext/Polly@d0e46bdb1e (2026-08-13).
Data as JSON: /api/errors/681efbb976ce8b11.
Report an issue: GitHub.