dotnet/reactive · error · ArgumentNullException
Value cannot be null. (Parameter 'first')
Error message
Value cannot be null. (Parameter 'first')
What it means
WithLatestFrom combines a source observable (first) with the latest value from another observable (second) as they arrive. The extension method validates its receiver/argument and throws ArgumentNullException with parameter name 'first' when the first (source) IAsyncObservable<TFirst> is null, failing fast before any subscription machinery is created.
Solutions
- Ensure the source observable assigned to `first` is created (e.g. via AsyncObservable.CreateAsyncObservable...) before chaining.
- Check whether an earlier operator in the chain can return null and fix it to throw or return a valid observable.
- Add a null check at pipeline construction time with a descriptive message.
- If the source is optional by design, substitute an empty observable instead of null.
Example fix
// before IAsyncObservable<int> first = GetMaybeNullSource(); var result = first.WithLatestFrom(second); // after var result = (first ?? AsyncObservable.Empty<int>()).WithLatestFrom(second);
Defensive patterns
Strategy: validation
Validate before calling
if (first is null) throw new ArgumentNullException(nameof(first)); var result = first.WithLatestFrom(second);
Type guard
bool IsSourceValid<T>(IAsyncObservable<T> o) => o is not null;
Try / catch
try
{
var result = first.WithLatestFrom(second);
}
catch (ArgumentNullException ex) when (ex.ParamName == "first")
{
// fall back to an empty source pipeline
var result = AsyncObservable.Empty<TFirst>().WithLatestFrom(second);
} Prevention
- Check that every operator earlier in the chain returns a non-null observable.
- Initialize pipeline source variables at construction, not lazily at use.
- Enable nullable reference types so null receivers are compile-time errors.
- Substitute AsyncObservable.Empty/Never for legitimately absent sources.
When it happens
Trigger: Invoking first.WithLatestFrom(second) where the receiver `first` is null, e.g. chaining off a pipeline variable that was never assigned or a factory method that returned null.
Common situations: Chained pipeline construction where an earlier operator returned null instead of an observable; configuration-driven pipelines where the primary source was not wired; unit tests building the chain with a null placeholder.
Related errors
- Value cannot be null. (Parameter 'second')
- source
- source
- comparer
- Value cannot be null. (Parameter 'resultSelector')
AI-assisted analysis of dotnet/reactive@94b5d5ab91 (2026-09-15).
Data as JSON: /api/errors/a8198cddc10df161.
Report an issue: GitHub.
Appendix: source
Thrown at AsyncRx.NET/System.Reactive.Async/Linq/Operators/WithLatestFrom.cs:16
// 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.Disposables;
using System.Threading;
using System.Threading.Tasks;
namespace System.Reactive.Linq
{
public partial class AsyncObservable
{
public static IAsyncObservable<(TFirst first, TSecond second)> WithLatestFrom<TFirst, TSecond>(this IAsyncObservable<TFirst> first, IAsyncObservable<TSecond> second)
{
if (first == null)
throw new ArgumentNullException(nameof(first));
if (second == null)
throw new ArgumentNullException(nameof(second));
return CreateAsyncObservable<(TFirst first, TSecond second)>.From(
first,
second,
static async (first, second, observer) =>
{
var (firstObserver, secondObserver) = AsyncObserver.WithLatestFrom(observer);
// REVIEW: Consider concurrent subscriptions.
var firstSubscription = await first.SubscribeSafeAsync(firstObserver).ConfigureAwait(false);
var secondSubscription = await second.SubscribeSafeAsync(secondObserver).ConfigureAwait(false);
return StableCompositeAsyncDisposable.Create(firstSubscription, secondSubscription);
});
}View on GitHub (pinned to 94b5d5ab91)