我已經習慣了能夠處理異步操作的取消時,執行一個異步模式:什麼情況下會等待取消的任務拋出TaskCanceledException?
public async Task InvokeAsync(CancellationToken cancellationToken)
{
using(cancellationToken.Register(handler.Stop))
{
try
{
await handler.HandleAsync();
}
catch(HandlerStoppedException ex)
{
cancellationToken.ThrowIfCancellationRequested();
throw;
}
}
}
的方法調用,其暴露某種取消機構的異步組件。當令牌信號取消請求時,取消令牌設置回調以調用取消機制。
我可以在我的測試中調用此方法以在超時內執行其功能。
async Task TestInvoke()
{
using (var timeout = new CancellationTokenSource(TimeSpan.FromSeconds(10))
{
try
{
await InvokeAsync(timeout.Token);
}
catch (TaskCancelledException ex)
{
if (ex.CancellationToken == timeout.Token)
{
throw new TimeoutException(
"Operation failed to complete in the allowed time.", ex);
}
throw;
}
}
}
我的期望是,一個async
方法中拋出OperationCanceledException
將導致該方法返回過渡到「已取消」狀態Task
。然後我期待任何等待這個取消的任務的嘗試應該拋出一個TaskCanceledException
。
在我目前的情況下(代碼非常類似於上面),當我等待任務時,我得到一個OperationCanceledException
。如果我檢查任務的狀態,我可以看到它處於「已取消」狀態,並且沒有與之關聯的異常。
更奇怪的是,如果我在任務上調用Wait()
,則會拋出包含預期的TaskCanceledException
的AggregateException
。
在什麼情況下等待取消的任務會拋出OperationCanceledException
而不是更典型的TaskCanceledException
?
http://stackoverflow.com/questions/26577519/why-is-taskcanceledexception-thrown-and-does-not-always-breaks-into-the-debugger這應該對你有幫助。 – MetaColon