117 lines
4.0 KiB
Java
117 lines
4.0 KiB
Java
package com.knowledge.base.infrastructure.util;
|
||
|
||
import com.fasterxml.jackson.core.type.TypeReference;
|
||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||
import lombok.extern.slf4j.Slf4j;
|
||
import okhttp3.*;
|
||
import org.springframework.stereotype.Component;
|
||
|
||
import java.io.IOException;
|
||
import java.util.Map;
|
||
import java.util.concurrent.TimeUnit;
|
||
|
||
/**
|
||
* OkHttp封装的 HTTP 客户端工具类(支持 JSON POST、GET、Token注入、泛型反序列化、流式请求)
|
||
*/
|
||
@Slf4j
|
||
@Component
|
||
public class HttpHelper {
|
||
|
||
private final OkHttpClient client;
|
||
private final ObjectMapper objectMapper;
|
||
|
||
public HttpHelper() {
|
||
this.client = new OkHttpClient.Builder()
|
||
.connectTimeout(60, TimeUnit.SECONDS)
|
||
.readTimeout(300, TimeUnit.SECONDS)
|
||
.build();
|
||
this.objectMapper = new ObjectMapper();
|
||
}
|
||
|
||
/**
|
||
* 发送 POST JSON 请求,自动反序列化为 Map
|
||
*/
|
||
public Map<String, Object> postJson(String url, Map<String, Object> body, String token) throws IOException {
|
||
Request request = buildJsonRequest(url, body, token, "POST");
|
||
return executeJson(request);
|
||
}
|
||
|
||
/**
|
||
* 发送 GET 请求,自动反序列化为 Map
|
||
*/
|
||
public Map<String, Object> get(String url, String token) throws IOException {
|
||
Request request = buildJsonRequest(url, null, token, "GET");
|
||
return executeJson(request);
|
||
}
|
||
|
||
/**
|
||
* 流式 POST 请求,返回 Response 实例,调用方负责关闭 response.body().close()
|
||
*/
|
||
public Response postStream(String url, Map<String, Object> body, String token) throws IOException {
|
||
String json = objectMapper.writeValueAsString(body);
|
||
RequestBody requestBody = RequestBody.create(json, MediaType.get("application/json; charset=utf-8"));
|
||
|
||
Request request = new Request.Builder()
|
||
.url(url)
|
||
.addHeader("Authorization", token)
|
||
.addHeader("Accept", "text/event-stream")
|
||
.addHeader("Connection", "keep-alive")
|
||
.post(requestBody)
|
||
.build();
|
||
|
||
return client.newCall(request).execute();
|
||
}
|
||
|
||
/**
|
||
* 构建 JSON 类型的 Request 请求
|
||
*/
|
||
private Request buildJsonRequest(String url, Map<String, Object> body, String token, String method) throws IOException {
|
||
RequestBody requestBody = null;
|
||
if (body != null) {
|
||
String json = objectMapper.writeValueAsString(body);
|
||
requestBody = RequestBody.create(json, MediaType.get("application/json; charset=utf-8"));
|
||
}
|
||
|
||
Request.Builder builder = new Request.Builder().url(url);
|
||
if (token != null && !token.isBlank()) {
|
||
builder.header("Authorization", "Bearer " + token);
|
||
}
|
||
|
||
switch (method.toUpperCase()) {
|
||
case "POST":
|
||
builder.post(requestBody != null ? requestBody : RequestBody.create(new byte[0]));
|
||
break;
|
||
case "GET":
|
||
builder.get();
|
||
break;
|
||
case "PUT":
|
||
builder.put(requestBody);
|
||
break;
|
||
case "DELETE":
|
||
if (requestBody != null) {
|
||
builder.delete(requestBody);
|
||
} else {
|
||
builder.delete();
|
||
}
|
||
break;
|
||
default:
|
||
throw new IllegalArgumentException("不支持的请求方法:" + method);
|
||
}
|
||
|
||
return builder.build();
|
||
}
|
||
|
||
/**
|
||
* 执行请求并解析为 Map
|
||
*/
|
||
private Map<String, Object> executeJson(Request request) throws IOException {
|
||
try (Response response = client.newCall(request).execute()) {
|
||
if (!response.isSuccessful()) {
|
||
throw new IOException("请求失败: " + response.code() + " - " + response.message());
|
||
}
|
||
String json = response.body().string();
|
||
return objectMapper.readValue(json, new TypeReference<>() {});
|
||
}
|
||
}
|
||
}
|