正确使用 HttpClient

  • 正确使用 HttpClient已关闭评论
  • 160 次浏览
  • A+
所属分类:.NET技术
摘要

其实标题应该叫:在控制台程序中使用IHttpClientFactory以前一直使用的是HttpWebRequest,.NET6工程代码提示已过时,使用HttpClient代替,所以尝试使用HttpClient。经过几天的学习探索,基本掌握了HttpClient的使用方法。


正确使用 HttpClient

其实标题应该叫:在控制台程序中使用IHttpClientFactory

以前一直使用的是HttpWebRequest,.NET6工程代码提示已过时,使用HttpClient代替,所以尝试使用HttpClient。经过几天的学习探索,基本掌握了HttpClient的使用方法。

由于有时会写控制台程序,所以简单封装了一下(写控制台程序时使用,写Web程序时也可以使用但比较另类,一般不用这种方式,注入的方式请搜索别的博客):

using Microsoft.Extensions.DependencyInjection; using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks;  namespace Utils {     /// <summary>     /// HttpClient工厂类     /// </summary>     public class HttpClientFactory     {         private static readonly IHttpClientFactory _httpClientFactory;          static HttpClientFactory()         {             ServiceCollection serviceCollection = new ServiceCollection();             ServiceProvider serviceProvider = serviceCollection.AddHttpClient().BuildServiceProvider();             _httpClientFactory = serviceProvider.GetService<IHttpClientFactory>();         }          public static HttpClient GetClient()         {             return _httpClientFactory.CreateClient();         }     } } 

如何使用

string url = "http://192.168.31.11:5028/Test/Get"; HttpClient httpClient = HttpClientFactory.GetClient(); string strResult = await (await httpClient.GetAsync(url)).Content.ReadAsStringAsync(); 

在控制台程序中使用IHttpClientFactory

需要通过NuGet搜索安装下面两个包:
Microsoft.Extensions.Http
Microsoft.Extensions.DependencyInjection
然后使用上述代码

注意事项

HttpClient虽然有Dispose方法,但千万不要调用Dispose,也千万不要使用using语句,否则会产生大量TIME_WAIT(因为Socket连接等一段时间才会释放),端口用完可就要报错了!
也不要使用全局单例HttpClient,因为这种方式不支持DNS变更。

参考博客

https://www.cnblogs.com/yakniu/p/16331179.html
http://www.manongjc.com/detail/29-vhvbqzxwhlunudu.html
https://www.bilibili.com/read/cv11776829/

======== 以下是旧代码 ===================================================================================================

根据评论所述,下述旧工厂类代码存在的问题

  1. 没有解决DNS过期的问题
  2. 不能限制默认访问头,可能被修改
  3. HttpClient池大小设置成多少也是个问题

使用 HttpClient 注意事项

  1. HttpClient默认最大并发连接数是2
  2. 本机测试(被请求的WebApi部署在本机)HttpClient不会被限制最大并发连接数
  3. 使用HttpClient要写个工厂类,因为HttpClient不能频繁创建
  4. HttpClient类提供的方法是线程安全的

HttpClient 工厂类

using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks;  namespace Factory {     /// <summary>     /// HttpClient工厂类     /// 注意:     /// 1. HttpClient默认最大并发连接数是2     /// 2. 本机测试HttpClient不会被限制最大并发连接数     /// </summary>     public class HttpClientFactory     {         private int _httpClientCount;          private readonly HttpClient[] _httpClientArray;          private int _index = -1;          private readonly object _lock = new object();          private static readonly HttpClientFactory _instance = new HttpClientFactory();          public static HttpClientFactory Instance         {             get             {                 return _instance;             }         }          public HttpClientFactory(int httpClientCount = 50)         {             _httpClientCount = httpClientCount;             _httpClientArray = new HttpClient[_httpClientCount];             for (int i = 0; i < _httpClientCount; i++)             {                 _httpClientArray[i] = new HttpClient();             }         }          public HttpClient Get()         {             lock (_lock)             {                 _index++;                 if (_index == _httpClientCount)                 {                     _index = 0;                 }                 return _httpClientArray[_index];             }         }     } } 

如何使用

string url = "http://192.168.31.11:5028/Test/Get"; HttpClient httpClient = HttpClientFactory.Instance.Get(); string strResult = await (await httpClient.GetAsync(url)).Content.ReadAsStringAsync();