1

I have awaited only Task and Task of TResult but everything which has GetAwaiter() method can be awaited (either instance method - Awaitable pattern or extension method).

Has anyone await something different than Task it in real cases? If yes why?

Examples

public class MyAwaitableClass
{
    public MyAwaiter GetAwaiter()
    {
        return new MyAwaiter();
    }
}

public class MyAwaiter : INotifyCompletion
{
    public void GetResult()
    {
    }

    public bool IsCompleted
    {
        get { return false; }
    }

    //From INotifyCompletion
    public void OnCompleted(Action continuation)
    {
    }
}

public static class TimeSpanExtensions
{
     public static TaskAwaiter GetAwaiter(this TimeSpan timeSpan)
     {
        return TaskEx.Delay(timeSpan).GetAwaiter();
     }
 }

usage:

MyAwaitableClass awaitableObject = new MyAwaitableClass();
await awaitableObject;

await TimeSpan.FromSeconds(15);

Regards

chunk1ty
  • 400
  • 3
  • 14
  • Can you provide an example of a non-Task that can be `await`ed in order to illustrate what you're asking? I'm assuming you're referring to task-like types as dealt with in [this article](https://devblogs.microsoft.com/premier-developer/extending-the-async-methods-in-c/)? – ProgrammingLlama Mar 16 '20 at 05:53
  • Not really. Task-like type is introduced in c# 7. The async/await is introduced with c# 5. I read [await anything;](https://devblogs.microsoft.com/pfxteam/await-anything/) and at the end Stephen Toub said _I look forward to seeing all the interesting and useful awaiters you come up with._ So I am looking for some real cases where i possibly could apply that approach. – chunk1ty Mar 16 '20 at 06:32
  • Pretty sure this question is off topic and will end up being closed... but FWIW I've been a SWE for 10+ years and anwered 1,700 questions on this forum and never once seen a custom awaiter of any kind. – John Wu Mar 16 '20 at 06:48
  • It's never too late to improve yourself :). I am also not pretty sure whether I am going to find a real use case to await something different that **Task** but there are a lot of experience developers around the world who eventually have used is some edge cases (probably is some performance optimization cases). – chunk1ty Mar 16 '20 at 07:33
  • 1
    Some time ago I was curious if a `System.Timers.Timer` could be awaitable, and [it is actually possible](https://stackoverflow.com/questions/56844128/creating-an-awaitable-system-timers-timer/56844580#56844580). But I haven't use it in a real life situation (yet). – Theodor Zoulias Mar 16 '20 at 07:43

1 Answers1

2

Usually when default awaitable does not fulfill requirements, custom awaitable could be helpful. In one legacy application (.net 4.5) I worked on, there was custom awaitable to set and restore operation scope for WCF calls (proper async flow was introduced since .net 4.6.2).

There are also cases where people use it to set and restore thread culture: https://devblogs.microsoft.com/pfxteam/await-anything/

UPDATE

Just some update on this one:

If you are doing COM component and your types are going to be consumed in another language e.g. Javascript. It is highly likely that you will need to provide your own async experience simply because Task is a CLR type which is not available in other languages.

In this case, if you want your async types to be used, in C# projects, as Tasks, you need custom awaitable.

weichch
  • 9,306
  • 1
  • 13
  • 25