TimeoutAsync does not propegate the correct cancellation token
See original GitHub issueSummary: When cancelling the execution of a timeout policy and then catching the operation cancelled exception, the cancellation token in the exception does not match the one that was cancelled. This makes it impossible to check which cancellation token triggered the exception.
Expected behavior:
OperationCanceledException.CancellationToken
should equal the input cancellation token.
Actual behaviour:
OperationCanceledException.CancellationToken
does not equal the input cancellation token.
Steps / Code to reproduce the problem:
using System.Diagnostics;
using Polly;
using Polly.Timeout;
namespace PollyBug
{
public class Program
{
public static async Task Main(string[] args)
{
// Create an async timeout policy
var timeoutPolicy = Policy.TimeoutAsync(TimeSpan.FromSeconds(10), TimeoutStrategy.Optimistic);
// Create a cancellation token
var cancellationTokenSource = new CancellationTokenSource();
var cancellationToken = cancellationTokenSource.Token;
// Execute the timeout policy with a cancellable task
var task = timeoutPolicy.ExecuteAsync(c => Task.Delay(TimeSpan.FromSeconds(10), c), cancellationToken);
// Cancel the task
cancellationTokenSource.Cancel();
try
{
// Await the task to throw the cancellation exception
await task;
}
catch (OperationCanceledException exception)
{
// The cancellation tokens do not match!
Debug.Assert(exception.CancellationToken == cancellationToken);
}
}
}
}
Stack trace:
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.ConfiguredTaskAwaitable.ConfiguredTaskAwaiter.GetResult()
at Polly.AsyncPolicy.<>c__DisplayClass40_0.<<ImplementationAsync>b__0>d.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.ValidateEnd(Task task)
at System.Runtime.CompilerServices.ConfiguredTaskAwaitable`1.ConfiguredTaskAwaiter.GetResult()
at Polly.Timeout.AsyncTimeoutEngine.<ImplementationAsync>d__0`1.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at Polly.Timeout.AsyncTimeoutEngine.<ImplementationAsync>d__0`1.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.ConfiguredTaskAwaitable.ConfiguredTaskAwaiter.GetResult()
at Polly.AsyncPolicy.<ExecuteAsync>d__12.MoveNext()
at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()
at System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)
at System.Runtime.CompilerServices.TaskAwaiter.GetResult()
at PollyBug.Program.<Main>d__0.MoveNext() in C:\Users\Rick\source\repos\PollyBug\Program.cs:line 27
Issue Analytics
- State:
- Created a year ago
- Comments:6 (4 by maintainers)
Top Results From Across the Web
c# - Polly with cancellation token is not working for ...
1 Answer. You can't use optimistic timeout strategy to cancel a Thread . This strategy uses the co-operative behaviour of the CancellationToken ...
Read more >Recommended patterns for CancellationToken
Propagate your CancellationToken to all the methods you call that accept one, except after the “point of no cancellation” referred to in the ......
Read more >A Deep Dive into C#'s CancellationToken | by Mitesh Shah
This request can only be issued by the requesting object, i.e. no individual operation can cancel itself and other operations with that token....
Read more >Patterns & Practices for efficiently handling C# async/await ...
The simplest pattern for cancellation processing is to provide a CancellationToken at the end of the argument and propagate it to the inner ......
Read more >Just because you stopped waiting for it, doesn't mean the ...
It does not allow you to arbitrarily stop a Task from running. The same is true if you use a CancellationToken with WaitAsync()...
Read more >Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start FreeTop Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
Top GitHub Comments
@martincostello Added the stack trace
This issue was closed because it has been inactive for 14 days since being marked as stale.