Skip to content

[Repo Assist] fix: async { for x in taskSeq } no longer wraps exceptions in AggregateException#321

Draft
github-actions[bot] wants to merge 2 commits intomainfrom
repo-assist/fix-async-awaittask-129-2026-03-2c2c8da1e1b359c3
Draft

[Repo Assist] fix: async { for x in taskSeq } no longer wraps exceptions in AggregateException#321
github-actions[bot] wants to merge 2 commits intomainfrom
repo-assist/fix-async-awaittask-129-2026-03-2c2c8da1e1b359c3

Conversation

@github-actions
Copy link
Contributor

@github-actions github-actions bot commented Mar 9, 2026

🤖 This is a draft PR from Repo Assist, an automated AI assistant.

Closes #129

Root cause

AsyncExtensions.fs used Async.AwaitTask to await the task returned by TaskSeq.iterAsync. Async.AwaitTask always wraps task exceptions in AggregateException, meaning that try/catch blocks in async {} expressions that iterate over a taskSeq with for could not catch the original exception type:

// Before this fix: catch block receives AggregateException, not InvalidOperationException
async {
    for item in myTaskSeq do
        try
            doSomethingThatMightThrow item
        with :? InvalidOperationException -> // <-- this did NOT match
            ()
}

Fix

Replace Async.AwaitTask with a private awaitTaskCorrect function using Async.FromContinuations that:

  • Unwraps single inner exceptions from AggregateException before routing to the error continuation
  • Propagates multi-exception AggregateException as-is (correct for cases with multiple concurrent failures)
  • Correctly routes task cancellation to the async cancellation continuation

This is the standard AwaitTaskCorrect pattern discussed extensively in the F# community (see fslang-suggestions#840).

Files changed

  • src/FSharp.Control.TaskSeq/AsyncExtensions.fs — add awaitTaskCorrect, replace Async.AwaitTask
  • src/FSharp.Control.TaskSeq.Test/TaskSeq.AsyncExtensions.Tests.fs — 2 new regression tests
  • release-notes.txt — entry under v0.6.0

AI Disclosure

This PR was created by Repo Assist, an automated AI assistant.

Test Status

Build: succeeded (Release configuration, netstandard2.1)
Tests: 4530 passed, 2 skipped, 0 failed — full suite
New tests: 2 regression tests in ExceptionPropagation module (50 total in AsyncExtensions)
Formatting: dotnet fantomas . --check passes

Generated by Repo Assist ·

To install this agentic workflow, run

gh aw add githubnext/agentics/workflows/repo-assist.md@346204513ecfa08b81566450d7d599556807389f

…teException

Replace Async.AwaitTask with a correct awaiting function that unwraps single
inner exceptions from AggregateException, so that try/catch blocks in async {}
expressions see the original exception type.

Also adds two regression tests that verify the fix:
- exceptions propagate without AggregateException wrapping
- catch blocks see the original exception type

Closes #129

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@github-actions github-actions bot added automation bug Something isn't working repo-assist labels Mar 9, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

automation bug Something isn't working repo-assist

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Remove AggregateException wrapping in Async CE for extension and prevent threadpool transition

0 participants