HttpClient 5 连接释放问题:爬虫场景下如何正确释放连接?
解决HttpClient 5异步爬虫中SimpleHttpResponse的连接释放问题
核心逻辑
HttpClient 5的异步客户端(CloseableHttpAsyncClient)是靠连接池管理器自动处理连接的复用和释放的,根本不需要找专门的“释放连接”方法——但前提是你得把响应内容处理到位,别占着连接不放。
具体操作步骤
- 必须处理响应实体:如果响应带了内容(比如
SimpleHttpResponse.getBody()),要么把内容读完,要么直接关掉流:- 用工具类一次性读取:比如
EntityUtils.toString(response.getBody()),这个方法读完会自动关流 - 手动关流:要是你自己处理输入流,处理完记得调用
response.getBody().close()
- 用工具类一次性读取:比如
- 别攥着响应对象不放:处理完响应就赶紧丢掉
SimpleHttpResponse的引用,让GC回收它,这样连接管理器才能正常把连接放回池里 - 配置靠谱的连接池参数:创建客户端的时候,通过
PoolingAsyncClientConnectionManager设好最大连接数、空闲超时这些,比如:PoolingAsyncClientConnectionManager connManager = PoolingAsyncClientConnectionManagerBuilder.create() .setMaxConnTotal(100) .setMaxConnPerRoute(20) .setDefaultConnectionConfig(ConnectionConfig.custom() .setSocketTimeout(Timeout.ofSeconds(10)) .setConnectTimeout(Timeout.ofSeconds(5)) .build()) .setDefaultPoolConfig(PoolConfig.custom() .setIdleTimeout(Timeout.ofSeconds(30)) .build()) .build(); CloseableHttpAsyncClient client = HttpAsyncClients.custom() .setConnectionManager(connManager) .build();
避坑提醒
绝对别碰CloseableHttpAsyncClient.close(),这会直接把整个客户端和连接池都关了,完全不符合爬虫长期运行的需求。只要你把响应实体处理好,连接管理器会自动把连接放回池子给下一次请求复用。
内容的提问来源于stack exchange,提问作者何子洋
相关产品推荐
相关产品推荐

