Skip to content

Commit 58f705a

Browse files
thomhurstclaude
andcommitted
fix: Add ConfigureAwait(false) to remaining Task.WhenAll statements
Found and fixed additional methods that were returning Task.WhenAll directly without awaiting with ConfigureAwait(false). This completes the comprehensive ConfigureAwait(false) implementation across the entire library. Fixed files: - BatchAsyncProcessor.cs & BatchAsyncProcessor_1.cs - ParallelAsyncProcessor.cs & ParallelAsyncProcessor_1.cs - UnboundedParallelAsyncProcessor.cs & UnboundedParallelAsyncProcessor_1.cs - ResultBatchAsyncProcessor_1.cs & ResultBatchAsyncProcessor_2.cs - ResultParallelAsyncProcessor_1.cs & ResultParallelAsyncProcessor_2.cs - ResultUnboundedParallelAsyncProcessor_1.cs & ResultUnboundedParallelAsyncProcessor_2.cs All methods now properly use async/await with ConfigureAwait(false) pattern. All 498 tests pass. 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
1 parent 1ccca97 commit 58f705a

12 files changed

Lines changed: 36 additions & 32 deletions

EnumerableAsyncProcessor/RunnableProcessors/BatchAsyncProcessor.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,8 @@ internal override async Task Process()
2424
}
2525
}
2626

27-
private Task ProcessBatch(ActionTaskWrapper[] taskWrappers)
27+
private async Task ProcessBatch(ActionTaskWrapper[] taskWrappers)
2828
{
29-
return Task.WhenAll(taskWrappers.Select(tw => tw.Process(CancellationToken)));
29+
await Task.WhenAll(taskWrappers.Select(tw => tw.Process(CancellationToken))).ConfigureAwait(false);
3030
}
3131
}

EnumerableAsyncProcessor/RunnableProcessors/BatchAsyncProcessor_1.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,8 @@ internal override async Task Process()
2525
}
2626
}
2727

28-
private Task ProcessBatch(ItemTaskWrapper<TInput>[] currentBatch)
28+
private async Task ProcessBatch(ItemTaskWrapper<TInput>[] currentBatch)
2929
{
30-
return Task.WhenAll(currentBatch.Select(tw => tw.Process(CancellationToken)));
30+
await Task.WhenAll(currentBatch.Select(tw => tw.Process(CancellationToken))).ConfigureAwait(false);
3131
}
3232
}

EnumerableAsyncProcessor/RunnableProcessors/ParallelAsyncProcessor.cs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,13 @@ internal ParallelAsyncProcessor(int count, Func<Task> taskSelector, Cancellation
1111
_isIOBound = isIOBound;
1212
}
1313

14-
internal override Task Process()
14+
internal override async Task Process()
1515
{
1616
// For I/O-bound tasks, don't use Task.Run wrapper as it adds unnecessary overhead
1717
// The tasks are already async and won't block threads
1818
if (_isIOBound)
1919
{
20-
return Task.WhenAll(TaskWrappers.Select(taskWrapper =>
20+
await Task.WhenAll(TaskWrappers.Select(taskWrapper =>
2121
{
2222
var task = taskWrapper.Process(CancellationToken);
2323
// Fast-path for already completed tasks
@@ -26,10 +26,11 @@ internal override Task Process()
2626
return task;
2727
}
2828
return task;
29-
}));
29+
})).ConfigureAwait(false);
30+
return;
3031
}
3132

3233
// For CPU-bound tasks, use Task.Run to offload to ThreadPool
33-
return Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken))));
34+
await Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken)))).ConfigureAwait(false);
3435
}
3536
}

EnumerableAsyncProcessor/RunnableProcessors/ParallelAsyncProcessor_1.cs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,13 @@ internal ParallelAsyncProcessor(IEnumerable<TInput> items, Func<TInput, Task> ta
1111
_isIOBound = isIOBound;
1212
}
1313

14-
internal override Task Process()
14+
internal override async Task Process()
1515
{
1616
// For I/O-bound tasks, don't use Task.Run wrapper as it adds unnecessary overhead
1717
// The tasks are already async and won't block threads
1818
if (_isIOBound)
1919
{
20-
return Task.WhenAll(TaskWrappers.Select(taskWrapper =>
20+
await Task.WhenAll(TaskWrappers.Select(taskWrapper =>
2121
{
2222
var task = taskWrapper.Process(CancellationToken);
2323
// Fast-path for already completed tasks
@@ -26,10 +26,11 @@ internal override Task Process()
2626
return task;
2727
}
2828
return task;
29-
}));
29+
})).ConfigureAwait(false);
30+
return;
3031
}
3132

3233
// For CPU-bound tasks, use Task.Run to offload to ThreadPool
33-
return Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken))));
34+
await Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken)))).ConfigureAwait(false);
3435
}
3536
}

EnumerableAsyncProcessor/RunnableProcessors/ResultProcessors/ResultBatchAsyncProcessor_1.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,8 @@ internal override async Task Process()
2626
}
2727
}
2828

