关于 unirest-java-3
面向 Java 8 及以上项目的 Unirest-Java 3.x 参考技能,介绍如何使用 Apache HttpClient 4 构建 HTTP 客户端。内容涵盖请求、响应、配置、模拟测试和缓存。
主要功能
- 01构建多种 HTTP 请求
- 02使用 GSON 映射 JSON 对象
- 03支持 CompletableFuture 异步请求
- 04配置代理、超时和连接池
- 05模拟测试与响应缓存
适用场景
- 01在 Java 项目中调用 REST API
- 02调试 HTTP 客户端请求
- 03为服务配置代理与连接池
- 04缓存响应并处理异步请求
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ full-stack-skills/ java-skills --skill unirest-java-3安装后在 Claude Code 中输入/unirest-java-3确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
agents/openai.yamlreferences/caching.mdconfiguration.mdmocking.mdproxies.mdrequests.mdresponses.md详细介绍
Unirest-Java 3.x 参考(v3.14.5)
本技能介绍适用于 Java 8+ 的 Unirest-Java 3.x HTTP 客户端库。它使用 Apache HttpClient 4 作为 HTTP 引擎,并默认包含 GSON 作为 JSON 解析器。
能力边界
✅ 擅长领域
- 使用流畅 API 构建 HTTP 请求(GET、POST、PUT、DELETE、PATCH)
- 使用内置 GSON 映射 JSON/对象(无需额外依赖)
- 使用 CompletableFuture 发起异步请求(通过 Apache HttpAsyncClient)
- 监控进度的文件上传
- HTTP 客户端的模拟测试
- 使用可配置的淘汰策略缓存响应
- 代理配置(简单、系统级、按请求)
- 用于日志记录和身份验证的请求/响应拦截器
- 调整连接池(
concurrency(total, perRoute)) - 套接字超时控制(独立于连接超时)
- 套接字错误时自动重试(
automaticRetries()) - 用于后台线程管理的关闭钩子
- 支持自定义 HostnameVerifier
⚠️ 要求
- Java 8 或更高版本
- Apache HttpClient 4(传递依赖)
- Maven/Gradle 依赖管理
❌ 不适用范围(及替代方案)
- HTTP/2 → 使用 Unirest 4.x(默认使用 HTTP/2)
- 通过 Unirest 使用 WebSocket → 使用 Apache HttpClient WebSocket 或专用库
- 服务器发送事件(SSE)→ 使用 Unirest 4.x 或自定义实现
- 自定义执行器支持 → 3.x 中不可用
- Java Authenticator 集成 → 使用 Apache 专用身份验证机制
- ProxySelector 支持 → 使用按请求代理或系统属性
何时使用本技能
用户需要以下功能时,请使用本技能:
- 在 Java 8+ 项目中向 REST API 发起 HTTP 请求
- 使用 Apache HttpClient 作为 HTTP 引擎
- 内置 GSON,无需额外依赖
- 调整连接池(
concurrency()) - 独立控制套接字超时
- 在套接字错误时自动重试
- 配置按请求代理
- 使用自定义 HostnameVerifier
快速开始
Maven 依赖(Unirest 3.14.5):
<dependency>
<groupId>com.konghq</groupId>
<artifactId>unirest-java</artifactId>
<version>3.14.5</version>
</dependency>
✅ 无需声明 JSON 模块 — 默认包含 GSON。
最简 GET 请求:
String body = Unirest.get("https://api.example.com/users")
.asString()
.getBody();
最简 JSON POST 请求:
HttpResponse<JsonNode> response = Unirest.post("https://api.example.com/users")
.header("Content-Type", "application/json")
.body(new User("Alice", "[email protected]"))
.asJson();
关键:安装
Unirest 3.x 是单一依赖,默认包含 GSON:
<dependency>
<groupId>com.konghq</groupId>
<artifactId>unirest-java</artifactId>
<version>3.14.5</version>
</dependency>
✅ 无需单独声明 JSON 模块 — 已包含基于 GSON 的
JsonObjectMapper。
关键:配置
所有配置均通过 Unirest.config() 完成:
Unirest.config()
.connectTimeout(5000)
.socketTimeout(10000)
.concurrency(200, 20)
.setDefaultHeader("Accept", "application/json")
.setDefaultBasicAuth("user", "pass")
.followRedirects(true)
.verifySsl(true)
.enableCookieManagement(true)
.automaticRetries(true)
.proxy("proxy.com", 8080, "user", "pass");
关键配置选项:
| 方法 | 影响 | 默认值 |
|---|---|---|
connectTimeout(int) | 连接超时(毫秒) | 10000 |
socketTimeout(int) | 套接字/读取超时(毫秒) | 60000 |
concurrency(int, int) | 最大总连接数、每个路由的最大连接数 | 200/20 |
followRedirects(boolean) | 跟随 HTTP 重定向 | true |
verifySsl(boolean) | 强制执行 SSL 验证 | true |
enableCookieManagement(boolean) | 接受/存储 Cookie | true |
automaticRetries(boolean) | 套接字错误时自动重试(最多 4 次) | true |
retryAfter(boolean) | 收到带有 Retry-After 标头的 429/529 时自动重试 | false |
defaultBaseUrl(String) | 所有请求的默认基础 URL | 无 |
addShutdownHook(boolean) | 注册 JVM 关闭钩子 | false |
useSystemProperties(boolean) | 使用代理等系统属性 | true |
多个配置:
// Primary instance (same as static Unirest)
UnirestInstance unirest = Unirest.primaryInstance();
// Spawn a new independent instance
UnirestInstance custom = Unirest.spawnInstance();
custom.config().connectTimeout(3000);
⚠️ 如果你创建了新实例,必须自行负责将其关闭。
完整配置表、拦截器、对象映射器和指标,请参阅 references/configuration.md。
关键:发起请求
基本请求类型:
Unirest.get("http://localhost/users").asString();
Unirest.post("http://localhost/users").body(json).asJson();
Unirest.put("http://localhost/users/1").body(user).asEmpty();
Unirest.delete("http://localhost/users/1").asEmpty();
路由参数:
Unirest.get("http://localhost/users/{id}")
.routeParam("id", "42")
.asString();
// Results in http://localhost/users/42
查询参数:
Unirest.get("http://localhost/search")
.queryString("q", "unirest")
.queryString("page", 1)
.asString();
标头和身份验证:
Unirest.get("http://localhost/protected")
.header("X-Custom", "value")
.basicAuth("user", "pass")
.asString();
表单数据:
Unirest.post("http://localhost/form")
.field("name", "Alice")
.field("age", 30)
.asEmpty();
文件上传:
Unirest.post("http://localhost/upload")
.field("file", new File("/path/to/file.zip"))
.asEmpty();
异步请求:
CompletableFuture<HttpResponse<JsonNode>> future = Unirest.get("http://localhost/data")
.asJsonAsync(response -> {
System.out.println(response.getBody());
});
按请求代理(仅限 3.x):
Unirest.get("http://localhost/data")
.proxy("proxy.com", 8080)
.asString();
JSON Patch(RFC-6902):
Unirest.jsonPatch("http://localhost/resource")
.add("/fruits/-", "Apple")
.remove("/bugs")
.replace("/name", "Updated")
.asJson();
有关上传进度、分页请求、客户端证书等内容,请参阅 references/requests.md。
关键:处理响应
响应类型:
// String
String body = Unirest.get(url).asString().getBody();
// Object mapping (GSON included by default)
Book book = Unirest.get(url).asObject(Book.class).getBody();
// Generic types
List<Book> books = Unirest.get(url)
.asObject(new GenericType<List<Book>>(){}).getBody();
// JSON
JsonNode json = Unirest.get(url).asJson().getBody();
// File
File file = Unirest.get(url).asFile("/tmp/download.zip").getBody();
// Empty (status/headers only)
HttpResponse resp = Unirest.delete(url).asEmpty();
错误处理:
Unirest.get("http://localhost/data")
.asJson()
.ifSuccess(response -> handleSuccess(response))
.ifFailure(response -> {
log.error("Status: " + response.getStatus());
response.getParsingError().ifPresent(e -> {
log.error("Parse error: " + e.getMessage());
});
});
解析错误:
response.getParsingError().ifPresent(ex -> {
String originalBody = ex.getOriginalBody();
String message = ex.getMessage();
});
映射错误对象:
HttpResponse<Book> book = Unirest.get(url).asObject(Book.class);
Error err = book.mapError(Error.class);
有关下载进度、大型响应、正文映射等内容,请参阅 references/responses.md。
关键:模拟
静态模拟:
MockClient mock = MockClient.register();
mock.expect(HttpMethod.GET, "http://api.example.com/users")
.thenReturn("{\"name\":\"Alice\"}")
.withStatus(200);
String body = Unirest.get("http://api.example.com/users")
.asString().getBody();
// body == "{\"name\":\"Alice\"}"
mock.verifyAll(); // Verify all expects were called
实例模拟(3.x 要求同时注册两个客户端):
UnirestInstance unirest = Unirest.spawnInstance();
MockClient mock = MockClient.register(unirest);
// In 3.x, the mock implements both Client and AsyncClient
正文匹配:
mock.expect(HttpMethod.POST, "http://api.example.com/users")
.body(FieldMatcher.of("name", "Alice", "role", "admin"))
.thenReturn()
.withStatus(201);
验证调用次数:
var expect = mock.expect(HttpMethod.GET, "http://api.example.com/users").thenReturn();
expect.verify(); // At least once
expect.verify(Times.never()); // Never called
有关 POJO 响应、多个 expect 等内容,请参阅 references/mocking.md。
关键:缓存
基本缓存:
Unirest.config().cacheResponses(true);
使用选项的高级缓存:
Unirest.config().cacheResponses(Cache.builder()
.depth(100) // Max entries
.maxAge(5, TimeUnit.MINUTES)); // Entry TTL
自定义缓存(例如 Guava):
Unirest.config().cacheResponses(
Cache.builder().backingCache(new MyGuavaCache()));
有关自定义缓存实现的详细信息,请参阅 references/caching.md。
关键:代理
简单代理:
Unirest.config().proxy("proxy.com", 8080, "user", "pass");
逐请求代理(仅限 3.x):
Unirest.get("http://localhost/data")
.proxy("proxy.com", 8080)
.asString();
系统属性(3.x 中默认为 true):
System.setProperty("http.proxyHost", "localhost");
System.setProperty("http.proxyPort", "7777");
// useSystemProperties defaults to true in 3.x
有关详细信息,请参阅 references/proxies.md。
快速修复
| 错误 | 原因 | 修复方法 |
|---|---|---|
NoClassDefFoundError: kong/unirest/Unirest | 包名错误 | 使用 import kong.unirest.*(而非 kong.unirest.core.*) |
asObject() 返回 null 正文 | 响应解析失败 | 查看 response.getParsingError() 获取详细信息 |
ConnectException: Connection timed out | 无法访问服务或超时时间过短 | 增大 connectTimeout 或检查网络 |
SocketTimeoutException | 超过读取超时时间 | 增大 socketTimeout(默认值为 60000ms) |
SSLHandshakeException | SSL 验证失败 | 仅在开发环境使用 verifySsl(false);在生产环境修复证书 |
| 代理无法工作 | 系统属性可能已禁用 | 检查 useSystemProperties(true)(3.x 中默认为 true) |
| 连接过多 | 连接池已耗尽 | 增大 concurrency(total, perRoute) |
| 自动重试无法工作 | 已禁用或不适用 | 检查 automaticRetries(true)(默认为 true) |
注意事项
- Java 8+ 即可满足要求 — 3.x 可在 Java 8 上运行(而 4.x 要求 Java 11+)
- 默认包含 GSON — 无需单独声明 JSON 模块(而 4.x 需要)
- 包名为
kong.unirest— 而非kong.unirest.core(后者用于 4.x) - 单个 Maven 依赖项 —
unirest-java:3.14.5(而 4.x 使用 BOM + core + module) - Apache HttpClient 引擎 — 使用 Apache HttpClient 4(而非 java.net.http.HttpClient)
- Socket 超时独立设置 —
socketTimeout()单独控制读取超时,不受connectTimeout()影响 - 连接池调优 —
concurrency(total, perRoute)可用于调优 Apache 的连接池 - 默认启用自动重试 —
automaticRetries(true)会针对套接字错误重试,最多 4 次 - 支持逐请求代理 —
request.proxy(host, port)可用(在 4.x 中已移除) - 支持 HostnameVerifier —
hostnameVerifier(verifier)可用于自定义 SSL 主机名验证 - 提供关闭钩子 —
addShutdownHook(true)会注册 JVM 关闭钩子 - 默认启用系统代理属性 —
useSystemProperties默认为true(而 4.x 中并非如此) - Unirest 不支持 WebSocket — 请使用 Apache HttpClient WebSocket 或专用库
- 不支持 SSE — 3.x 中不存在
Unirest.sse() - 模拟注册需要同时使用两个客户端 — MockClient 同时实现
Client和AsyncClient
参考资料
请求
- requests.md — 路由参数、查询参数、标头、身份验证、正文类型、文件上传、上传进度、异步请求、分页请求、逐请求代理
响应
- responses.md — asEmpty/asString/asObject/asJson/asFile、GenericType、解析错误、错误对象映射、下载进度、大型响应、错误处理
配置
- configuration.md — 完整配置选项表、全局拦截器、多个配置、对象映射器、指标、Apache 专属选项
模拟
- mocking.md — 静态/实例模拟、多个预期(评分)、验证、请求体匹配、表单参数、POJO 响应
缓存
- caching.md — 基础/高级缓存、自定义缓存实现
代理
- proxies.md — 简单代理、系统属性、按请求设置代理