#httpclient #connection-pooling #resttemplate #apache-httpcomponents
#httpclient #соединение-объединение #resttemplate #apache-httpcomponents
Вопрос:
Я добавляю PoolingHttpClientConnectionManager в нашу службу загрузки Spring, которая в настоящее время использует RestTemplate и CloseableHttpClient для выполнения запросов. Служба использует Apache httpcomponents 4.5.
Что произойдет, если произойдет временное отключение сети? Удаляются ли поврежденные соединения из пула? Или пул заполняется плохими соединениями во время отключения? После завершения отключения пул восстанавливается самостоятельно? Или мне нужно написать код для их обнаружения и удаления из пула?
Вот код, который у меня есть на данный момент:
@Bean
public CloseableHttpClient closeableHttpClient() {
CloseableHttpClient client = HttpClients.custom()
.setDefaultRequestConfig(getDefaultRequestConfig())
.setConnectionManager(poolingHttpClientConnectionManager())
.setKeepAliveStrategy(getConnectionKeepAliveStrategy())
.setRetryHandler(getHttpRequestRetryHandler())
.build();
return client;
}
@Bean
public PoolingHttpClientConnectionManager poolingHttpClientConnectionManager() {
Registry<ConnectionSocketFactory> socketFactoryRegistry = getSocketFactoryRegistry();
PoolingHttpClientConnectionManager poolingConnectionManager = new PoolingHttpClientConnectionManager(socketFactoryRegistry);
poolingConnectionManager.setMaxTotal(maxTotalConnections);
poolingConnectionManager.setDefaultMaxPerRoute(maxRouteConnections);
return poolingConnectionManager;
}
@Bean
public Runnable idleConnectionMonitor(PoolingHttpClientConnectionManager pool) {
return new Runnable() {
@Override
@Scheduled(fixedDelay = 20000)
public void run() {
if (pool != null) {
pool.closeExpiredConnections();
pool.closeIdleConnections(idleConnectionCloseTime, TimeUnit.MILLISECONDS);
}
}
};
}
@Bean
public TaskScheduler taskScheduler() {
ThreadPoolTaskScheduler scheduler = new ThreadPoolTaskScheduler();
scheduler.setThreadNamePrefix("idleMonitor");
scheduler.setPoolSize(idleMonitorPoolSize);
return scheduler;
}
private RequestConfig getDefaultRequestConfig() {
RequestConfig requestConfig = RequestConfig.custom()
.setConnectTimeout(establishConnectionTimeout)
.setConnectionRequestTimeout(fetchConnectionTimeout)
.setSocketTimeout(socketInactivityTimeout)
.build();
return requestConfig;
}
private Registry<ConnectionSocketFactory> getSocketFactoryRegistry() {
SSLConnectionSocketFactory socketFactory;
socketFactory = new SSLConnectionSocketFactory(getSSLContext(), new String[] { sslProtocol }, null, new DefaultHostnameVerifier());
Registry<ConnectionSocketFactory> socketFactoryRegistry = RegistryBuilder
.<ConnectionSocketFactory> create().register("https", socketFactory)
.build();
return socketFactoryRegistry;
}
private SSLContext getSSLContext() {
TrustStrategy acceptingTrustStrategy = null;
try {
KeyStore keyStore = KeyStore.getInstance(keyStoreType);
keyStore.load(new FileInputStream(new File(keyStoreFile)), keyStorePwd.toCharArray());
return new SSLContextBuilder()
.loadTrustMaterial(keyStore, acceptingTrustStrategy)
.loadKeyMaterial(keyStore, keyStorePwd.toCharArray())
.build();
} catch (KeyStoreException | IOException | NoSuchAlgorithmException | CertificateException | KeyManagementException | UnrecoverableKeyException e) {
throw new RuntimeException(e);
}
}
private ConnectionKeepAliveStrategy getConnectionKeepAliveStrategy() {
return (httpResponse, httpContext) -> {
HeaderIterator headerIterator = httpResponse.headerIterator(HTTP.CONN_KEEP_ALIVE);
HeaderElementIterator elementIterator = new BasicHeaderElementIterator(headerIterator);
while (elementIterator.hasNext()) {
HeaderElement element = elementIterator.nextElement();
String param = element.getName();
String value = element.getValue();
if (value != null amp;amp; param.equalsIgnoreCase("timeout")) {
return Long.parseLong(value) * 1000; // convert to ms
}
}
return defaultKeepAliveTime;
};
}
private DefaultHttpRequestRetryHandler getHttpRequestRetryHandler() {
return new DefaultHttpRequestRetryHandler(httprequestRetryCount, false);
}
Ответ №1:
Эти соединения становятся недействительными или «устаревшими». Если HttpClient настроен для проверки соединений перед их использованием для выполнения запросов, устаревшие соединения будут обнаружены и удалены.