5

New ASP.NET Web API HttpClient has been giving me some strange results. Here is my code:

class Program {

    static async void Main(string[] args) {

        var address = "http://localhost:3895/api/urls";

        Console.WriteLine(await getStringAsync(address));
        Console.ReadLine();

    }

    public static async Task<string> getStringAsync(string uri) {

        var httpClient = new HttpClient();
        return await httpClient.GetStringAsync(uri);
    }
}

This never comes back and the console suddenly appears and disappears. When I change the code as below, it works as it is supposed to:

static void Main(string[] args) {

    var address = "http://localhost:3895/api/urls";

    Console.WriteLine(getString(address));
    Console.ReadLine();

}

public static string getString(string uri) { 

    var httpClient = new HttpClient();

    return httpClient.GetStringAsync(uri).Result;
}

Any idea on what would be the issue?

Robaticus
  • 22,857
  • 5
  • 54
  • 63
tugberk
  • 57,477
  • 67
  • 243
  • 335
  • 1
    That doesn't even compile. An entry point (`Main`) can't be async. It will fail with the CS4009 error. – vcsjones Mar 26 '12 at 19:23
  • @vcsjones In the Async CTP it's allowed (but a bad idea) –  Mar 26 '12 at 19:25
  • 1
    @hvd Interesting. Best that they disallow it now though. – vcsjones Mar 26 '12 at 19:27
  • thanks guys, I was trying to see if the app works. So, the console app is just a test. but good to know that. I will try this somewhere else. – tugberk Mar 26 '12 at 19:32
  • The same idea holds for unit tests. Just make sure to use `async Task` rather than `async void`. The latter is a form of fire-and-forget. –  Mar 27 '12 at 18:43
  • Please refer this answer -- http://stackoverflow.com/a/28518326/3879847 – Ranjithkumar Jan 23 '17 at 10:34

1 Answers1

9

async on Main is disallowed in the VS11/.NET 4.5 compiler, so I'm assuming you're using the Async CTP. If using .NET 4.5 is at all an option, do make the switch.

That aside, the reason it doesn't work is because async, or more generally, tasks, rely on being able to signal some way for the remainder of the code to be executed. It works with .Result because the code runs synchronously, so the problem doesn't apply.

There is no built-in support for console applications, because they don't normally use message loops in the way that for example WinForms does, but you can look at Microsoft Visual Studio Async CTP\Samples\(C# Testing) Unit Testing\AsyncTestUtilities, notably GeneralThreadAffineContext.cs, to get a basic example that works in console applications too.