How to create a canceled task

I am writing a Stream class and is locked in the ReadAsync method. Please take a look at the code, I think it can better explain the situation so that I can do this with my English.

public override Task<int> ReadAsync(byte[] buffer, int offset, int count, System.Threading.CancellationToken cancellationToken) { if (!cancellationToken.IsCancellationRequested) { return _connection.ReceiveAsync(new ArraySegment<byte>(buffer, offset, count)); } return // <--------------- what here? } 

Using ILSpy, I see that other Stream classes return the canceled task as follows:

 return new Task<TResult>(true, default(TResult), TaskCreationOptions.None, cancellationToken); 

However, this task constructor is internal, and I cannot call it.

Google did not help me at all.

+5
source share
2 answers

The most direct way to create a canceled task is to use TaskCompletionSource :

 var tcs = new TaskCompletionSource<int>(); tcs.TrySetCanceled(); return tcs.Task; 

If you have not used it before, TaskCompletionSource provides a β€œpromise” task, which basically allows you to say: β€œHere, take this Task now and I will give the result (or report an error / cancellation) when I am ready.” This is useful when you want to plan / coordinate work yourself, and not just rely on TaskScheduler .

Alternatively, if you rewrite your method using async/await , you can force the cancellation exception to automatically propagate to the result of the Task :

 public async override Task<int> ReadAsync( byte[] buffer, int offset, int count, CancellationToken cancellationToken) { cancellationToken.ThrowIfCancellationRequested(); return await _connection.ReceiveAsync( new ArraySegment<byte>( buffer, offset, count)); } 
+9
source

the next version of .Net (v4.5.3) adds a way to create a canceled task using this internal constructor. There are both general and non-general versions:

 var token = new CancellationToken(true); Task task = Task.FromCanceled(token); Task<int> genericTask = Task.FromCanceled<int>(token); 

Keep in mind that the CancellationToken used must be canceled before calling FromCanceled

+5
source

Source: https://habr.com/ru/post/1201168/


All Articles