Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

HttpClient GetAsync hanging

I have an identical method in two of my WP8 apps. Given the same url and same device, the method works on one app, but not the other. In the failing app, GetAsync is hanging after it is called. No time out, no exception.

Here is the method in question.

    private async Task<Byte[]> DownloadData(string uri)
    {
        byte[] myDataBuffer = null;
        var newUri = new Uri(uri, UriKind.Absolute);
        var myWebClient = new HttpClient();

        var response = await myWebClient.GetAsync(newUri);
        if (response.Content.Headers.ContentType.MediaType == "text/plain"
            || response.Content.Headers.ContentLength < 200)
        {
            throw new Exception(await response.Content.ReadAsStringAsync());
        }
        myDataBuffer = await response.Content.ReadAsByteArrayAsync();
        return myDataBuffer;
    }

This happens every time on one particular app, but not the other. Same device. Has anybody ever experienced this behavior? The url is valid, the code is identical. Is there a project setting somewhere that might affect this? I'm using the HttpClient in another portion of the failing app and it works there.

I can change the code to use a HttpWebRequest and that works fine. Just not the HttpClient.

I just now discovered that if I copy the method into my button_click handler, it works there too. Is there a problem having this method inside a separate class? That seems odd to me.

update

What seems to be breaking it is multiple layers of async methods calling it. Within the class I have

    public override byte[] GetImageData(string imageUri)
    {
        return GetImageDataAsync(imageUri).Result;
    }

    public async Task<byte[]> GetImageDataAsync(string imageUri)
    {
        return await DownloadData(imageUri);
    }

from my button_click handler, I'm calling GetImageData(uri). If I change that to await GetImageDataAsync(uri) it works.

Is Result not the correct property to reference in GetImageData?

Here's a test url "http://www.rei.com/pix/common/REI_logo.gif"

like image 908
earthling Avatar asked Oct 25 '13 02:10

earthling


1 Answers

Calling Result or Wait can cause deadlocks, as I explain on my blog.

The proper way to solve this is to use await. I assume that there's some reason you want to synchronously block, but it's better to use await and find a way to make it work in your code.

like image 177
Stephen Cleary Avatar answered Nov 12 '22 18:11

Stephen Cleary