【问题标题】:Difference between configuring connection via PoolingHttpClientConnectionManager and HttpClientBuilder通过 PoolingHttpClientConnectionManager 和 HttpClientBuilder 配置连接的区别
【发布时间】:2020-09-07 12:41:33
【问题描述】:

我有两个 restTemplate 配置。一种是通过 PoolingHttpClientConnectionManager 配置连接,另一种是直接通过 HttpClientBuilder 配置。两者都使用 HttpClient 进行连接相关配置。

下面是一个HttpClientBuilder


        final HttpClientBuilder httpClientBuilder = HttpClientBuilder.create();
        httpClientBuilder.setMaxConnTotal(maxConnPerRoute);
        httpClientBuilder.setMaxConnPerRoute(maxConnPerRoute);
        httpClientBuilder.setConnectionReuseStrategy(new NoConnectionReuseStrategy());

        final HttpComponentsClientHttpRequestFactory httpComponentsClientHttpRequestFactory
            = new HttpComponentsClientHttpRequestFactory();

        httpComponentsClientHttpRequestFactory.setConnectTimeout(connectionTimeout);
        httpComponentsClientHttpRequestFactory.setReadTimeout(connectionTimeout);
        httpComponentsClientHttpRequestFactory.setHttpClient(httpClientBuilder.build());

        final BufferingClientHttpRequestFactory bufferingClientHttpRequestFactory =
            new BufferingClientHttpRequestFactory(httpComponentsClientHttpRequestFactory);
       final RestTemplate restTemplate = new RestTemplate(bufferingClientHttpRequestFactory);

这里我们直接设置httpClient之类的

httpComponentsClientHttpRequestFactory.setHttpClient(httpClientBuilder.build());

下面是 PoolingHttpClientConnectionManager

   private ClientHttpRequestFactory clientHttpRequestFactory(final ConnectionPooling connectionPooling) {
        final PoolingHttpClientConnectionManager connectionManager = new PoolingHttpClientConnectionManager();
       
        connectionManager.setDefaultMaxPerRoute(connectionPooling.getMaxConnections());

        connectionManager.setMaxTotal(connectionPooling.getMaxConnections());

        final HttpClient httpclient = HttpClientBuilder
            .create()
            .setConnectionManager(connectionManager)
            .build();

        final HttpComponentsClientHttpRequestFactory connectionFactory =
            new HttpComponentsClientHttpRequestFactory(httpclient);
        connectionFactory.setConnectTimeout(connectionPooling.getConnectionTimeout());
        connectionFactory.setReadTimeout(connectionPooling.getReadTimeout());
        connectionFactory.setConnectionRequestTimeout(connectionPooling.getConnectionRequestTimeoutMillis());

        final IdleConnectionEvictor idleConnectionTimeoutThread =
            new IdleConnectionEvictor(connectionManager,
                connectionPooling.getIdleConnectionCheckMillis(), TimeUnit.MILLISECONDS,
                connectionPooling.getIdleConnectionTimeoutMillis(), TimeUnit.MILLISECONDS);
        idleConnectionTimeoutThread.start();

        return new BufferingClientHttpRequestFactory(connectionFactory);
    }

我们在这里设置


        final HttpClient httpclient = HttpClientBuilder
            .create()
            .setConnectionManager(connectionManager)
            .build();

这两种配置有什么区别?两者的反应会不同吗?

【问题讨论】:

    标签: java spring httpclient apache-httpclient-4.x


    【解决方案1】:

    他们的行为会有所不同。由于您的第一个 HttpClientBuilder 没有设置连接管理器,因此它是线程不安全的。出于多种原因,拥有像您的第二个示例这样的连接管理器很有用。 Apache 文档很好地总结了连接管理器的好处here

    HTTP 连接管理器的目的是充当新 HTTP 连接的工厂,管理持久连接的生命周期并同步对持久连接的访问​​,确保一次只有一个线程可以访问连接.

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-12-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多