dotnet/reactive · error · ArgumentOutOfRangeException
Specified argument was out of the range of valid values…
Error message
Specified argument was out of the range of valid values. (Parameter 'bufferSize')
What it means
Replay(source, bufferSize) throws ArgumentOutOfRangeException('bufferSize') when bufferSize is negative. The replay buffer size must be >= 0; a negative value cannot describe a valid number of notifications to retain.
Solutions
- Pass a non-negative bufferSize (0 replays nothing).
- If unbounded replay is intended, use the parameterless source.Replay() overload which keeps all notifications.
- Clamp the value: Math.Max(0, requestedSize).
Example fix
// before var size = config.BufferSize ?? -1; // -1 meant 'unbounded' var replay = source.Replay(size); // after var replay = config.BufferSize.HasValue ? source.Replay(Math.Max(0, config.BufferSize.Value)) : source.Replay();
Defensive patterns
Strategy: validation
Validate before calling
if (bufferSize < 0)
throw new ArgumentOutOfRangeException(nameof(bufferSize), bufferSize, "Buffer size must be non-negative.");
var replay = source.Replay(bufferSize); Type guard
static bool IsValidBufferSize(int bufferSize) => bufferSize >= 0;
Try / catch
try
{
var replay = source.Replay(bufferSize);
}
catch (ArgumentOutOfRangeException ex) when (ex.ParamName == "bufferSize")
{
var replay = source.Replay(); // fall back to unbounded
} Prevention
- Don't use -1 to mean 'unbounded' with this API; call the parameterless overload instead.
- Clamp configured sizes with Math.Max(0, value).
- Test boundary values (0, 1, -1) when wiring buffer sizes from config.
When it happens
Trigger: Calling source.Replay(bufferSize) with bufferSize < 0, e.g. -1 used as a sentinel for 'unbounded', or a computed size that underflowed.
Common situations: Porting from APIs where -1 means 'infinite buffer'; config values that are negative; integer arithmetic producing a negative count (e.g. size - extra when extra > size).
Related errors
- Specified argument was out of the range of valid values…
- Value cannot be null. (Parameter 'bufferOpenings')
- Value cannot be null. (Parameter 'bufferBoundaries')
- ArgumentOutOfRangeException (default message: Specified…
- throw new ArgumentOutOfRangeException(nameof(timeSpan));
AI-assisted analysis of dotnet/reactive@94b5d5ab91 (2026-09-15).
Data as JSON: /api/errors/39bc3bf1bdc4f5fb.
Report an issue: GitHub.
Appendix: source
Thrown at AsyncRx.NET/System.Reactive.Async/Linq/Operators/Replay.cs:38
return Multicast(source, new SequentialReplayAsyncSubject<TSource>());
}
public static IConnectableAsyncObservable<TSource> Replay<TSource>(this IAsyncObservable<TSource> source, IAsyncScheduler scheduler)
{
if (source == null)
throw new ArgumentNullException(nameof(source));
if (scheduler == null)
throw new ArgumentNullException(nameof(scheduler));
return Multicast(source, new SequentialReplayAsyncSubject<TSource>(scheduler));
}
public static IConnectableAsyncObservable<TSource> Replay<TSource>(this IAsyncObservable<TSource> source, int bufferSize)
{
if (source == null)
throw new ArgumentNullException(nameof(source));
if (bufferSize < 0)
throw new ArgumentOutOfRangeException(nameof(bufferSize));
return Multicast(source, new SequentialReplayAsyncSubject<TSource>(bufferSize));
}
public static IConnectableAsyncObservable<TSource> Replay<TSource>(this IAsyncObservable<TSource> source, int bufferSize, IAsyncScheduler scheduler)
{
if (source == null)
throw new ArgumentNullException(nameof(source));
if (bufferSize < 0)
throw new ArgumentOutOfRangeException(nameof(bufferSize));
if (scheduler == null)
throw new ArgumentNullException(nameof(scheduler));
return Multicast(source, new SequentialReplayAsyncSubject<TSource>(bufferSize, scheduler));
}
public static IConnectableAsyncObservable<TSource> Replay<TSource>(this IAsyncObservable<TSource> source, TimeSpan window)
{View on GitHub (pinned to 94b5d5ab91)