HttpUtils工具类

前言

一般在开发中,我们对接其他系统,最常用的就是使用http请求,去调用其他接口获取数据,下面记录了一个httputils工具类

一、httputils工具类

示例代码:

java 复制代码
package com.centerm.cpay.acps.common.util;


import com.alibaba.fastjson.JSON;
import lombok.extern.slf4j.Slf4j;
import org.apache.http.HttpEntity;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.config.Registry;
import org.apache.http.config.RegistryBuilder;
import org.apache.http.config.SocketConfig;
import org.apache.http.conn.DnsResolver;
import org.apache.http.conn.HttpConnectionFactory;
import org.apache.http.conn.ManagedHttpClientConnection;
import org.apache.http.conn.routing.HttpRoute;
import org.apache.http.conn.socket.ConnectionSocketFactory;
import org.apache.http.conn.socket.PlainConnectionSocketFactory;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.entity.ContentType;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.DefaultConnectionReuseStrategy;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.DefaultConnectionKeepAliveStrategy;
import org.apache.http.impl.client.DefaultHttpRequestRetryHandler;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.ManagedHttpClientConnectionFactory;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.apache.http.impl.conn.SystemDefaultDnsResolver;
import org.apache.http.impl.io.DefaultHttpRequestWriterFactory;
import org.apache.http.impl.io.DefaultHttpResponseParserFactory;
import org.apache.http.util.EntityUtils;

import java.nio.charset.Charset;
import java.util.Map;
import java.util.concurrent.TimeUnit;

/**
 * http请求封装
 *
 * @author lh
 * @date 2022-09-23
 */
@Slf4j
public class HttpUtils {

    /**
     * 默认请求类型
     */
    private static final String DEFAULT_CONTENT_TYPE = "application/json";

    /**
     * 默认编码
     */
    private static final String DEFAULT_ENCODING = "utf-8";

    /**
     * GBK编码
     */
    private static final String GBK_ENCODING = "GBK";

    /**
     * 默认超时时间
     */
    private static final int DEFAULT_TIME_OUT = 60;

    private static PoolingHttpClientConnectionManager manager = null;

    private static CloseableHttpClient httpClient = null;

    /**
     * 获取httpclient对象
     *
     * @return
     */
    public static synchronized CloseableHttpClient getHttpClient(int timeOut) {
        if (null == httpClient) {
            log.info("============================================创建");
            // 注册访问协议相关的socket工厂
            Registry<ConnectionSocketFactory> socketFactoryRegistry = RegistryBuilder.<ConnectionSocketFactory>create()
                    .register("http", PlainConnectionSocketFactory.INSTANCE)
                    .register("https", SSLConnectionSocketFactory.getSystemSocketFactory())
                    .build();

            // httpConnection工厂
            HttpConnectionFactory<HttpRoute, ManagedHttpClientConnection> connectionFactory =
                    new ManagedHttpClientConnectionFactory(DefaultHttpRequestWriterFactory.INSTANCE
                            , DefaultHttpResponseParserFactory.INSTANCE);

            // DNS解析器
            DnsResolver dnsResolver = SystemDefaultDnsResolver.INSTANCE;
            // 创建池化连接管理器
            manager = new PoolingHttpClientConnectionManager(socketFactoryRegistry, connectionFactory, dnsResolver);
            // socket配置
            SocketConfig socketConfig = SocketConfig.custom().setTcpNoDelay(true).build();
            manager.setDefaultSocketConfig(socketConfig);
            // 连接池最大连接数
            manager.setMaxTotal(300);
            manager.setDefaultMaxPerRoute(200);
            // 5s检测一次连接池连接
            manager.setValidateAfterInactivity(5 * 1000);
            // 默认请求配置
            RequestConfig requestConfig = RequestConfig.custom()
                    // 连接超时时间
                    .setConnectTimeout(timeOut * 1000)
                    // 等待数据超时时间
                    .setSocketTimeout(timeOut * 1000)
                    // 从连接池获取连接超时时间
                    .setConnectionRequestTimeout(timeOut * 1000)
                    .build();
            // 创建httpclient
            httpClient = HttpClients.custom()
                    .setConnectionManager(manager)
                    // 连接池不共享
                    .setConnectionManagerShared(false)
                    // 定期回收空闲连接
                    .evictIdleConnections(timeOut, TimeUnit.SECONDS)
                    // 定期回收过期连接
                    .evictExpiredConnections()
                    .setConnectionTimeToLive(timeOut, TimeUnit.SECONDS)
                    // 设置默认请求
                    .setDefaultRequestConfig(requestConfig)
                    // 连接重用策略
                    .setConnectionReuseStrategy(DefaultConnectionReuseStrategy.INSTANCE)
                    // 长连接配置
                    .setKeepAliveStrategy(DefaultConnectionKeepAliveStrategy.INSTANCE)
                    // 设置重试次数
                    .setRetryHandler(new DefaultHttpRequestRetryHandler(0, false))
                    .build();

            // jvm停止或重启时,关闭连接池释放连接
            Runtime.getRuntime().addShutdownHook(new Thread() {

                @Override
                public void run() {
                    try {
                        if (null != httpClient) {
                            httpClient.close();
                        }
                    } catch (Exception e) {
                        log.error("httpclient关闭异常:{}", e);
                    }
                }
            });
        }
        return httpClient;
    }

