Rust AI实践:用Rig构建LLM应用

Rust AI 正从实验阶段迈向更实用的应用。我们最近启动了一项新项目与Rust基金会的直播系列探讨Rust与AI如何在现实应用中结合。在第一场会议中,我们的开发者倡导者Orhun Parmaksız与首席维护员Stephen Korzeniewski进行了交谈装备以及0x游乐场。

奥尔亨展示了他与里格一起创造的一个小型编码代理。失败.随后他和Stephen在会议中共同审查了代码。演示为我们提供了一个实用的起点,帮助我们了解Rust中AI代理的工作原理以及Rig带来的实现。

简而言之;总结

Rig为Rust开发者提供了一个通用接口,方便与OpenAI、Anthropic和Gemini等大型语言模型提供商合作。它支持AI代理、工具、RAG、数据库集成、流式传输和本地模型。

直播期间,Orhun演示了用Rig和Ratatui构建的小型编码代理,Stephen则讲解了代理的设置、工具及支持抽象。

什么是Rig?

Rig 是一个开源的 Rust 库,用于处理来自不同供应商的大型语言模型。OpenAI、Anthropic、Gemini 以及其他提供商各自提供自己的 API。

虽然许多服务商声称支持OpenAI,但每个服务在实际中表现略有不同。

Rig通过为所有提供者使用单一的Rust接口来处理这些差异,因此开发者可以切换供应商而无需重写依赖LLM的应用部分。

“Rig实现了一种使用所有这些提供者的方式。”

斯蒂芬·科尔泽涅夫斯基0xPlaygrounds 的主维护者

其抽象涵盖了简单的模型请求和更高级的应用程序,可以调用工具或获取外部上下文。

Rig 如何构建 LLM 应用

Rig 将 LLM 应用组织为几个核心部分:提供者客户端、完备模型、代理及其可用的任何工具。提供者客户端将应用连接到服务,而选定模型用于配置代理。

Stephen 将代理描述为高于大型语言模型的抽象层。直接模型请求遵循简单的文本输入、文本输出流程。智能体围绕该模型调用添加指令、令牌限制和能力。

rust ai

在 Rig 中,这些指令通过前言提供,作为系统提示符,包含在每个请求的开头。代理在每次运行时保持与提供者连接,而 Rig 通过统一接口处理提供者 API 之间的差异。

由于与模型提供者的通信涉及网络请求,Rig 为此流使用异步 API。其中很大一部分异步工作在库内部处理,使应用代码能够专注于其配置和行为。

这种分离赋予代理的每个部分明确的角色:Rig 负责与提供者的连接,前言定义其指令。工具使代理能够超越生成文本,与应用的其他部分交互。

人工智能代理和工具在Rig中的工作原理

在 Rig 中,工具是通过 Rust 的工具特性定义的。正如 Stephen 所说:“工具基本上是 AI 代理可以执行的一个 Rust 函数。”

实现该特征定义了工具的名称、输入、输出和错误类型,以及调用工具时运行的函数。工具定义通过 JSON 模式描述其预期参数,为模型提供了其可提供的输入的结构化描述。

一旦工具注册到代理,支持工具调用的模型可以决定何时使用该工具,并将结果纳入响应中。底层的 Rust 函数可能会执行计算、查询数据库、检索信息或与其他服务交互。

工具还可以接收上下文,从而访问状态。这可以用来计数调用次数、缓存结果,或保留工具调用之间所需的信息。

Rig 将同样的模型扩展到代理本身。代理可以作为工具提供给另一个代理。这使得代理之间可以用单一的工具接口来委派任务。

编码代理演示内部

Orhun将这些元素整合在Rat Code中,Rat Code是一个由Rig和Ratatui构建的小型终端编码代理。该应用程序呈现了一个简单的提示与响应界面,Rig管理其下的代理。

项目在代码中保持其主要职责的可见性。在main.rs该应用程序负责设置提供者客户端、模型和代理。读取文件、写入文件和运行shell命令的能力分别定义,并通过Rig的工具界面向代理注册。

