分离单元测试和集成测试
集成测试较慢且需要 API 凭证,所以要将它们与单元测试分开。这让你可以在每次更改时运行快速的单元测试,而将集成测试保留给 CI 或部署前检查。 使用文件命名约定来分离集成测试。将集成测试文件命名为*.int.test.ts,并配置 vitest 在默认运行中排除它们:
vitest.config.ts
package.json 中添加脚本:
管理 API 密钥
集成测试需要真实的 API 凭证。从环境变量中加载它们,以使密钥不进入源代码控制。 添加dotenv/config 作为 vitest 的 setup 文件,以便从 .env 自动加载环境变量:
vitest.config.ts
.env
断言结构而非内容
LLM 响应在每次运行之间有所不同。不要断言确切的输出字符串,而是验证响应的结构属性:消息类型、工具调用名称、参数形状和消息数量。使用自定义测试匹配器
langchain 提供了自定义 vitest 匹配器,使结构断言更可读,并在失败时产生清晰的错误消息。在 setup 文件中注册一次,它们就可以在每个 expect() 调用中使用。
设置
添加一个 vitest setup 文件,用 LangChain 匹配器扩展expect:
vitest.setup.ts
vitest.config.ts
检查消息类型
每个消息类都有对应的匹配器:toBeHumanMessage()、toBeAIMessage()、toBeSystemMessage() 和 toBeToolMessage()。不带参数调用只检查类型,或传入字符串来同时匹配内容:
断言工具调用
三个匹配器覆盖了对AIMessage 的工具调用断言:
断言工具消息
toHaveToolMessages() 接受完整的消息数组,并按顺序检查其中的 ToolMessage 实例:
断言中断和结构化响应
toHaveBeenInterrupted() 检查 LangGraph 中断结果中的 __interrupt__ 字段。传入值来匹配中断负载:
toHaveStructuredResponse() 检查结果上的 structuredResponse 字段。传入对象来匹配特定字段:
匹配器参考
降低成本和延迟
调用 LLM API 的集成测试会产生实际成本。一些实践有助于保持测试套件快速且经济:- 使用较小的模型:
gemini-3.1-flash-lite-preview或同等模型,用于只需验证工具调用和响应结构的测试。 - 设置
maxTokens:限制响应长度以避免冗长、昂贵的补全。 - 限制测试范围:每个测试测试一个行为。当单轮测试足够时,避免链接多个 LLM 调用的端到端场景。
- 选择性运行:使用上面的测试分离,只在 CI 或部署前运行集成测试,而不是在每次文件保存时运行。
下一步
了解如何使用确定性匹配或 LLM 评委评估器来评估智能体轨迹,请参阅评估。连接这些文档到 Claude、VSCode 等,通过 MCP 获取实时答案。

