Java SDK
MCP 客户端
Java SDK
MCP 客户端
学习如何使用 Model Context Protocol (MCP) 客户端与 MCP 服务器交互
Model Context Protocol 客户端
MCP 客户端是 Model Context Protocol (MCP) 架构中的关键组件,负责建立和管理与 MCP 服务器的连接。它实现了协议的客户端部分,处理:
- 协议版本协商以确保与服务器的兼容性
- 能力协商以确定可用功能
- 消息传输和 JSON-RPC 通信
- 工具发现和执行
- 资源访问和管理
- 提示系统交互
- 可选功能如根目录管理和采样支持
客户端提供同步和异步 API,以适应不同的应用场景。
// 使用自定义配置创建同步客户端
McpSyncClient client = McpClient.sync(transport)
.requestTimeout(Duration.ofSeconds(10))
.capabilities(ClientCapabilities.builder()
.roots(true) // 启用根目录功能
.sampling() // 启用采样功能
.build())
.sampling(request -> new CreateMessageResult(response))
.build();
// 初始化连接
client.initialize();
// 列出可用工具
ListToolsResult tools = client.listTools();
// 调用工具
CallToolResult result = client.callTool(
new CallToolRequest("calculator",
Map.of("operation", "add", "a", 2, "b", 3))
);
// 列出和读取资源
ListResourcesResult resources = client.listResources();
ReadResourceResult resource = client.readResource(
new ReadResourceRequest("resource://uri")
);
// 列出和使用提示
ListPromptsResult prompts = client.listPrompts();
GetPromptResult prompt = client.getPrompt(
new GetPromptRequest("greeting", Map.of("name", "Spring"))
);
// 添加/删除根目录
client.addRoot(new Root("file:///path", "description"));
client.removeRoot("file:///path");
// 关闭客户端
client.closeGracefully();
// 使用自定义配置创建同步客户端
McpSyncClient client = McpClient.sync(transport)
.requestTimeout(Duration.ofSeconds(10))
.capabilities(ClientCapabilities.builder()
.roots(true) // 启用根目录功能
.sampling() // 启用采样功能
.build())
.sampling(request -> new CreateMessageResult(response))
.build();
// 初始化连接
client.initialize();
// 列出可用工具
ListToolsResult tools = client.listTools();
// 调用工具
CallToolResult result = client.callTool(
new CallToolRequest("calculator",
Map.of("operation", "add", "a", 2, "b", 3))
);
// 列出和读取资源
ListResourcesResult resources = client.listResources();
ReadResourceResult resource = client.readResource(
new ReadResourceRequest("resource://uri")
);
// 列出和使用提示
ListPromptsResult prompts = client.listPrompts();
GetPromptResult prompt = client.getPrompt(
new GetPromptRequest("greeting", Map.of("name", "Spring"))
);
// 添加/删除根目录
client.addRoot(new Root("file:///path", "description"));
client.removeRoot("file:///path");
// 关闭客户端
client.closeGracefully();
// 使用自定义配置创建异步客户端
McpAsyncClient client = McpClient.async(transport)
.requestTimeout(Duration.ofSeconds(10))
.capabilities(ClientCapabilities.builder()
.roots(true) // 启用根目录功能
.sampling() // 启用采样功能
.build())
.sampling(request -> Mono.just(new CreateMessageResult(response)))
.build();
// 初始化连接
client.initialize()
.doOnSuccess(v -> logger.info("客户端已初始化"))
.subscribe();
// 列出可用工具
client.listTools()
.doOnNext(tools -> logger.info("发现工具: {}", tools))
.subscribe();
// 调用工具
client.callTool(new CallToolRequest("calculator",
Map.of("operation", "add", "a", 2, "b", 3)))
.doOnNext(result -> logger.info("工具结果: {}", result))
.subscribe();
资源访问
资源代表服务器端的数据源,客户端可以使用 URI 模板访问。MCP 客户端提供方法来发现可用资源并通过标准化接口检索其内容。
// 列出可用资源及其名称
var resources = client.listResources();
resources.forEach(resource -> System.out.println(resource.getName()));
// 使用 URI 模板检索资源内容
var content = client.getResource("file", Map.of(
"path", "/path/to/file.txt"
));
// 列出可用资源及其名称
var resources = client.listResources();
resources.forEach(resource -> System.out.println(resource.getName()));
// 使用 URI 模板检索资源内容
var content = client.getResource("file", Map.of(
"path", "/path/to/file.txt"
));
// 异步列出可用资源
client.listResources()
.doOnNext(resources -> resources.forEach(resource ->
System.out.println(resource.getName())))
.subscribe();
// 异步检索资源内容
client.getResource("file", Map.of(
"path", "/path/to/file.txt"
))
.subscribe();
提示系统
提示系统支持与服务器端提示模板的交互。这些模板可以被发现和执行,并带有自定义参数,允许基于预定义模式进行动态文本生成。
// 列出可用提示模板
var prompts = client.listPrompts();
prompts.forEach(prompt -> System.out.println(prompt.getName()));
// 使用参数执行提示模板
var response = client.executePrompt("echo", Map.of(
"text", "你好,世界!"
));
// 列出可用提示模板
var prompts = client.listPrompts();
prompts.forEach(prompt -> System.out.println(prompt.getName()));
// 使用参数执行提示模板
var response = client.executePrompt("echo", Map.of(
"text", "你好,世界!"
));
// 异步列出可用提示模板
client.listPrompts()
.doOnNext(prompts -> prompts.forEach(prompt ->
System.out.println(prompt.getName())))
.subscribe();
// 异步执行提示模板
client.executePrompt("echo", Map.of(
"text", "你好,世界!"
))
.subscribe();