dotnet/reactive · error · ArgumentNullException
Value cannot be null. (Parameter 'source')
Error message
Value cannot be null. (Parameter 'source')
What it means
The parameterless Replay() extension requires a non-null source IAsyncObservable. It validates arguments up front and throws ArgumentNullException before creating the SequentialReplayAsyncSubject / connectable wrapper. This is a programming error in the caller, not a runtime condition.
Solutions
- Ensure the source observable is created before calling Replay (check the factory method for null-returning paths).
- Coalesce to an empty observable if a null source is legitimate: source ?? AsyncObservable.Empty<T>().
- Throw early in your own factory if the source cannot be built, so failures surface at creation time.
Example fix
// before var src = cache.Get(key); // may be null var replay = src.Replay(); // after var src = cache.Get(key) ?? AsyncObservable.Empty<int>(); var replay = src.Replay();
Defensive patterns
Strategy: validation
Validate before calling
if (source == null)
throw new InvalidOperationException("Source observable must be created before calling Replay.");
var replay = source.Replay(); Type guard
static bool IsNonNull<T>(IAsyncObservable<T> source) => source is not null;
Try / catch
try
{
var replay = source.Replay();
}
catch (ArgumentNullException ex) when (ex.ParamName == "source")
{
// log and fall back to building the source again
} Prevention
- Make source factories non-null-returning (throw instead).
- Use ?? AsyncObservable.Empty<T>() for optional sources.
- Enable nullable reference types so null flows are caught at compile time.
When it happens
Trigger: Calling source.Replay() where source is null — typically the result of a factory/lookup that returned null, or chaining off a nullable expression.
Common situations: A GetObservable-style helper returning null on cache miss; conditional pipeline construction where an earlier step was skipped; refactoring that removed null-coalescing around the source.
Related errors
- Value cannot be null. (Parameter 'scheduler')
- Value cannot be null. (Parameter 'observer')
- comparer
- predicate
- Value cannot be null. (Parameter 'source10')
AI-assisted analysis of dotnet/reactive@94b5d5ab91 (2026-09-15).
Data as JSON: /api/errors/7bec09515f7c97c5.
Report an issue: GitHub.
Appendix: source
Thrown at AsyncRx.NET/System.Reactive.Async/Linq/Operators/Replay.cs:18
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT License.
// See the LICENSE file in the project root for more information.
using System.Reactive.Concurrency;
using System.Reactive.Subjects;
using System.Threading.Tasks;
namespace System.Reactive.Linq
{
// REVIEW: Expose Replay using ConcurrentAsyncAsyncSubject<T> underneath.
public partial class AsyncObservable
{
public static IConnectableAsyncObservable<TSource> Replay<TSource>(this IAsyncObservable<TSource> source)
{
if (source == null)
throw new ArgumentNullException(nameof(source));
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));View on GitHub (pinned to 94b5d5ab91)