Based on my own testing, the content will not be transferred until you start reading the content stream and you are correct that the call to Task.Result is a blocking call, but in itself it is a synchronization point. But it does not block the preliminary buffer of all content, it is blocked only until the content begins to arrive from the server.
Thus, an infinite flow will not be blocked for an infinite amount of time. Thus, trying to get the stream asynchronously might be considered redundant, especially if your header processing is relatively short. But if you want, you can always process the headers while the content stream is being processed in another task. Something like this will accomplish this.
static void Main(string[] args) { var url = "http://somesite.com/bigdownloadfile.zip"; var client = new HttpClient(); var request = new HttpRequestMessage(HttpMethod.Get, url); var getTask = client.SendAsync(request, HttpCompletionOption.ResponseHeadersRead); Task contentDownloadTask = null; var continuation = getTask.ContinueWith((t) => { contentDownloadTask = Task.Run(() => { var resultStream = t.Result.Content.ReadAsStreamAsync().Result; resultStream.CopyTo(File.Create("output.dat")); }); Console.WriteLine("Got {0} headers", t.Result.Headers.Count()); Console.WriteLine("Blocking after fetching headers, press any key to continue..."); Console.ReadKey(true); }); continuation.Wait(); contentDownloadTask.Wait(); Console.WriteLine("Finished downloading {0} bytes", new FileInfo("output.dat").Length); Console.WriteLine("Finished, press any key to exit"); Console.ReadKey(true); }
Note that there is no need to check whether part of the headers is complete, you explicitly indicated that with the HttpCompletionOption.ResponseHeadersRead option. The SendAsync task SendAsync not continue until headers are received.
source share