2
votes

I've spent many hours trying to figure this one out, but unfortunately to no avail. I'd be grateful for any help.

The problem is that the PostAsync call blocks event though I use await and ConfigureAwait(false). The below handler is called on the UI thread:

private async void OnApplicationLaunching(object sender, LaunchingEventArgs e)
{
    using (var httpClient = new HttpClient())
    {
        var content = new List<KeyValuePair<string, string>>();

        var urlEncodedContent = new FormUrlEncodedContent(content);

        await httpClient.PostAsync("url address", urlEncodedContent).ConfigureAwait(false);
    }
}

Edit 1

  • I use WindowsPhone 8.0 silverlight
  • In my opinion it is a deadlock. The execution is blocked until the exception appears with "task got canceled" message
  • I am not interested in "fire and forget". I need to be sure that the data is sent before allowing further execution.

Edit 2

Here's another code sample which does not differ alot from previous one, but beter resembles the code samples from Stephen's blog

Section "Preventing the Deadlock" in http://blog.stephencleary.com/2012/07/dont-block-on-async-code.html

Section "Avoiding Context" in http://blog.stephencleary.com/2012/02/async-and-await.html

private async void OnApplicationLaunching(object sender, LaunchingEventArgs e)
{
    await this.SendSth();

    // here I want to know for sure that data has already been sent
}

private async Task SendSth()
{
    using (var httpClient = new HttpClient())
    {
        var content = new List<KeyValuePair<string, string>>();

        var urlEncodedContent = new FormUrlEncodedContent(content);

        await httpClient.PostAsync("some url", urlEncodedContent).ConfigureAwait(false);
    }
}

By the way, thanks Stephen for your great articles. They help alot.

1
are you using WPF, UWP windows forms?Kasper Due
What exactly do you mean by "blocks"? Is it a deadlock, or does it just pause for a second or so? Also, is this on the .NET desktop?Stephen Cleary
I am not interested in "fire and forget". I need to be sure that the data is sent before allowing further execution: Sounds to me like you do want it to block. So what's the problem? Or in other words, you don't want the application to launch (because that's what your method is for) until the data is sent.sstan
Nobody knows the answer? I mean, I'm really grateful even for the comments that appeared. I'm just suprised that such a typical scenario is not working and nobody even can say why. Did i make something stupid in my example? Or am I ommiting sth important? Or maybe i do not understand exactly how async await should work in this case? Any help would be valuable.x x

1 Answers

-1
votes

From my understanding of asynchronous programming in C#, ConfigureAwait should be called in library.

See this article from Stephen Cleary. Check this also.