如何确定给定“HttpClient"实例的最大同时连接数 [英] How to determine the maximum number of simultaneous connections for a given `HttpClient` instance

查看:24
本文介绍了如何确定给定“HttpClient"实例的最大同时连接数的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个 Servlet,它在启动时构建一个 HttpClient 实例.它与服务请求时使用的协作模块共享此客户端.我想使用 FutureRequestExecutionService API 内协作模块可以轻松地并发发送一些请求.这需要使用 HttpClient 实例以及 ExecutorService 实例.教程建议设置ExecutorService 使用与HttpClient 的最大并发连接数相同的线程数.

I have a Servlet that builds an HttpClient instance when it starts. It shares this client with a collaborating module used when servicing requests. I would like to use the FutureRequestExecutionService API within the collaborating module to easily send some requests concurrently. This requires using an HttpClient instance along with an ExecutorService instance. The tutorial recommends setting the ExecutorService to use the same number of threads as the HttpClient's maximum number of concurrent connections.

futureRequestExecutionService 的构造函数采用任何现有的 httpClient 实例和一个 ExecutorService 实例.配置两者时,将最大连接数与您将要使用的线程数保持一致非常重要.当线程数多于连接数时,连接可能会开始超时,因为没有可用连接.当连接数多于线程数时,futureRequestExecutionService 不会全部使用.

The constructor for the futureRequestExecutionService takes any existing httpClient instance and an ExecutorService instance. When configuring both, it is important to align the maximum number of connections with the number of threads you are going to use. When there are more threads than connections, the connections may start timing out because there are no available connections. When there are more connections than threads, the futureRequestExecutionService will not use all of them.

我认为协作模块应该是为其并发请求创建 ExecutorService 的模块.这种情况下的问题是协作模块不一定知道它应该使用多少线程,因为它不知道 HttpClient 已配置为允许多少个同时连接.

I thought that the collaborating module should be the one creating the ExecutorService for its concurrent requests. The problem in that case is that the collaborating module does not necessarily know how many threads it should be using since it doesn't know how many simultaneous connections the HttpClient has been configured to allow.

我知道我可以使用 HttpClientgetConnectionManager 方法,但从 4.3 开始,这已被弃用.那么,确定给定 HttpClient 将允许多少个同时连接的推荐方法是什么?我怀疑错误的答案是保存对用于构建 HttpClientConnectionManager 对象的引用并将其与协作模块一起传递或定义某种全局常量.也许我问错了问题.

I know I could use HttpClient's getConnectionManager method, but as of 4.3 this is deprecated. So then what is the recommended way of ascertaining how many simultaneous connections a given HttpClient will allow? I suspect that the wrong answer is to save a reference to the ConnectionManager object used to build the HttpClient and pass it along with the collaborating module or to define some kind of global constant. Maybe I'm asking the wrong question.

也许我应该同时创建 HttpClientExecutorServiceFutureRequestExecutionService 对象,然后只传递FutureRequestExecutionService 实例到要发出 HTTP 请求的模块使用共享客户端.我想以一种与 HttpClient 的作者的意图一致的方式来做到这一点;我只是不确定在这种情况下到底是什么.

Perhaps I should instead create the HttpClient, ExecutorService, and FutureRequestExecutionService objects all at the same time and then pass just the FutureRequestExecutionService instance to the modules that want to make HTTP requests using a shared client. I'd like to do this in a manner that is consistent with the intent of the authors of HttpClient; I'm just not sure in this case what that is exactly.

澄清一下,HttpClient 实例是使用 HttpClientBuilder 创建的,该 HttpClientBuilder 为它的连接管理器.但是,这与创建 PoolingHttpClientConnectionManagerFutureRequestExecutionService 的范围不同.我开始怀疑它们应该一起创建,然后使用 FutureRequestExecutionService 实例而不是传递 HttpClient 实例.

To clarify, the HttpClient instance is created using an HttpClientBuilder that has a PoolingHttpClientConnectionManager set for its connection manager. However, this does not happen in the same scope as the creation of the PoolingHttpClientConnectionManager and FutureRequestExecutionService. I am starting to suspect that they should be created together and then instead of passing the HttpClient instance around, use the FutureRequestExecutionService instance.

推荐答案

这里的重点是避免出现太多工作线程最终争用太少连接从而导致性能瓶颈的情况.每个路由的工作线程和连接数/总限制只需要合理:例如,12 个工作线程和 10 个连接或 10 个工作线程和 12 个连接,但不像 12 个工作线程和 2 个连接.

The main point here is to avoid situations when too many worker threads end up contending for too few connections thus causing a performance bottleneck. The number of worker threads and connections per route / total limits just need to be about reasonable: say, 12 workers and 10 connections or 10 workers and 12 connections but not like 12 workers and 2 connections.

说了这么多,要回答您的问题,我不建议将 PoolingHttpClientConnectionManagerFutureRequestExecutionService 接线代码紧密耦合.对我来说,更好的方法应该是拥有一个简单的 POJO 或什至是一个表示 HTTP 服务配置的哈希映射,您的所有接线代码都应该依赖它,而不是直接耦合各种实现类.

Having said all that, to answer your question I would not recommend tightly coupling of PoolingHttpClientConnectionManager and the FutureRequestExecutionService wiring code. To me a better approach should be having a simple POJO or even a hash map representing HTTP service configuration that all your wiring code should depend upon instead of direct coupling of various implementation classes.

这方面的事情

static class MyHttpServiceConfig {
    int workerNum = 10;
};

MyHttpServiceConfig config = new MyHttpServiceConfig();

CloseableHttpClient client = HttpClients.custom()
        .setMaxConnPerRoute(config.workerNum)
        .build();

ExecutorService executor = Executors.newFixedThreadPool(config.workerNum);

FutureRequestExecutionService executionService = new FutureRequestExecutionService(
         client, executor);

这篇关于如何确定给定“HttpClient"实例的最大同时连接数的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