1. 直接工具(tools)
最直接的方式是使用 tools() 方法直接传入 ToolCallback 实例。这种方式适合工具数量较少、工具定义明确的场景。
import com.alibaba.cloud.ai.graph.agent.ReactAgent;
import org.springframework.ai.tool.ToolCallback;
import org.springframework.ai.tool.function.FunctionToolCallback;
// 创建工具
ToolCallback weatherTool = FunctionToolCallback
.builder("get_weather", new WeatherFunction())
.description("Get weather for a given city")
.inputType(WeatherInput.class)
.build();
ToolCallback searchTool = FunctionToolCallback
.builder("search", new SearchFunction())
.description("Search for information")
.inputType(String.class)
.build();
// 使用 tools() 方法直接提供工具
ReactAgent agent = ReactAgent.builder()
.name("my_agent")
.model(chatModel)
.tools(weatherTool, searchTool) // 直接传入 ToolCallback 实例
.systemPrompt("You are a helpful assistant with access to weather and search tools.")
.saver(new MemorySaver())
.build();
适用场景:
- 工具数量较少(通常少于 5 个)
- 工具定义在编译时已知
- 需要类型安全的工具定义
2. 方法工具(methodTools)
使用 methodTools() 方法传入带有 @Tool 注解方法的对象。这种方式让工具定义更加简洁,适合将工具逻辑组织在类中。
import com.alibaba.cloud.ai.graph.agent.ReactAgent;
import org.springframework.ai.tool.annotation.Tool;
import org.springframework.ai.tool.annotation.ToolParam;
// 定义工具类,使用 @Tool 注解
public class CalculatorTools {
@Tool(description = "Add two numbers together")
public String add(
@ToolParam(description = "First number") int a,
@ToolParam(description = "Second number") int b) {
return String.valueOf(a + b);
}
@Tool(description = "Multiply two numbers together")
public String multiply(
@ToolParam(description = "First number") int a,
@ToolParam(description = "Second number") int b) {
return String.valueOf(a * b);
}
}
// 使用 methodTools() 方法
CalculatorTools calculatorTools = new CalculatorTools();
ReactAgent agent = ReactAgent.builder()
.name("calculator_agent")
.model(chatModel)
.description("An agent that can perform calculations")
.instruction("You are a helpful calculator assistant.")
.methodTools(calculatorTools) // 传入带有 @Tool 注解方法的对象
.saver(new MemorySaver())
.build();
// 可以传入多个 methodTools 对象
WeatherTools weatherTools = new WeatherTools();
ReactAgent multiAgent = ReactAgent.builder()
.name("multi_tool_agent")
.model(chatModel)
.methodTools(calculatorTools, weatherTools) // 多个工具对象
.build();
适用场景:
- 工具逻辑组织在类中
- 需要将相关工具分组
- 工具方法需要访问类成员变量
3. 工具提供者(toolCallbackProviders)
使用 ToolCallbackProvider 接口动态提供工具。这种方式适合需要根据运行时条件动态决定提供哪些工具的场景。
import com.alibaba.cloud.ai.graph.agent.ReactAgent;
import org.springframework.ai.tool.ToolCallback;
import org.springframework.ai.tool.ToolCallbackProvider;
import org.springframework.ai.tool.function.FunctionToolCallback;
import java.util.List;
// 实现 ToolCallbackProvider 接口
public class CustomToolCallbackProvider implements ToolCallbackProvider {
private final List<ToolCallback> toolCallbacks;
public CustomToolCallbackProvider(List<ToolCallback> toolCallbacks) {
this.toolCallbacks = toolCallbacks;
}
@Override
public ToolCallback[] getToolCallbacks() {
return toolCallbacks.toArray(new ToolCallback[0]);
}
}
// 创建工具
ToolCallback searchTool = FunctionToolCallback.builder("search", new SearchToolWithContext())
.description("Search for information")
.inputType(String.class)
.build();
// 创建 ToolCallbackProvider
ToolCallbackProvider toolProvider = new CustomToolCallbackProvider(List.of(searchTool));
// 使用 toolCallbackProviders() 方法
ReactAgent agent = ReactAgent.builder()
.name("search_agent")
.model(chatModel)
.description("An agent that can search for information")
.instruction("You are a helpful assistant with search capabilities.")
.toolCallbackProviders(toolProvider) // 使用 ToolCallbackProvider
.saver(new MemorySaver())
.build();
适用场景:
- 需要根据运行时条件动态提供工具
- 工具来自外部系统或配置
- 需要实现工具的动态加载和卸载
4. 工具名称解析(toolNames + resolver)
使用 toolNames() 方法指定工具名称,配合 resolver() 方法提供的 ToolCallbackResolver 来解析工具。这种方式适合工具定义和工具使用分离的场景。
import com.alibaba.cloud.ai.graph.agent.ReactAgent;
import org.springframework.ai.tool.ToolCallback;
import org.springframework.ai.tool.function.FunctionToolCallback;
import org.springframework.ai.tool.resolution.StaticToolCallbackResolver;
import java.util.List;
// 创建工具(使用复合类型)
ToolCallback searchTool = FunctionToolCallback.builder("search", new SearchFunctionWithRequest())
.description("Search for information")
.inputType(SearchRequest.class)
.build();
ToolCallback calculatorTool = FunctionToolCallback.builder("calculator", new CalculatorFunctionWithRequest())
.description("Perform arithmetic calculations")
.inputType(CalculatorRequest.class)
.build();
// 创建 StaticToolCallbackResolver,包含所有工具
StaticToolCallbackResolver resolver = new StaticToolCallbackResolver(
List.of(calculatorTool, searchTool));
// 使用 toolNames() 指定要使用的工具名称,必须配合 resolver() 使用
ReactAgent agent = ReactAgent.builder()
.name("multi_tool_agent")
.model(chatModel)
.description("An agent with multiple tools")
.instruction("You are a helpful assistant with access to calculator and search tools.")
.toolNames("calculator", "search") // 使用工具名称而不是 ToolCallback 实例
.resolver(resolver) // 必须提供 resolver 来解析工具名称
.saver(new MemorySaver())
.build();
重要提示:toolNames() 方法必须与 resolver() 方法配合使用,否则会抛出异常。
适用场景:
- 工具定义和工具使用分离
- 需要从配置或外部系统读取工具名称
- 工具可能动态变化,但名称保持稳定
5. 工具解析器(resolver)
直接使用 resolver() 方法提供 ToolCallbackResolver。解析器可以用于工具节点,也可以与 toolNames() 配合使用。
import com.alibaba.cloud.ai.graph.agent.ReactAgent;
import org.springframework.ai.tool.ToolCallback;
import org.springframework.ai.tool.function.FunctionToolCallback;
import org.springframework.ai.tool.resolution.StaticToolCallbackResolver;
import java.util.List;
// 创建工具
ToolCallback calculatorTool = FunctionToolCallback.builder("calculator", new CalculatorFunctionWithContext())
.description("Perform arithmetic calculations")
.inputType(String.class)
.build();
// 创建 resolver
StaticToolCallbackResolver resolver = new StaticToolCallbackResolver(
List.of(calculatorTool));
// 使用 resolver,可以直接在 tools 中使用,也可以仅通过 resolver 提供
ReactAgent agent = ReactAgent.builder()
.name("resolver_agent")
.model(chatModel)
.description("An agent using ToolCallbackResolver")
.instruction("You are a helpful calculator assistant.")
.tools(calculatorTool) // 直接指定工具
.resolver(resolver) // 同时设置 resolver 供工具节点使用
.saver(new MemorySaver())
.build();
适用场景:
- 需要自定义工具解析逻辑
- 工具来自多个来源需要统一管理
- 需要实现工具的动态查找和加载
6. 组合使用多种方式
你可以同时使用多种工具提供方式,ReactAgent 会将它们合并。
import com.alibaba.cloud.ai.graph.agent.ReactAgent;
import org.springframework.ai.tool.ToolCallback;
import org.springframework.ai.tool.ToolCallbackProvider;
import org.springframework.ai.tool.function.FunctionToolCallback;
import java.util.List;
// Method tools
CalculatorTools calculatorTools = new CalculatorTools();
// Direct tool
ToolCallback searchTool = FunctionToolCallback.builder("search", new SearchToolWithContext())
.description("Search for information")
.inputType(String.class)
.build();
// ToolCallbackProvider
ToolCallbackProvider toolProvider = new CustomToolCallbackProvider(List.of(searchTool));
// 组合使用多种方式
ReactAgent agent = ReactAgent.builder()
.name("combined_tool_agent")
.model(chatModel)
.description("An agent with multiple tool provision methods")
.instruction("You are a helpful assistant with calculator and search capabilities.")
.methodTools(calculatorTools) // Method-based tools
.toolCallbackProviders(toolProvider) // Provider-based tools
.tools(searchTool) // Direct tools
.saver(new MemorySaver())
.build();
适用场景:
- 工具来自不同来源
- 需要灵活组合不同类型的工具
- 逐步迁移或扩展现有工具集
根据你的具体需求选择合适的工具提供方式:
| 方式 | 适用场景 | 优点 | 缺点 |
|---|---|---|---|
| tools() | 工具数量少、定义明确 | 简单直接、类型安全 | 工具多时代码冗长 |
| methodTools() | 工具逻辑组织在类中 | 代码组织清晰、易于维护 | 需要创建工具类 |
| toolCallbackProviders() | 动态提供工具 | 灵活、支持运行时决策 | 需要实现接口 |
| toolNames() + resolver() | 工具定义和使用分离 | 解耦、支持配置化 | 必须配合 resolver |
| resolver() | 自定义解析逻辑 | 高度灵活 | 需要实现解析器 |
| 组合使用 | 复杂场景 | 最大灵活性 | 可能增加复杂度 |
本文整理自 Spring AI Alibaba 官方文档《Tools 工具》:https://java2ai.com/docs/frameworks/agent-framework/tutorials/tools

AI项目博客






