簡體   English   中英

如何使用HttpClient()存儲來自多個異步請求的返回數據,直到所有請求完成?

[英]How to store return data from multiple async requests using HttpClient() until all requests complete?

我需要遍歷一系列來自網址的數據發布請求。 請求需要異步。 檢查所有返回已完成的最佳方法是什么,並存儲該數據直到返回所有數據? 喜歡使用HttpClient()

代碼段:

     HttpContent httpContent = new FormUrlEncodedContent(postData);           
     HttpResponseMessage response =  client.PostAsync("/mydata", httpContent).Result; 

     var responsecode = (int)response.StatusCode; 

     if (response.IsSuccessStatusCode)
     {
         var responseBodyAsText = await response.Content.ReadAsStringAsync();
         return responseBodyAsText;
     }
     else
     {
         return responsecode +" " +response.ReasonPhrase; 
     }

`

好吧,首先,請記住,你在這里遇到了一個異步問題:

 HttpContent httpContent = new FormUrlEncodedContent(postData);           

 // whoops! .Result makes this line synchronous.
 HttpResponseMessage response =  client.PostAsync("/mydata", httpContent).Result;

 var responsecode = (int)response.StatusCode; 

 if (response.IsSuccessStatusCode)
 {
     var responseBodyAsText = await response.Content.ReadAsStringAsync();
     return responseBodyAsText;
 }
 else
 {
     return responsecode +" " +response.ReasonPhrase; 
 }

接下來,由於HttpClient為您提供了一個Task<HttpResponseMessage> ,您似乎希望將所有響應作為字符串,例如,一個Task<IEnumerable<string>> ,對吧? 我們可以輕松編寫一個函數來將Task<HttpResponseMessage>轉換為Task<string>

public async Task<string> ReadResultAsync(Task<HttpResponseMessage> responseTask)
{
    var response = await responseTask;

    var responsecode = (int)response.StatusCode; 

    if (response.IsSuccessStatusCode)
    {
        var responseBodyAsText = await response.Content.ReadAsStringAsync();

        return responseBodyAsText;
    }
    else
    {
        return responsecode + " " + response.ReasonPhrase; 
    }
}

現在假設你有一些發布數據的集合,你需要轉換成這個異步字符串集合,稱為myData

// bear in mind, this code doesn't (necessarily) need to be in a
//  method marked "async". If you want to await on resultsTask, though,
//  it would need to be in an async method.

var tasks = myData
    .Select(x => new FormUrlEncodedContent(x)) //  IEnumerable<FormUrlEncodedContent>
    .Select(x => client.PostAsync("/mydata", x)) // IEnumerable<Task<HttpResponseMessage>>
    .Select(x => ReadResultAsync(x)) // IEnumerable<Task<string>>
    .ToArray(); // Task<string>[]

var resultsTask = Task.WhenAll(tasks); // here is Task<string[]>

寫一個異步函數來激發你的帖子數據(我剛用過你的代碼,請添加正確的錯誤/異常處理):

async Task<string> PostDataAsync(Dictionary<string, string> postData)
{
    var httpContent = new FormUrlEncodedContent(postData);           
    var response = await client.PostAsync("/mydata", httpContent).ConfigureAwait(false); 

    var responsecode = (int)response.StatusCode; 

    if (response.IsSuccessStatusCode)
    {
        var responseBodyAsText = await response.Content.ReadAsStringAsync().ConfigureAwait(false);
        return responseBodyAsText;
    }
    else
    {
       return responsecode +" " +response.ReasonPhrase; 
    }
}

現在,假設您有一個帖子數據列表'List> postDataCollection`,然后構建您的請求

var postRequests = postDataCollection.Select(pd => PostDataAsync(pd)).ToArray();

然后等待所有人完成

var postResponses = await Task.WhenAll(postRequests);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM