package com.sckw.robot.util; import com.alibaba.fastjson2.JSONObject; import lombok.extern.slf4j.Slf4j; import okhttp3.*; import org.apache.commons.lang3.StringUtils; import javax.net.ssl.SSLContext; import javax.net.ssl.SSLSocketFactory; import javax.net.ssl.TrustManager; import javax.net.ssl.X509TrustManager; import java.io.IOException; import java.net.URLEncoder; import java.nio.charset.StandardCharsets; import java.security.SecureRandom; import java.security.cert.X509Certificate; import java.util.LinkedHashMap; import java.util.Map; import java.util.concurrent.Semaphore; import java.util.concurrent.TimeUnit; @Slf4j public class OkHttpUtils { private static volatile OkHttpClient okHttpClient; private static final Semaphore semaphore = new Semaphore(0); private final Map headerMap = new LinkedHashMap<>(); private final Map paraMap = new LinkedHashMap<>(); private final Map bodyParaMap = new LinkedHashMap<>(); private String bodyParaString; private String url; private Request.Builder request; static { try { TrustManager[] trustManagers = buildTrustManagers(); okHttpClient = new OkHttpClient.Builder() .connectTimeout(15, TimeUnit.SECONDS) .writeTimeout(20, TimeUnit.SECONDS) .readTimeout(20, TimeUnit.SECONDS) .sslSocketFactory(createSSLSocketFactory(trustManagers), (X509TrustManager) trustManagers[0]) .hostnameVerifier((hostName, session) -> true) .retryOnConnectionFailure(true) .build(); } catch (Exception e) { log.error("Failed to initialize OkHttpClient", e); } } public static OkHttpUtils builder() { return new OkHttpUtils(); } public OkHttpUtils url(String url) { this.url = url; return this; } public OkHttpUtils addPara(String key, String value) { this.paraMap.put(key, value); return this; } public OkHttpUtils addBodyPara(String key, String value) { this.bodyParaMap.put(key, value); return this; } public OkHttpUtils addBodyJsonStr(String string) { this.bodyParaString = string; return this; } public OkHttpUtils addHeader(String key, String value) { this.headerMap.put(key, value); return this; } public OkHttpUtils addHeaderMap(Map map) { this.headerMap.putAll(map); return this; } public OkHttpUtils get() { this.request = new Request.Builder().get().url(buildUrl()); return this; } public OkHttpUtils post(boolean isJsonPost) { RequestBody requestBody; if (isJsonPost) { String json = StringUtils.isNotBlank(bodyParaString) ? bodyParaString : JSONObject.toJSONString(bodyParaMap); requestBody = RequestBody.create(json, MediaType.parse("application/json; charset=utf-8")); } else { FormBody.Builder formBody = new FormBody.Builder(); bodyParaMap.forEach(formBody::add); requestBody = formBody.build(); } this.request = new Request.Builder().post(requestBody).url(buildUrl()); return this; } private String buildUrl() { if (paraMap.isEmpty()) return this.url; StringBuilder urlBuilder = new StringBuilder(this.url).append("?"); paraMap.forEach((key, value) -> { try { urlBuilder.append(URLEncoder.encode(key, StandardCharsets.UTF_8)) .append("=") .append(URLEncoder.encode(value, StandardCharsets.UTF_8)) .append("&"); } catch (Exception e) { log.warn("Parameter encoding failed: {}={}", key, value, e); } }); urlBuilder.deleteCharAt(urlBuilder.length() - 1); return urlBuilder.toString(); } public String sync() { setHeaders(); try (Response response = okHttpClient.newCall(request.build()).execute()) { if (response.body() != null) { return response.body().string(); } } catch (IOException e) { log.error("Sync request failed", e); } return null; } public String async() { final StringBuilder buffer = new StringBuilder(); setHeaders(); okHttpClient.newCall(request.build()).enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { log.error("Async request failed", e); buffer.append("请求失败:").append(e.getMessage()); semaphore.release(); } @Override public void onResponse(Call call, Response response) throws IOException { if (response.body() != null) { buffer.append(response.body().string()); } semaphore.release(); } }); try { semaphore.acquire(); } catch (InterruptedException e) { Thread.currentThread().interrupt(); log.error("Semaphore interrupted", e); } return buffer.toString(); } public void async(ICallBack callBack) { setHeaders(); okHttpClient.newCall(request.build()).enqueue(new Callback() { @Override public void onFailure(Call call, IOException e) { callBack.onFailure(call, e.getMessage()); } @Override public void onResponse(Call call, Response response) throws IOException { if (response.body() != null) { callBack.onSuccessful(call, response.body().string()); } } }); } private void setHeaders() { headerMap.forEach((k, v) -> request.addHeader(k, v)); } private static SSLSocketFactory createSSLSocketFactory(TrustManager[] trustAllCerts) throws Exception { SSLContext sc = SSLContext.getInstance("SSL"); sc.init(null, trustAllCerts, new SecureRandom()); return sc.getSocketFactory(); } private static TrustManager[] buildTrustManagers() { return new TrustManager[]{ new X509TrustManager() { @Override public void checkClientTrusted(X509Certificate[] chain, String authType) {} @Override public void checkServerTrusted(X509Certificate[] chain, String authType) {} @Override public X509Certificate[] getAcceptedIssuers() { return new X509Certificate[0]; } } }; } public interface ICallBack { void onSuccessful(Call call, String data); void onFailure(Call call, String errorMsg); } }