Question

In one of MVA videos i saw next construction:

static void Main(string[] args)
{
    Action testAction = async () =>
    {
        Console.WriteLine("In");
        await Task.Delay(100);
        Console.WriteLine("After first delay");
        await Task.Delay(100);
        Console.WriteLine("After second delay");
    };

    testAction.Invoke();
}

Result of execution will be:

In
Press any key to continue . . .

It's perfectly compiles, but right now i don't see any way to await it. I might put Thread.Sleep or Console.ReadKey after invocation, but that's not what i want.

So how this delegate should be modified to become awaitable?(or at least how can i track that execution completed?)

Is there are any practical usage of such delegates?

Was it helpful?

Solution

In order for something to be awaited, it has to be awaitable. As void is not so, you cannot await on any Action delegate.

An awaitable is any type that implements a GetAwaiter method, which returns a type that implements either INotifyCompletion or ICriticalNotifyCompletion, like Task and Task<T>, for example.

If you want to wait on a delegate, use Func<Task>, which is an equivalent to a named method with the following signature:

public Task Func()

So, in order to await, change your method to:

static void Main(string[] args)
{
    Func<Task> testFunc = async () =>
    {
        Console.WriteLine("In");
        await Task.Delay(100);
        Console.WriteLine("First delay");
        await Task.Delay(100);
        Console.WriteLine("Second delay");
    };
}

And now you can await it:

await testFunc();

OTHER TIPS

Recently I found that NUnit able to await async voidtests. Here is good description how it works: How does nunit successfully wait for async void methods to complete?

You won't use it in regular tasks, but it's good to know that it is possible

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top