29-
private Task ProcessBatch(ActionTaskWrapper<TOutput>[] batch)
29+
private async Task ProcessBatch(ActionTaskWrapper<TOutput>[] batch)
3030
{
31-
return Task.WhenAll(batch.Select(tw => tw.Process(CancellationToken)));
31+
await Task.WhenAll(batch.Select(tw => tw.Process(CancellationToken))).ConfigureAwait(false);
3232
}
3333
}

EnumerableAsyncProcessor/RunnableProcessors/ResultProcessors/ResultBatchAsyncProcessor_2.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,8 @@ internal override async Task Process()
2222
}
2323
}
2424

25-
private Task ProcessBatch(ItemTaskWrapper<TInput, TOutput>[] currentBatch)
25+
private async Task ProcessBatch(ItemTaskWrapper<TInput, TOutput>[] currentBatch)
2626
{
27-
return Task.WhenAll(currentBatch.Select(tw => tw.Process(CancellationToken)));
27+
await Task.WhenAll(currentBatch.Select(tw => tw.Process(CancellationToken))).ConfigureAwait(false);
2828
}
2929
}

EnumerableAsyncProcessor/RunnableProcessors/ResultProcessors/ResultParallelAsyncProcessor_1.cs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,13 @@ internal ResultParallelAsyncProcessor(int count, Func<Task<TOutput>> taskSelecto
1111
_isIOBound = isIOBound;
1212
}
1313

14-
internal override Task Process()
14+
internal override async Task Process()
1515
{
1616
// For I/O-bound tasks, don't use Task.Run wrapper as it adds unnecessary overhead
1717
// The tasks are already async and won't block threads
1818
if (_isIOBound)
1919
{
20-
return Task.WhenAll(TaskWrappers.Select(taskWrapper =>
20+
await Task.WhenAll(TaskWrappers.Select(taskWrapper =>
2121
{
2222
var task = taskWrapper.Process(CancellationToken);
2323
// Fast-path for already completed tasks
@@ -26,10 +26,11 @@ internal override Task Process()
2626
return task;
2727
}
2828
return task;
29-
}));
29+
})).ConfigureAwait(false);
30+
return;
3031
}
3132

3233
// For CPU-bound tasks, use Task.Run to offload to ThreadPool
33-
return Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken))));
34+
await Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken)))).ConfigureAwait(false);
3435
}
3536
}

EnumerableAsyncProcessor/RunnableProcessors/ResultProcessors/ResultParallelAsyncProcessor_2.cs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,13 +11,13 @@ internal ResultParallelAsyncProcessor(IEnumerable<TInput> items, Func<TInput, Ta
1111
_isIOBound = isIOBound;
1212
}
1313

14-
internal override Task Process()
14+
internal override async Task Process()
1515
{
1616
// For I/O-bound tasks, don't use Task.Run wrapper as it adds unnecessary overhead
1717
// The tasks are already async and won't block threads
1818
if (_isIOBound)
1919
{
20-
return Task.WhenAll(TaskWrappers.Select(taskWrapper =>
20+
await Task.WhenAll(TaskWrappers.Select(taskWrapper =>
2121
{
2222
var task = taskWrapper.Process(CancellationToken);
2323
// Fast-path for already completed tasks
@@ -26,10 +26,11 @@ internal override Task Process()
2626
return task;
2727
}
2828
return task;
29-
}));
29+
})).ConfigureAwait(false);
30+
return;
3031
}
3132

3233
// For CPU-bound tasks, use Task.Run to offload to ThreadPool
33-
return Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken))));
34+
await Task.WhenAll(TaskWrappers.Select(taskWrapper => Task.Run(() => taskWrapper.Process(CancellationToken)))).ConfigureAwait(false);
3435
}
3536
}

EnumerableAsyncProcessor/RunnableProcessors/ResultProcessors/ResultUnboundedParallelAsyncProcessor_1.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ internal ResultUnboundedParallelAsyncProcessor(int count, Func<Task<TOutput>> ta
1313
{
1414
}
1515

16-
internal override Task Process()
16+
internal override async Task Process()
1717
{
1818
// Start ALL tasks immediately without any throttling
1919
// This provides true unbounded parallelism
@@ -28,6 +28,6 @@ internal override Task Process()
2828
return task;
2929
});
3030

31-
return Task.WhenAll(tasks);
31+
await Task.WhenAll(tasks).ConfigureAwait(false);
3232
}
3333
}

EnumerableAsyncProcessor/RunnableProcessors/ResultProcessors/ResultUnboundedParallelAsyncProcessor_2.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ internal ResultUnboundedParallelAsyncProcessor(IEnumerable<TInput> items, Func<T
1313
{
1414
}
1515

16-
internal override Task Process()
16+
internal override async Task Process()
1717
{
1818
// Start ALL tasks immediately without any throttling
1919
// This provides true unbounded parallelism
@@ -28,6 +28,6 @@ internal override Task Process()
2828
return task;
2929
});
3030

31-
return Task.WhenAll(tasks);
31+
await Task.WhenAll(tasks).ConfigureAwait(false);
3232
}
3333
}

0 commit comments

Comments
 (0)