I'm trying to understand the difference between the various timeout configurations in HttpClient and the simplest way to configure it.
The various options are shown in this code:
RequestConfig requestConfig = RequestConfig.custom()
.setConnectionRequestTimeout(connectionRequestTimeout, TimeUnit.MILLISECONDS)
.setResponseTimeout(responseTimeout, TimeUnit.MILLISECONDS)
.setConnectTimeout(connectTimeout, TimeUnit.MILLISECONDS) // Deprecated - Use {@link ConnectionConfig.Builder#setConnectTimeout(Timeout)}.
.build();
ConnectionConfig connectionConfig = ConnectionConfig.custom()
.setConnectTimeout(connectTimeout, TimeUnit.MILLISECONDS)
.setSocketTimeout(socketTimeout, TimeUnit.MILLISECONDS)
.build();
SocketConfig socketConfig = SocketConfig.custom()
.setSoTimeout(socketTimeout, TimeUnit.MILLISECONDS)
.build();
PoolingHttpClientConnectionManager poolingHttpClientConnectionManager = PoolingHttpClientConnectionManagerBuilder.create()
.setDefaultConnectionConfig(connectionConfig)
.setDefaultSocketConfig(socketConfig)
.build();
HttpClient httpClient = HttpClientBuilder.create()
.setConnectionManager(poolingHttpClientConnectionManager)
.setDefaultRequestConfig(requestConfig)
.build();
My current understanding is this:
ConnectionRequestTimeout
is the time taken to get a connection from the pool - relevant if under load.
ConnectTimeout
is the time taken to establish the connection.
But what is the difference between:
RequestConfig.setResponseTimeout()
ConnectionConfig.setSocketTimeout()
SocketConfig.setSoTimeout()
they all seem to be read / response timeouts for a request. Do I only need to set one of these?
From some limited testing it seems ResponseTimeout
overrides the others possibly implying thats all I need.
In this case it would be nice just to have to use RequestConfig
to set all three but the ConnectTimeout
has been deprecated there and moved to ConnectionConfig
which also contains the SocketTimeout
.
I'm using this with SpringBoot 3 / Spring 6 and the recent removal of the readTimeout
configuration option on HttpComponentsClientHttpRequestFactory
seems to imply its best to set this up directly on the HttpClient.
In your case, setting just ResponseTimeout in RequestConfig will typically cover your needs for managing how long a request waits for a response, making it easier to configure and understand. Here’s a suggested approach to simplify things:
Here’s a simplified configuration:
RequestConfig requestConfig = RequestConfig.custom()
.setConnectionRequestTimeout(connectionRequestTimeout, TimeUnit.MILLISECONDS)
.setResponseTimeout(responseTimeout, TimeUnit.MILLISECONDS)
.build();
ConnectionConfig connectionConfig = ConnectionConfig.custom()
.setConnectTimeout(connectTimeout, TimeUnit.MILLISECONDS)
.build();
PoolingHttpClientConnectionManager poolingHttpClientConnectionManager = PoolingHttpClientConnectionManagerBuilder.create()
.setDefaultConnectionConfig(connectionConfig)
.build();
HttpClient httpClient = HttpClientBuilder.create()
.setConnectionManager(poolingHttpClientConnectionManager)
.setDefaultRequestConfig(requestConfig)
.build();
This approach keeps the configuration centralized and manageable, leveraging ResponseTimeout as your primary timeout, while ensuring ConnectTimeout is properly configured in ConnectionConfig. This setup should work well with Spring Boot 3 / Spring 6, aligning with recent updates in timeout handling.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With