async void Main()
{
var cp=new ConentProxy();
Console.WriteLine(await cp.GetAsync());
Console.ReadLine();
}
// Define other methods and classes here
public class HttpsContentProvider : IContentProvider
{
private static HttpClient hc=new HttpClient();
//**@No.1**
public async Task<string> GetAsync() {
return await hc.GetStringAsync("https://www.stackoverflow.com").ConfigureAwait(false);
}
}
public class DefaultContentProvider : IContentProvider
{
//**@No.2**
public async Task<string> GetAsync()
{
return await Task.FromResult("Default").ConfigureAwait(false);
}
}
public interface IContentProvider
{
Task<string> GetAsync();
}
public class ConentProxy : IContentProvider
{
public static int conentType = int.Parse(ConfigurationManager.AppSettings["UseHttps"] ?? "0");
//**@No.3**
public async Task<string> GetAsync()
{
switch (conentType)
{
case 0:return await new HttpsContentProvider().GetAsync();
default:return await new DefaultContentProvider().GetAsync();
}
}
}
In the code above, there are three "async" with a "@No." tag ahead. They are all short methods just one or two lines only.
They can be await without "async" as they return Task
or Task<T>
.
It could be far more than 2 call layer on the No.1 tag in actual code. So there will be many "async"s cascade.
Should I add an "async" to a short method or not ? As I know, there is cost for async
and await
;
Especilly the No.3, it's just a proxy method. The real operation method will block is the HttpClient.GetStringAsync
at @No.1.
=====================================================
After reading the first answer from @dustinmoris, I found the following code in HttpClient
class. It makes me confused that there is no async
and no ConfigureAwait(false)
, which is the same as other methods of HttpClient
public Task<byte[]> ReadAsByteArrayAsync()
{
this.CheckDisposed();
TaskCompletionSource<byte[]> tcs = new TaskCompletionSource<byte[]>();
this.LoadIntoBufferAsync().ContinueWithStandard((Action<Task>) (task =>
{
if (HttpUtilities.HandleFaultsAndCancelation<byte[]>(task, tcs))
return;
tcs.TrySetResult(this.bufferedContent.ToArray());
}));
return tcs.Task;
}