    /**
     * http请求
     *
     * @param url
     * @param params
     * @return
     */
    public static String httpPost(String url, Map params,Map<String,String> headers) {
        log.info("POST请求url:{}", url);
        log.info("POST请求参数:{}",JSON.toJSONString(params));
        CloseableHttpClient httpClient = getHttpClient(DEFAULT_TIME_OUT);
        HttpPost httpPost = new HttpPost(url);

        if (null != headers){
            for (String key:headers.keySet()){
                httpPost.setHeader(key,headers.get(key).toString());
            }
        }

        String json = JSON.toJSONString(params);
        StringEntity stringEntity = new StringEntity(json, DEFAULT_ENCODING);
        stringEntity.setContentEncoding(DEFAULT_ENCODING);
        httpPost.setEntity(stringEntity);
        String result = null;
        try (CloseableHttpResponse response = httpClient.execute(httpPost);) {
            HttpEntity entity = response.getEntity();
            if (null != entity) {
                result = EntityUtils.toString(entity, ContentType.getOrDefault(entity).getCharset());
                EntityUtils.consume(entity);
            }
        } catch (Exception e) {
            log.error("接口请求异常:{}", e);
        }
        return result;
    }

    /**
     * http请求(POST请求,GBK编码)
     *
     * @param url
     * @param params
     * @return
     */
    public static String httpPostGBK(String url, Map params,Map<String,String> headers) {
        log.info("POST请求url:{}", url);
        log.info("POST请求参数:{}",JSON.toJSONString(params));
        CloseableHttpClient httpClient = getHttpClient(DEFAULT_TIME_OUT);
        HttpPost httpPost = new HttpPost(url);

        if (null != headers){
            for (String key:headers.keySet()){
                httpPost.setHeader(key,headers.get(key).toString());
            }
        }

        String json = JSON.toJSONString(params);
        StringEntity stringEntity = new StringEntity(json, DEFAULT_ENCODING);
        stringEntity.setContentEncoding(DEFAULT_ENCODING);
        httpPost.setEntity(stringEntity);
        String result = null;
        try (CloseableHttpResponse response = httpClient.execute(httpPost);) {
            HttpEntity entity = response.getEntity();
            if (null != entity) {
//                result = EntityUtils.toString(entity, ContentType.getOrDefault(entity).getCharset());
                result = EntityUtils.toString(entity, Charset.defaultCharset());
                EntityUtils.consume(entity);
            }
        } catch (Exception e) {
            log.error("接口请求异常:{}", e);
        }
        return result;
    }

    /**
     * http请求(POST请求,GBK编码)
     *
     * @param url
     * @param params
     * @param headers
     * @param timeOut 超时时间
     * @return
     */
    public static String httpPostGBK(String url, Map params, Map<String, String> headers, int timeOut) {
        log.info("POST请求url:{}", url);
        log.info("POST请求参数:{}", JSON.toJSONString(params));
        CloseableHttpClient httpClient = getHttpClient(timeOut);
        HttpPost httpPost = new HttpPost(url);

        if (null != headers) {
            for (String key : headers.keySet()) {
                httpPost.setHeader(key, headers.get(key).toString());
            }
        }

        String json = JSON.toJSONString(params);
        StringEntity stringEntity = new StringEntity(json, DEFAULT_ENCODING);
        stringEntity.setContentEncoding(DEFAULT_ENCODING);
        httpPost.setEntity(stringEntity);
        String result = null;
        try (CloseableHttpResponse response = httpClient.execute(httpPost);) {
            HttpEntity entity = response.getEntity();
            if (null != entity) {
//                result = EntityUtils.toString(entity, ContentType.getOrDefault(entity).getCharset());
                result = EntityUtils.toString(entity, Charset.defaultCharset());
                EntityUtils.consume(entity);
            }
        } catch (Exception e) {
            log.error("接口请求异常:{}", e);
        }
        return result;
    }

    /**
     * http请求
     *
     * @param url
     * @return
     */
    public static String httpGet(String url) {
        log.info("请求url:{}", url);
        CloseableHttpClient httpClient = getHttpClient(DEFAULT_TIME_OUT);
        HttpGet httpGet = new HttpGet(url);
        String result = null;
        try (CloseableHttpResponse response = httpClient.execute(httpGet);) {
            HttpEntity entity = response.getEntity();
            if (null != entity) {
                result = EntityUtils.toString(entity, ContentType.getOrDefault(entity).getCharset());
                EntityUtils.consume(entity);
            }
        } catch (Exception e) {
            log.error("接口请求异常:{}", e);
        }
        return result;
    }
}
相关推荐
六千江山16 分钟前
从字符串中提取符合规则的汽车车牌
java
33255_40857_2805924 分钟前
从韩立结婴看Java进阶:一个10年老码农的修仙式成长指南
java
赵星星52025 分钟前
透彻理解Java中的深拷贝与浅拷贝:从误区到最佳实践
java·后端
心月狐的流火号26 分钟前
Java CompletableFuture 核心API
java
黑客影儿36 分钟前
Java技术总监的成长之路(技术干货分享)
java·jvm·后端·程序人生·spring·tomcat·maven
京东云开发者41 分钟前
EXCEL导入—设计与思考
java·架构
Warren981 小时前
软件测试-Selenium学习笔记
java·javascript·笔记·学习·selenium·测试工具·安全
没有bug.的程序员1 小时前
JVM 运行时数据区详解:内存模型与对象生命周期全景解析
java·jvm·运行时数据区·内存模型·对象生命周期
一语长情2 小时前
Netty流量整形:保障微服务通信稳定性的关键策略
java·后端·架构
盖世英雄酱581362 小时前
第一个RAG项目遇到的问题
java·spring boot