当前位置: 首页 > news >正文

Spring AI alibaba 工具调用

本文为个人学习笔记整理,仅供交流参考,非专业教学资料,内容请自行甄别。

文章目录

  • 概述
  • 一、工具调用
    • 1.1、工具调用流程
    • 1.2、工具的定义使用
  • 二、ToolCallback
  • 三、工具上下文
  • 四、ToolCallingManager
  • 五、异常处理


概述

  用户在使用AI时,可能不仅仅需要AI对于问题给出答案,而是需要AI提供一些功能的扩展,例如提供图片,资源下载,文件生成等。这些操作则是利用到了AI工具调用的特性。

一、工具调用

1.1、工具调用流程

  工具调用简单来说,就是让AI大模型使用外部工具完成特定功能。工具调用,不是让AI服务器自己调用工具,提供调用逻辑的工具取决于客户端应用程序:

  • 模型只能请求一个工具调用并提供输入参数。
  • 应用程序则负责执行来自输入参数的工具调用并返回结果。

  模型无法直接访问到用户编写的工具的API,这是一个至关重要的安全考虑因素,工具调用的执行流程:

  1. 用户通过注解或编程的方式,创建工具类,自己编写利用工具要实现的业务逻辑。将工具类注册到chatClient中,可以是针对单个对话设置,也可以是全局设置。即程序告诉AI可以使用的工具,描述每个工具的参数和功能。
  2. 大模型在对话中分析用户的问题,判断需要使用哪个工具,输出工具名称和参数的信息。
  3. Spring AI 将工具调用的请求进行分发,应用程序执行对应的工具调用的业务逻辑。
  4. 应用程序将执行工具的结果发回给Spring AI
  5. Spring AI 将结果发送给大模型。
  6. 大模型根据上一步的结果,再次生成最终的回答给用户。

在这里插入图片描述
  相当于在应用程序和大模型之间,通过Spring AI中转了一道,大模型无法直接调用应用程序编写的工具。

1.2、工具的定义使用

  工具的定义,有注解式和编程式两种,注解式相对比较简单,主要是通过@Tool@ToolParam注解实现,例如定义一个简单的本地文件读写工具:

  • @Tool注解的description 属性,表明了加入了该注解的方法的作用。
  • @ToolParam的description 属性,表明了加入了该注解的方法中参数的含义。
/*** 文件读写工具*/
public class FileOperationTool {private final String FILE_DIR = FileConstant.FILE_SAVE_DIR + "/file";@Tool(description = "Read content from a file")public String readFile(@ToolParam(description = "Name of the file to read") String fileName) {String filePath = FILE_DIR + "/" + fileName;try {return FileUtil.readUtf8String(filePath);} catch (Exception e) {return "Error reading file: " + e.getMessage();}}@Tool(description = "Write content to a file")public String writeFile(@ToolParam(description = "Name of the file to write") String fileName,@ToolParam(description = "Content to write to the file") String content) {String filePath = FILE_DIR + "/" + fileName;try {// 创建目录FileUtil.mkdir(FILE_DIR);FileUtil.writeUtf8String(content, filePath);return "File written successfully to: " + filePath;} catch (Exception e) {return "Error writing to file: " + e.getMessage();}}
}

  在定义了工具类后,还需要编写一个配置类,将所有的工具类组成一个ToolCallback[]对象:

@Configuration
public class ToolRegistration {@Beanpublic ToolCallback[] toolCallbacks(){FileOperationTool fileOperationTool = new FileOperationTool();PDFGenerationTool pdfGenerationTool = new PDFGenerationTool();ResourceDownloadTool resourceDownloadTool = new ResourceDownloadTool();TerminalOperationTool terminalOperationTool = new TerminalOperationTool();WebScrapingTool webScrapingTool = new WebScrapingTool();WebSearchTool webSearchTool = new WebSearchTool();return ToolCallbacks.from(fileOperationTool,pdfGenerationTool,resourceDownloadTool,terminalOperationTool,webScrapingTool,webSearchTool);}
}

  最后在构造chatClient时进行指定:

/*** 调用工具*/@Resourceprivate ToolCallback[] toolCallbacks;/*** 调用工具链* @param text* @param chatId* @return*/public String doChatWithTools(String text, String chatId){ChatResponse chatResponse = chatClient.prompt().user(text).advisors(spec -> spec.param(CHAT_MEMORY_CONVERSATION_ID_KEY, chatId).param(CHAT_MEMORY_RETRIEVE_SIZE_KEY, 10)).tools(toolCallbacks).call().chatResponse();return chatResponse.getResult().getOutput().getText();}

二、ToolCallback

  工具底层的核心是ToolCallback接口:
在这里插入图片描述
  其中提供了三个方法,getToolDefinition有两个实现,分别代表了注解方式函数式调用方式。
在这里插入图片描述
  这里的ToolDefinition是AI 模型用于确定何时以及如何调用工具的定义,可以指定工具名称,工具说明,以及工具的约束文档。
在这里插入图片描述
  getToolMetadata是获取工具的元信息。ToolMetadata中包含了一个关键的returnDirect它代表了使用工具获取到的结果,是直接返回给用户,还是要发送给大模型再次进行处理,默认是false。可以在注解中指定:

@Tool(description = “Download a resource from a given URL”,returnDirect = false)

在这里插入图片描述
  call则是将调用工具获取到的结果发送给大模型:
在这里插入图片描述

三、工具上下文

  ToolContext代表了工具上下文,是一个map的结构,它类似于ThreadLocal,可以将一些信息放入上下文中传递。
在这里插入图片描述
  可以通过chatClient的toolContext方法进行设置。这些信息只会在应用程序的上下文中进行传递,不会发送给AI大模型,也就避免了敏感信息泄露的问题。

四、ToolCallingManager

