1、restTemplate超时配置
通过定义ClientHttpRequestFactory工厂并配置超时时间初始化restTemplate。RestTemplate默认也是用的ClientHttpRequestFactory的。
public RestTemplate iRestTemplate() {
SimpleClientHttpRequestFactory httpClientFactory= new SimpleClientHttpRequestFactory();
(2000);
(10000);
return new RestTemplate(httpClientFactory);
}
2、支持连接池配置
默认的ClientHttpRequestFactory使用的是HttpUrlConnection,本身不支持连接池。当需要启用连接池提高吞吐量或者减少请求响应时间,替换掉默认的ClientHttpRequestFactory,如Apache HttpComponents HttpClient。
@Bean
public RestTemplate restTemplate(@Qualifier("clientHttpRequestFactory") ClientHttpRequestFactory factory) {
RestTemplate restTemplate = new RestTemplate(factory);
().set(1,
new StringHttpMessageConverter(("UTF-8")));
return restTemplate;
}
@Bean(name = "clientHttpRequestFactory")
public ClientHttpRequestFactory clientHttpRequestFactory(HttpClient client) {
HttpComponentsClientHttpRequestFactory clientHttpRequestFactory = new
HttpComponentsClientHttpRequestFactory(client);
(());
(());
(());
return clientHttpRequestFactory;
}
@Bean
public HttpClient httpClient() {
HttpClientBuilder httpClientBuilder = ();
try {
// 针对https协议相关配置
SSLContext sslContext = ("SSL");// 获取一个SSLContext实例
TrustManager[] trustAllCerts = {new InsecureTrustManager()};
(null, trustAllCerts, new ());// 初始化SSLContext实例
//设置信任ssl访问
(sslContext);
HostnameVerifier hostnameVerifier = ;
SSLConnectionSocketFactory sslConnectionSocketFactory = new SSLConnectionSocketFactory(sslContext, hostnameVerifier);
Registry<ConnectionSocketFactory> socketFactoryRegistry = RegistryBuilder.<ConnectionSocketFactory>create()
// 注册http和https请求
.register("http", ())
.register("https", sslConnectionSocketFactory).build();
PoolingHttpClientConnectionManager poolingHttpClientConnectionManager = new PoolingHttpClientConnectionManager(socketFactoryRegistry);
(());
(());
(poolingHttpClientConnectionManager);
(new DefaultHttpRequestRetryHandler((), true));
//设置默认请求头
List<Header> headers = getDefaultHeaders();
(headers);
();
((), );
CloseableHttpClient httpClient = ();
().addShutdownHook(new Thread(() -> {
try {
();
} catch (IOException e) {
("close http client error.", e);
}
}));
return httpClient;
} catch (Exception e) {
("HttpClient create error.", e);
}
return null;
}
private List<Header> getDefaultHeaders() {
List<Header> headers = new ArrayList<>();
(new BasicHeader("Connection", "Keep-Alive"));
return headers;
}
class InsecureTrustManager implements X509TrustManager {
@Override
public void checkServerTrusted(X509Certificate[] arg0, String arg1) throws CertificateException {}
@Override
public void checkClientTrusted(X509Certificate[] x509Certificates, String s) throws CertificateException {}
/**
* 返回受信任的X509证书数组
*/
@Override
public X509Certificate[] getAcceptedIssuers() {
return null;
}
}
public class HttpClientProperties {
private int readTimeout;
private int connectTimeout;
private int acquireConnectionTimeout;
private int maxConnection;
private int maxConnectionRoute;
private int retryTimes;
private int idleTime;
}
3、响应状态错误码处理
默认实现,如果是4xx或者5xx,请求响应的时候会抛出异常:
/**
* #handleError()
*/
protected void handleError(ClientHttpResponse response, HttpStatus statusCode) throws IOException {
String statusText = ();
HttpHeaders headers = ();
byte[] body = getResponseBody(response);
Charset charset = getCharset(response);
String message = getErrorMessage((), statusText, body, charset);
switch (()) {
case CLIENT_ERROR:
throw (message, statusCode, statusText, headers, body, charset);
case SERVER_ERROR:
throw (message, statusCode, statusText, headers, body, charset);
default:
throw new UnknownHttpStatusCodeException(message, (), statusText, headers, body, charset);
}
}
在一些场景中,某些接口可能会通过不同的状态码来返回不同的错误信息,不是返回200的状态码,在消息体使用code等字段来标识,如果是4xx或者5xx的时候不希望抛异常,而由我们自己获取判断处理,可以如下方式定义:
@Bean
public RestTemplate restTemplate() {
RestTemplate restTemplate = new RestTemplate();
().set(1,
new StringHttpMessageConverter(("UTF-8")));
(new ResponseErrorHandler() {
@Override
public boolean hasError(ClientHttpResponse response) throws IOException {
return false;
}
@Override
public void handleError(ClientHttpResponse response) throws IOException {
}
});
return restTemplate;
}