i feel pretty confused by the output i'm getting out of what i believe is purely async program. As you can observe there are no obvious anti patterns (i hope) and blocking calls.
slowURL
throttles server response for 10 seconds. I did confirm by running calls to the local server with 10 second timeout that FetchSlowAsync
method call effectively blocks the main thread for 10 seconds when running the code in console.
I expected that TaskScheduler would schedule the calls not in a sequential manner but by always randomly determining the method call order. Alas the output is always deterministic.
FetchSlowAsync start
FetchSlowAsync got data!
FetchAsync start
FetchAsync got data!
FetchBingAsync start
FetchBingAsync got data!
All done!
My question is: what prompts FetchSlowAsync
to block rather than TaskScheduler to perform a context switch to another async method and get back to it when it's done?
And the next question that follows the former: why all the methods in async Main
are executed in the same order as they are being called given the async execution model is concurrent?
using static System.Console;
using System.Net.Http;
using System.Threading.Tasks;
class Start
{
const string serviceURL = "https://google.com";
const string slowDown = "http://slowwly.robertomurray.co.uk/delay/10000/url/";
const string slowURL = slowDown + serviceURL;
const string OkURL = serviceURL;
static async Task FetchSlowAsync()
{
await Console.Out.WriteLineAsync("FetchSlowAsync start");
await new HttpClient().GetStringAsync(slowURL); //BLOCKS MAIN THREAD FOR 10 seconds
await Console.Out.WriteLineAsync("FetchSlowAsync got data!");
}
static async Task FetchAsync()
{
await Console.Out.WriteLineAsync("FetchAsync start");
await new HttpClient().GetStringAsync(OkURL);
await Console.Out.WriteLineAsync("FetchAsync got data!");
}
static async Task FetchBingAsync()
{
await Console.Out.WriteLineAsync("FetchBingAsync start");
await new HttpClient().GetStringAsync("https://bing.com");
await Console.Out.WriteLineAsync("FetchBingAsync got data!");
}
static async Task Main()
{
await FetchSlowAsync();
await FetchBingAsync();
await FetchAsync();
await System.Console.Out.WriteLineAsync("All done!");
}
}