  ToolCallingManager是管理具调用过程的服务,主要分为了解析和调用两个步骤:
在这里插入图片描述
  executeToolCalls是调用工具的方法,其中主要做了如下几件事:

  1. 获取 AI 模型返回的所有生成结果,筛选出 “包含工具调用指令” 的结果,取第一个符合条件的结果。目的是从 AI 模型的响应中,定位到包含工具调用指令的那一条结果。
  2. 如果没有找到任何包含工具调用的结果,直接抛出异常。当前方法的职责就是 “执行工具调用”,如果 AI 模型根本没要求调用工具,说明调用场景不匹配(比如上游逻辑判断错误)
  3. 获取 AI 模型输出的具体内容,封装到助手提示词中。包含关键信息:工具名称(toolName)、调用参数(parameters)等。
  4. 调用buildToolContext方法,创建工具执行所需的上下文
  5. 根据助手提示词中的工具名称,找到对应的ToolCallback实现类,调用工具的execute方法执行具体业务逻辑。
  6. 更新对话历史,将工具调用及结果整合到对话历史中,整合的内容包括:原始用户指令,AI 模型的工具调用指令,工具执行的结果。
  7. 构建并返回最终结果,构建ToolExecutionResult对象,其中包含了更新后的完整对话历史和是否直接将工具结果返回给用户。这个结果会被返回给ChatModel,作为下一步处理的输入

在这里插入图片描述
  通常情况下,都是框架控制工具执行,即Spring AI 将自动截取来自模型的任何工具调用请求,调用该工具并将结果返回到模型中。,如果上述的过程,需要用户自己去控制,可以通过以下代码实现:

@Component
public class ChatToolsApp {@Resourceprivate ChatModel dashscopeChatModel;public String testChatTools() {ChatOptions chatOptions = ToolCallingChatOptions.builder().toolCallbacks(ToolCallbacks.from(new SystemDateTimeTool())).internalToolExecutionEnabled(false).build();// 创建工具调用管理器ToolCallingManager toolCallingManager = DefaultToolCallingManager.builder().build();// 创建初始提示Prompt prompt = new Prompt("获取当前系统的日期时间", chatOptions);// 传递用户问题给大模型 ,大模型分析用户问题,判断是否需要使用工具,响应工具名称和参数到ChatResponseChatResponse chatResponse = dashscopeChatModel.call(prompt);// ChatResponse的hasToolCalls不为空,证明大模型认为需要调用工具while (chatResponse.hasToolCalls()) {// 接收工具调用的请求,选择和大模型响应工具名称相匹配的工具,然后调用该工具,。ToolExecutionResult toolExecutionResult = toolCallingManager.executeToolCalls(prompt, chatResponse);// 创建包含工具结果的新提示prompt = new Prompt(toolExecutionResult.conversationHistory(), chatOptions);// 再次发送请求给模型,生成最终的回答chatResponse = dashscopeChatModel.call(prompt);}// 获取最终回答System.out.println(chatResponse.getResult().getOutput().getText());return chatResponse.getResult().getOutput().getText();}}

五、异常处理

  当工具调用失败时,框架抛出的异常类型是ToolExecutionExceptionToolExecutionExceptionProcessor可以用来处理ToolExecutionException
在这里插入图片描述
  它是一个接口,在实现类中,有一个alwaysThrow属性,默认值是false,如果true将抛出一个异常,而不是向模型发送错误消息。
在这里插入图片描述

  如果需要自定义,可以通过:

@Bean
ToolExecutionExceptionProcessor toolExecutionExceptionProcessor() {return new DefaultToolExecutionExceptionProcessor(true);
}
http://www.dtcms.com/a/438033.html

相关文章:

  • 机器学习基础入门(第三篇):监督学习详解与经典算法
  • 做产品的淘宝客网站网站建设的素材处理方式
  • 【专业词典】FAST
  • 诸城网站建设wordpress退出维护
  • 预约记录自动关联功能测试
  • 进程“悄悄话”函数——`socketpair`
  • QT肝8天14--编辑用户
  • Redis Zset的底层秘密:跳表(Skip List)的精妙设计
  • 广州金融网站建设2017网站开发语言排名
  • C++ priority_queue优先级队列
  • Kafka 授权与 ACL 深入实践
  • 西宁市住房和城乡建设局网站做一个个人网站
  • 瑞安做网站多少钱东莞网站建设找谁
  • 谷歌云+Apache Airflow,数据处理自动化的强力武器
  • 小红书自动化运营:智能体+RPA自动化+MCP实现采集仿写和自动发布
  • 网站域名和网站网址建筑培训网 江苏
  • 定制开发开源AI智能名片S2B2C商城小程序的会员制运营研究——以“老铁用户”培养为核心目标
  • 【aigc】chrome-devtools-mcp怎么玩?
  • 从《Life of A Pixel》来看Chrome的渲染机制
  • 【项目实战 Day9】springboot + vue 苍穹外卖系统(用户端订单模块 + 商家端订单管理模块 完结)
  • Mac 安装Neo4j教程
  • blender 解决shift快捷键和中英切换重复的问题
  • 网站动态图怎么做阳明拍卖公司网站
  • 01_Docker 部署 Ollama 模型(支持 NVIDIA GPU)
  • 苏州新区网站制作wordpress视频格式
  • 一位Android用户的科技漫游手记
  • android中调用相册
  • 安卓基础组件031-Retrofit 网络请求框架
  • Redis 黑马点评-商户查询缓存
  • Android geckoview 集成,JS交互,官方demo