3

There are some interesting examples of custom awaiters in Stephen Toub's Await Anything blog post. I specifically like await task.WithCulture() pattern which I think can be useful in real life. However, I can't think of anything else that possibly cannot be done with TaskCompletionSource.

One interesting field where it might be useful for is switching of execution contexts, like with ControlAwaiter from Stephen's blog or ContextSwitcher from this question. Yet this is not considered a good practice, AFAIU.

It'd be interesting to see some other practical and useful examples of custom awaiters, which still would not harm code readability and maintainability.

Community
  • 1
  • 1
noseratio
  • 59,932
  • 34
  • 208
  • 486
  • 1
    List questions (in this case asking for a list of all possible uses of custom awaiters) are inherently not well suited for SO. Such questions don't lend themselves to a specific, concrete, verifiable correct answer. – Servy Oct 23 '13 at 03:47
  • @Servy, would it be OK if I change it from *some other* to *any*, besides `await task.WithCulture()`? – noseratio Oct 23 '13 at 03:50
  • No, that wouldn't make a difference. – Servy Oct 23 '13 at 04:10
  • 2
    Judging from the votes, a lot of people are interested in this question. The question is quite specific, it even includes an example of an answer (thanks by the way!) that answers a common SO question about TPLs (how to flow Culture). – Panagiotis Kanavos Oct 23 '13 at 08:40
  • @PanagiotisKanavos Popularity is *reliant* when considering whether a question should be closed or not. Just because a question is popular doesn't make it appropriate for the site. And no, it's not specific. Any possible custom task awaiter is quite broad; there's nothing specific about it. – Servy Oct 23 '13 at 14:56
  • @Servy the deeper you delve in a subject, what seemed ambiguous becomes rather specific and important. Stephen just gave a great answer to the question – Panagiotis Kanavos Oct 23 '13 at 15:02
  • @PanagiotisKanavos He added three items to the list. Someone else could come along and add two more or one more, or feel that one or more of his doesn't belong, etc. The fact remains that the question cannot have a single correct answer; it can never be complete; it will always be an incomplete and ever changing list. Such questions are not well suited for SO's model, and as such it has been determined that they should be closed. If you would like to ask such questions you should simply do so in another context more suitable for such questions. – Servy Oct 23 '13 at 15:04

1 Answers1

7

There are very few realistic use cases for custom awaiters.

However, there are a handful of examples out there, which seem to fit into one of these categories:

  1. Avoiding Task for performance reasons. The Windows Store platform exposes its (unmanaged) asynchronous operations with custom awaitables. Another example is Stephen Toub's awaitable wrapper for the specialized Socket asynchronous API used in high-traffic memory-intensive scenarios.
  2. Modifying the behavior of existing awaits. E.g., ConfigureAwait(false) or the WithCurrentCulture you mentioned.
  3. Enabling reuse of an awaitable. The "event awaiter" type in this blog post satisfies one await per event raised. In contrast, tasks can only complete once.

Task.Yield also uses a custom awaitable, but it seems to be in a category all its own.

Personally, I avoid custom awaitables. Usually category (1) is only considered as a premature optimization. Category (2) is interesting conceptually but if you explore it out, you'll find that the behavior modifiers don't compose well. Category (3) is also interesting but more controversial IMO because the completion semantics may be surprising.

Stephen Cleary
  • 437,863
  • 77
  • 675
  • 810