该应用还使用 Rig 的流式 API 分段处理响应,并在模型生成答案时更新终端界面。在演示中,Stephen 还讨论了 Rig 的钩子系统、工具调用恢复及其抽象背后的一些设计选择。

你可以在直播,27:28开始.

RAG 和 Rust 中的本地模型

Rig还支持需要访问外部数据或希望运行模型更靠近应用部署地点的应用程序。

利用 RAG 将大型语言模型与外部数据连接

检索增强生成(RAG)在LLM生成响应前,先提供相关信息。应用程序将文档和用户查询转换为向量嵌入。然后利用语义相似性找到最相关的文档并将其添加到模型上下文中。

Rig 通过其数据库集成和向量存储抽象支持这一过程。开发者可以连接支持的数据库,或者如果他们更愿意使用一个不支持但能存储向量的数据库,也可以实现 Rig 的向量存储特性。

用Rig运行本地大型语言模型

Rig 提供了多种本地模型的工作方式,包括 Ollama、llama.cpp 和 Candle。它可以通过 Ollama 和 llama.cpp 连接到本地模型,这些都使用本地运行的服务器,而 rig-candle 集成则直接通过 Candle 在 Rust 应用中进行推理。

拥抱脸开发的蜡烛作为一个用于机器学习的Rust框架。通过rig-candle,用户可以直接将模型权重嵌入应用程序,本地运行推理,并将支持的模型运行到WebAssembly.这种方法使得发布不依赖托管模型API或独立本地推理服务器的应用程序成为可能。

对托管提供者、数据库和本地推理的支持,提供了对模型和数据运行位置的更多控制。这也引发了一个重要的实际问题:当模型提供者及其输出可能发生变化时,如何测试集成?

Rig 如何测试 LLM 集成

测试LLM应用存在一个不同寻常的挑战。模型响应是非确定性的,而集成代码的变化会影响应用与不同提供者的通信方式。Rig将测试提供者集成与评估模型输出质量区分开来。

在CI中重放提供者请求

Rig 主要测试其与磁带系统的提供商集成。维护者对实时提供者进行测试,记录 HTTP 流量,并将这些交互保存为 YAML 文件。模拟服务器随后可以回放录制的请求和响应,使 Rig 的测试能够在不与实时 API 连接的情况下运行。

据Stephen介绍,Rig大约有1700次提供者互动记录,且还在不断增加。项目在CI中为每个拉取请求重放这些交互,整个过程只需几秒钟。

测试实时模型行为

磁带测试可以验证API集成是否仍然有效,但无法显示模型输出质量是否发生变化。提供者会定期更新模型,因此即使代码未变,同一应用的行为也可能有所不同。

对于依赖响应质量的生产应用,Stephen 将针对实时模型的定时测试描述为更高级的方法。Rig 本身主要专注于测试其 API 集成,因此主要依赖静态磁带系统。

这些方法共同解决了两个不同的问题:集成是否仍然有效,实时模型是否仍能产生应用所需的结果?

Rust 和 AI 的下一步是什么?

Rust可以驱动AI应用,AI也能帮助开发者在Rust中构建软件。我们与Rust基金会的联合系列将探讨双方观点,汇聚社区中不同的声音。

Rig 为我们提供了一个实用的起点。它支持从模型提供者和代理到工具、RAG、流式推理和本地推理的各种内容。Rat Code 让我们看到 Rig 的代理和工具抽象在一个小型 Rust 应用中的工作原理。

非常感谢 Stephen 加入 Orhun,带我们了解 Rig 的设计过程,并分享他作为首席维护者的经验。

对于完整的老鼠代码攻略及其他对话内容——包括Rig的钩子系统和工具调用恢复,以及Stephen的AI辅助开发流程——在YouTube上观看完整课程.如果你正在尝试Rig或在Rust中构建AI代理,欢迎在评论区告诉我们你正在做什么,或者加入Discord上的Rig社区。

关注我们的更新,关注系列的下一轮。

添加评论
点赞收藏
点踩分享查看原文
评论
?
参与讨论