using cancellation
syntax for ambient CancellationToken
#9672
-
ProblemI'm tired of passing public async Task HandleRequestAsync(HttpContext context)
{
var token = context.RequestAborted;
var data = await database.GetDataAsync(token);
var result = await ProcessDataAsync(data, token);
await SendResponseAsync(result, token);
} Every method call needs that token parameter. It's verbose, easy to forget, and clutters the actual logic. Proposed SolutionWhat if we could make CancellationToken ambient in a scope, like this: public async Task HandleRequestAsync(HttpContext context)
{
using cancellation context.RequestAborted
{
var data = await database.GetDataAsync(); // gets token automatically
var result = await ProcessDataAsync(data); // gets token automatically
await SendResponseAsync(result); // gets token automatically
}
} How it works
Why this syntax?
Comparison with existing ideasI found similar proposals like #1332 (ambient parameters) and #81874 (cancel scopes), but they're either too general or too complex. This is simpler and focused only on cancellation. Real example from my codeInstead of this boilerplate: await ValidateOrderAsync(order, cancellationToken);
var inventory = await CheckInventoryAsync(order.Items, cancellationToken);
await ReserveInventoryAsync(inventory, cancellationToken);
await ProcessPaymentAsync(order.Payment, cancellationToken); I could write: using cancellation cancellationToken
{
await ValidateOrderAsync(order);
var inventory = await CheckInventoryAsync(order.Items);
await ReserveInventoryAsync(inventory);
await ProcessPaymentAsync(order.Payment);
} Much cleaner and less error-prone. Thoughts? |
Beta Was this translation helpful? Give feedback.
Replies: 3 comments 1 reply
-
Beta Was this translation helpful? Give feedback.
-
I'm skeptical. Sometimes it would be even worse to pass a cancellation token than to pass none. An example would be any two-phase process where the first phase can be canceled, but once cancelled, the second phase may not be canceled. The second phase could be as simple as writing a record saving an ID that was created in the first phase so that the result of the first phase is not orphaned. If the first phase successfully completes, then under no circumstances should the second phase be allowed to cancel. Right now, if you miss explicitly specifying CancellationToken.None for the second phase, the right thing happens. You're in the pit of success. If you were using an implicit cancellation token, it would become very hard to spot this kind of bug. |
Beta Was this translation helpful? Give feedback.
-
Beta Was this translation helpful? Give feedback.
Also:
#5989
#8866