httpclient async/await or not



我使用一个httpclient实例向rest web api发送多个请求以获取数据。以下是我的代码:

首先,我有一个控制层,它调用数据的数据层。

public class ControlLayer
{
    protected DataLayer dal;
    //constructors here
    public int getInfo1(int param)
    {
      int ret = this.dal.getInfo1(param);
      return ret;
    }
    public int getInfo2(int param)
    {
      int ret = this.dal.getInfo2(param);
      return ret;
    }
}

然后我有了调用webAPI的dataLayer,它看起来是这样的。为了简单起见,我直接使用.result。

public class DataLayer
{
    HttpClient client = new HttpClient();
    string url = "";
    public int getInfo1(int param1)
    {
      int ret=0;
      HttpResponseMessage response = client.GetAsync(url).Result;
      //.... do some work, get the value for ret
      return ret;
    }
    public int getInfo2(int param1)
    {
      int ret = 0;
      HttpResponseMessage response = client.GetAsync(url).Result;
      //.... do some work, get the value for ret
      return ret;
    }
}

我的问题是,我看到一些教程说我们应该避免使用.result,因为它可能会导致死锁。我不确定在我的情况下我需要使用什么async/await?如果我确实需要,我知道我应该一直异步,但我确实希望我的controlLayer是同步的,因为我有其他层调用controlLayer的函数,我不希望所有层的函数都是异步的,结果是Task<>,这是同步而非异步的情况吗?我想念吗某物欢迎提出任何建议。谢谢

我确实希望我的controlLayer是同步的,因为我有其他层调用controlLayer的函数,我不希望所有层的函数都是异步的,结果是Task<>

我建议你重新考虑一下。web请求基本上是异步操作,因此我建议您将"控制层"公开为异步API,并允许async通过代码库中的层"增长"。

然而,如果您真的想要一个同步的API,那么您应该只调用同步API。例如,使用WebClient而不是HttpClient。请勿调用Result以用同步API包装异步API。

如果您的代码是异步的,您只需要使用asyncawait——例如,如果它同时发送多个请求,则在发送请求后执行工作,而不是仅阻塞直到响应到达。

暂时忽略死锁问题-如果您的代码只是同步的,也就是说:每次发送请求时,只需等待响应,然后再执行其他操作,就不需要使用await,可以使用Result。有关类似的辩论,请参阅此问题。或者,您可以使用同步API(如注释和其他答案中建议的WebClient)。

至于与Result相关的死锁,我建议您阅读MSDN上的这篇文章,以便更好地了解发生了什么以及为什么发生。如果你正在编写一个简单的控制台应用程序,你真的不需要担心它(处理它的正确方法是只让Main方法非异步,并在那里使用ResultWait)。

相关内容

最新更新