如何等待特定的 http 状态代码 - C#

How to wait for a specific http status code - C#

我已经实施了这段代码,从现在开始 2 周了。从那时起,我试图改进我的代码,因为有时 Task.Delay 方法不足以等待第 3 方 API 发送我需要的正确的 http 状态代码。 (他们处理的时间比我预期的要长得多。)

var url = string.Format(_azureFormRecognizerConfig.RequestUrl, _azureFormRecognizerConfig.ResourceUrl, modelId);
var content = new StringContent(JsonConvert.SerializeObject(new { source = storagePath }), Encoding.UTF8, _azureFormRecognizerConfig.MediaType);

using (var httpClient = new HttpClient())
{
    // Request headers
    httpClient.DefaultRequestHeaders.Add(_azureFormRecognizerConfig.SubscriptionType, _azureFormRecognizerConfig.SubcriptionKey);

    using (var response = await httpClient.PostAsync(url, content))
    {
        try
        {
            response.EnsureSuccessStatusCode();
            responseLocationUri = response.Headers.GetValues("Operation-Location").FirstOrDefault();
        }
        catch (HttpRequestException ex)
        {
            _logger.Information($"Error in httpclient { ex.Message } ");
        }
    }

    Task.Delay(20000).Wait();

    using (var response = await httpClient.GetAsync(responseLocationUri))
    {
        try
        {
            response.EnsureSuccessStatusCode();
            responseBody = await response.Content.ReadAsStringAsync();

        }
        catch (HttpRequestException ex)
        {
            _logger.Information($"Error in httpclient { ex.Message } ");
        }
    }

    _logger.Information($"Response headers { responseBody }");
}

正如您在我的代码中看到的那样,我延迟了 20,000 毫秒(20 秒)只是为了处理逻辑并期望在该时间内完成该过程并且我可以获得正确的响应和值。

无论如何,我如何改进它或让它像回调或我仍然没有发现的东西一样工作。

谢谢!

我假设 API 是这样工作的:

  1. 你做了一个 Post,这会在服务器上开始一些计算。
  2. 您使用从 Post 返回的 url 进行获取。如果计算完成,这将成功,否则失败。

要管理它,您应该使用轮询,即

while(true){
    using (var response = await httpClient.GetAsync(responseLocationUri)){
         if(response.IsSuccessStatusCode){
               // Handle success case
               return someResult;
          }
          await Task.Delay(1000); // Wait 1s between each attempt
     }
 }

您可能还应该添加超时或检查返回的错误代码的类型,以避免在服务器从不响应时永远轮询。

如果您可以更改 API,使用某种 callback 而不是轮询也可能有意义,因为回调通常会导致使用较少的资源。