Skip to content

Eventually/WaitsFor lambda loses specialised assertion source type #5703

@thomhurst

Description

@thomhurst

Problem

Eventually (and its alias WaitsFor) in AssertionExtensions.cs only exposes a generic IAssertionSource<TValue> inside the lambda:

public static WaitsForAssertion<TValue> Eventually<TValue>(
    this IAssertionSource<TValue> source,
    Func<IAssertionSource<TValue>, Assertion<TValue>> assertionBuilder,
    TimeSpan timeout,
    ...)

This downcasts away specialised sources like CollectionAssertionBase<T>, DictionaryAssertionBase<...>, SetAssertionBase<...>, StringAssertions, TaskAssertion, etc. — so specialised extensions (e.g. collection-only assertions like HasCount, Contains, HasDistinctItems) are not accessible inside the polling lambda.

Repro

// Fails to compile: HasCount is defined on collection sources, not on IAssertionSource<List<int>>
await Assert.That(getList).Eventually(
    assert => assert.HasCount(3),
    timeout: TimeSpan.FromSeconds(5));

User must fall back to generic matchers (IsEqualTo, etc.) and loses the rich specialised surface.

Proposed fix

Add typed overloads preserving the source type, e.g.:

public static WaitsForAssertion<TCollection> Eventually<TCollection, TItem>(
    this CollectionAssertionBase<TCollection, TItem> source,
    Func<CollectionAssertionBase<TCollection, TItem>, Assertion<TCollection>> assertionBuilder,
    TimeSpan timeout, ...);

public static WaitsForAssertion<string> Eventually(
    this StringAssertions source,
    Func<StringAssertions, Assertion<string>> assertionBuilder,
    TimeSpan timeout, ...);
// ...etc for Dictionary / Set / Task / etc.

Same overload set for WaitsFor.

Acceptance

  • Specialised assertion APIs (HasCount, Contains, HasDistinctItems, dictionary key/value assertions, string assertions, ...) usable inside Eventually/WaitsFor lambdas without explicit casts.
  • Existing generic overload stays for non-specialised sources.
  • Tests cover at least collection + string + dictionary cases.

Ref: TUnit.Assertions/Extensions/AssertionExtensions.cs:1726 (WaitsFor), :1752 (Eventually).

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions