1.yml配置:
http:
pool:
maxTotal: 500
defaultMaxPerRoute: 300
connectTimeout: 10000
connectionRequestTimeout: 500
socketTimeout: 15000
validateAfterInactivity: 30000
2.HTTP配置类:
/**
* 说明:
* Http连接池属性。
*
* @author zlx
* @create: 2021-03-14
*/
@Data
public class HttpPoolProperties {
private Integer maxTotal;
private Integer defaultMaxPerRoute;
private Integer connectTimeout;
private Integer connectionRequestTimeout;
private Integer socketTimeout;
private Integer validateAfterInactivity;
/**
* 说明:
* 抽象的http client。
*
* @author zlx
* @create: 2021-03-14
*
*/
public class AbstractHttpClientConfig {
/**
* 说明:
* 构建一个基于连接池的apache http client;
*
* @param httpPoolProperties
* @return
*/
public HttpClient buildHttpClient(HttpPoolProperties httpPoolProperties) {
// 1.
Registry<ConnectionSocketFactory> registry = RegistryBuilder.<ConnectionSocketFactory>create()
.register("http", PlainConnectionSocketFactory.getSocketFactory())
.register("https", SSLConnectionSocketFactory.getSocketFactory())
.build();
// 2. http池properties:
PoolingHttpClientConnectionManager connectionManager = new PoolingHttpClientConnectionManager(registry);
connectionManager.setMaxTotal(httpPoolProperties.getMaxTotal());
connectionManager.setDefaultMaxPerRoute(httpPoolProperties.getDefaultMaxPerRoute());
connectionManager.setValidateAfterInactivity(httpPoolProperties.getValidateAfterInactivity());
RequestConfig requestConfig = RequestConfig.custom()
.setSocketTimeout(httpPoolProperties.getSocketTimeout())
.setConnectTimeout(httpPoolProperties.getConnectTimeout())
.setConnectionRequestTimeout(httpPoolProperties.getConnectionRequestTimeout())
.build();
return HttpClientBuilder.create()
.setDefaultRequestConfig(requestConfig)
.setConnectionManager(connectionManager)
.build();
}
/**
* 说明:
* 构建RestTemplate,并设置默认的字符集;
*
* @param clientHttpRequestFactory
* @return
*/
public RestTemplate buildRestTemplate(ClientHttpRequestFactory clientHttpRequestFactory, Charset charset) {
// 1. + httpClient pool:
RestTemplate restTemplate = new RestTemplate(clientHttpRequestFactory);
// 2. msg handler:
this.messageConverterHandler(restTemplate, charset);
return restTemplate;
}
/** 重新设置StringHttpMessageConverter字符集为UTF-8,解决中文乱码问题 */
public void messageConverterHandler(RestTemplate restTemplate, Charset charset) {
// 1. 消息转化器,字符集处理:
List<HttpMessageConverter<?>> converterList = restTemplate.getMessageConverters();
// 2. 重置:
HttpMessageConverter<?> converterTarget = null;
for (HttpMessageConverter<?> item : converterList) {
if (StringHttpMessageConverter.class == item.getClass()) {
converterTarget = item;
break;
}
}
if (null != converterTarget) {
converterList.remove(converterTarget);
}
converterList.add(1, new StringHttpMessageConverter(charset));
}
}
/**
* 说明:
* Http客户端注册。
* <p>
* 基于Apache Http client的RestTemplate
*
* @author zlx
* @create: 2021-03-14
*/
@Configuration
public class HttpClientConfig extends AbstractHttpClientConfig {
@Bean(name = "poolProperties")
@ConfigurationProperties(prefix = "http.pool")
public HttpPoolProperties poolProperties() {
return new HttpPoolProperties();
}
@Bean(value = "httpClient")
public HttpClient httpClient(@Qualifier("poolProperties") HttpPoolProperties httpPoolProperties) {
return this.buildHttpClient(httpPoolProperties);
}
@Bean(name = "httpRequestFactory")
public ClientHttpRequestFactory httpRequestFactory(@Qualifier("httpClient") HttpClient httpClient) {
HttpComponentsClientHttpRequestFactory httpRequestFactory = new HttpComponentsClientHttpRequestFactory(httpClient);
httpRequestFactory.setConnectionRequestTimeout(10000);
httpRequestFactory.setConnectTimeout(10000);
httpRequestFactory.setReadTimeout(10000);
return httpRequestFactory;
}
@Bean(name = "restTemplate")
public RestTemplate restTemplate(@Qualifier("httpRequestFactory") ClientHttpRequestFactory clientHttpRequestFactory) {
RestTemplate restTemplate = this.buildRestTemplate(clientHttpRequestFactory, StandardCharsets.UTF_8);
return restTemplate;
}
}
3.HTTP工具类:
/**
* @author zlx
* @create: 2021-03-14
*/
@Component
@Slf4j
public class HttpClientUtil {
@Qualifier("restTemplate")
@Autowired
private RestTemplate httpRestTemplate;
/**
* get请求
*
* @param url 地址
* @param uriVariables URI参数
* @return
*/
public String doGet(@NotNull String url,
Map<String, String> paramMap,
Object... uriVariables) {
return doGet(url, paramMap, String.class, null, uriVariables);
}
/**
* 不需要Header GET请求
*
* @param url 地址
* @param paramMap 参数
* @param responseType response类型
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doGet(@NotNull String url,
Map<String, String> paramMap,
@NotNull Class<T> responseType,
Object... uriVariables) {
return doGet(url, paramMap, responseType, null, uriVariables);
}
/**
* GET请求
*
* @param url 地址
* @param paramMap 参数
* @param responseType response类型
* @param headerMap Header
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doGet(@NotNull String url,
Map<String, String> paramMap,
@NotNull Class<T> responseType,
Map<String, String> headerMap,
Object... uriVariables) {
return doMethod(url, null, paramMap, responseType, headerMap, HttpMethod.GET, uriVariables);
}
/**
* 不需要Header POST
*
* @param url 地址
* @param object BODY
* @param responseType response类型
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doPost(@NotNull String url,
Object object,
Map<String, String> paramMap,
@NotNull Class<T> responseType,
Object... uriVariables) {
return doPost(url, object, paramMap, responseType, null, uriVariables);
}
/**
* POST
*
* @param url 地址
* @param object BODY
* @param paramMap Parameters
* @param responseType response类型
* @param headerMap Header
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doPost(@NotNull String url,
Object object,
Map<String, String> paramMap,
@NotNull Class<T> responseType,
Map<String, String> headerMap,
Object... uriVariables) {
return doMethod(url, object, paramMap, responseType, headerMap, HttpMethod.POST, uriVariables);
}
/**
* 不需要Header PUT请求
*
* @param url 地址
* @param object BODY
* @param paramMap Parameters
* @param responseType response类型
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doPut(@NotNull String url,
Object object,
Map<String, String> paramMap,
@NotNull Class<T> responseType,
Object... uriVariables) {
return doPut(url, object, paramMap, responseType, null, uriVariables);
}
/**
* PUT请求
*
* @param url 地址
* @param object BODY
* @param paramMap Parameters
* @param responseType response类型
* @param headerMap Header
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doPut(@NotNull String url,
Object object,
Map<String, String> paramMap,
@NotNull Class<T> responseType,
Map<String, String> headerMap,
Object... uriVariables) {
return doMethod(url, object, paramMap, responseType, headerMap, HttpMethod.PUT, uriVariables);
}
/**
* DELETE 请求
*
* @param url
* @param responseType response类型
* @param paramMap Parameters
* @param headerMap Header
* @param uriVariables URI参数
* @param <T>
* @return
*/
public <T> T doDelete(@NotNull String url,
@NotNull Class<T> responseType,
Map<String, String> paramMap,
Map<String, String> headerMap,
Object... uriVariables) {
return doMethod(url, null, paramMap, responseType, headerMap, HttpMethod.DELETE, uriVariables);
}
/**
* @param url 地址
* @param object BODY
* @param responseType response类型
* @param headerMap Header
* @param method Http方法
* @param uriVariables URI参数
* @param <T> responseType实体
* @return
*/
public <T> T doMethod(@NotNull String url,
Object object,
Map<String, ?> paramMap,
@NotNull Class<T> responseType,
Map<String, String> headerMap,
HttpMethod method,
Object... uriVariables) {
HttpEntity httpEntity = this.createHttpEntity(object, headerMap);
// 出现异常打印响应body处理
httpRestTemplate.setErrorHandler(new RestResponseErrorHandler());
url = getUrlParamsByMap(url, paramMap);
// 发出请求:
ResponseEntity<T> responseEntity =
httpRestTemplate.exchange(url, method, httpEntity, responseType, uriVariables);
return this.getEntityFromHttpResponse(responseEntity);
}
/**
* Map转url参数
*
* @param url
* @param map
* @return
*/
private String getUrlParamsByMap(String url, Map<String, ?> map) {
if (map == null || map.size() < 1) {
return url;
}
StringBuffer stringBuffer = new StringBuffer();
stringBuffer.append(url);
String wenHao = "?";
String yuMark = "&";
if (url.contains(wenHao)) {
stringBuffer.append(yuMark);
} else {
stringBuffer.append(wenHao);
}
for (Map.Entry<String, ?> entry : map.entrySet()) {
stringBuffer.append(entry.getKey() + "=" + entry.getValue());
stringBuffer.append(yuMark);
}
String str = stringBuffer.toString();
if (str.endsWith(yuMark)) {
str = StringUtils.substringBeforeLast(str, yuMark);
}
return str;
}
/**
* 说明:
* 创建HTTP请求实体(header + entity)
*
* @param body
* @param headerMap
* @param <T>
* @return
*/
private <T> HttpEntity createHttpEntity(T body, Map<String, String> headerMap) {
// 1. 生成Http Header:
HttpHeaders headers = createHttpHeaders(headerMap);
return new HttpEntity(body, headers);
}
/**
* 创建 Header
*
* @param headerMap
* @return
*/
private HttpHeaders createHttpHeaders(Map<String, String> headerMap) {
HttpHeaders headers = new HttpHeaders();
if (null != headerMap) {
headerMap.forEach((key, value) -> {
headers.set(key, value);
});
}
return headers;
}
/**
* @param responseEntity
* @param <T>
* @return
* @throws HttpException
*/
private <T> T getEntityFromHttpResponse(ResponseEntity<T> responseEntity) {
// 3.提取用户信息:
if (responseEntity.getStatusCodeValue() != HttpStatus.OK.value()) {
throw new HHSJException(responseEntity.getBody().toString());
}
return responseEntity.getBody();
}
}