ASP.net HttpRequest上的静态HttpClient线程安全

前端之家收集整理的这篇文章主要介绍了ASP.net HttpRequest上的静态HttpClient线程安全前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我们正在为HttpClient创建一个包装器.因为我们将遵循 https://github.com/mspnp/performance-optimization性能优化指南.我们希望避免反模式 – 该文档中提到的不正确的实例化.我将此指南提交给我的团队使用静态HttpClient.我得到的反馈是线程安全性.每个请求都有一个包含用户声明的标头.由于我有一个静态的HttpClient,它是否是线程安全的?如果我们同时有多个请求命中代码(例如GET),那么设置标题是否会出现竞争条件?我们的实施如下.
  1. public class HttpClientHelper{
  2. private static readonly HttpClient _HttpClient;
  3. static HttpClientHelper() {
  4. HttpClient = new HttpClient();
  5. HttpClient.Timeout = TimeSpan.FromMinutes(SOME_CONFIG_VALUE);
  6. }
  7.  
  8. public async Task<HttpResponseMessage> CallHttpClientPostAsync(string requestUri,HttpContent requestBody)
  9. {
  10. AddHttpRequestHeader(httpClient);
  11. var response = await httpClient.PostAsync(requestUri,requestBody); //Potential thread synchronization issue???
  12. return response;
  13. }
  14.  
  15. public HttpResponseMessage CallHttpClientGet(string requestUri)
  16. {
  17. AddHttpRequestHeader(httpClient);
  18. var response = httpClient.GetAsync(requestUri).Result; //Potential thread synchronization issue???
  19. return response;
  20. }
  21.  
  22. private void AddHttpRequestHeader(HttpClient client)
  23. {
  24. string HeaderName = "CorrelationId";
  25. client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue(Properties.Settings.Default.HttpClientAuthHeaderScheme,GetTokenFromClaims()); //Race condition???
  26. if (client.DefaultRequestHeaders.Contains(HeaderName))
  27. client.DefaultRequestHeaders.Remove(HeaderName);
  28. client.DefaultRequestHeaders.Add(HeaderName,Trace.CorrelationManager.ActivityId.ToString());
  29. }

}

解决方法

你的团队是正确的,这远非线程安全.考虑这种情况:

>线程A将CorrelationId标头设置为“foo”.
>线程B将CorrelationId标头设置为“bar”.
>线程A发送请求,其中包含线程B的CorrelationId.

更好的方法是使用CallXXX方法创建新的HttpRequestMessage对象,并在其上设置标题,并使用HttpClient.SendAsync进行调用.

请记住,重新使用HttpClient实例仅在您对同一主机进行多次调用时才有用.

猜你在找的asp.Net相关文章