进阶主题
MCP 评估
使用 Evalite 和 AI SDK MCP 客户端评估 MCP 工具和工作流。
概述
评估(Evals)可帮助您验证 LLM 是否正确调用了您的 MCP 工具。本指南展示了如何使用 AI SDK MCP 客户端配合 Evalite 运行工具调用评估。
该方法保持库无关性,Evalite 仅作为示例运行器。您可以将这些模式适配到其他评估框架中。
提示词
使用 Evalite 为我的 Nuxt 应用 (@nuxtjs/mcp-toolkit) 设置 MCP 评估。
1. 安装依赖:pnpm add -D evalite vitest @ai-sdk/mcp ai
2. 在 package.json 中添加评估脚本:"eval": "evalite" 和 "eval:ui": "evalite watch"
3. 在 .env 中设置 AI 提供商 API 密钥和 MCP_URL=http://localhost:3000/mcp
4. 创建 test/mcp.eval.ts 并编写 evalite() 测试用例
5. 每个测试用例包含一个输入(自然语言提示词)和预期的工具调用(例如 [{ toolName: 'my-tool', input: { ... } }])
6. 使用 @ai-sdk/mcp 中的 experimental_createMCPClient 连接到 MCP 服务器
7. 使用 ai 中的 generateText 配合 MCP 工具测试工具选择
8. 使用 evalite/scorers 中的 toolCallAccuracy 进行评分
9. 先启动开发服务器 (pnpm dev),然后运行 pnpm eval 或 pnpm eval:ui 打开可视化界面
文档:https://mcp-toolkit.nuxt.dev/advanced/evals
如需查看实际示例,请参阅 nuxt.com MCP 评估。
前置条件
- 本地运行的 MCP 服务器(例如,启用模块后运行
pnpm dev) - 模型提供商 API 密钥(AI Gateway、OpenAI 等)
设置
安装依赖
安装 Evalite、Vitest 和 AI SDK 相关包:
pnpm add -D evalite vitest @ai-sdk/mcp ai
npm install -D evalite vitest @ai-sdk/mcp ai
yarn add -D evalite vitest @ai-sdk/mcp ai
bun add -D evalite vitest @ai-sdk/mcp ai
添加评估脚本
将以下脚本添加到您的 package.json 中:
package.json
{
"scripts": {
"eval": "evalite",
"eval:ui": "evalite watch"
}
}
配置环境变量
创建一个 .env 文件,填入您的 AI 提供商密钥和 MCP 端点:
.env
# AI 提供商(AI Gateway 示例)
AI_GATEWAY_API_KEY=your_key
# 开发服务器暴露的 MCP 端点
MCP_URL=http://localhost:3000/mcp
编写您的第一个评估
在 test/ 目录中创建一个评估文件:
test/mcp.eval.ts
import { experimental_createMCPClient as createMCPClient } from '@ai-sdk/mcp'
import { generateText } from 'ai'
import { evalite } from 'evalite'
import { toolCallAccuracy } from 'evalite/scorers'
// AI Gateway 模型格式:provider/model-name
const model = 'openai/gpt-4o-mini'
const MCP_URL = process.env.MCP_URL ?? 'http://localhost:3000/mcp'
evalite('BMI Calculator', {
data: async () => [
{
input: 'Calculate BMI for someone who weighs 70kg and is 1.75m tall',
expected: [{ toolName: 'calculate-bmi', input: { weightKg: 70, heightM: 1.75 } }],
},
],
task: async (input) => {
const mcp = await createMCPClient({ transport: { type: 'http', url: MCP_URL } })
try {
const result = await generateText({
model,
prompt: input,
tools: await mcp.tools(),
})
return result.toolCalls ?? []
}
finally {
await mcp.close()
}
},
scorers: [({ output, expected }) => toolCallAccuracy({ actualCalls: output, expectedCalls: expected })],
})
运行评估
首先确保您的 MCP 服务器正在运行:
pnpm dev
npm run dev
yarn dev
bun dev
然后在另一个终端中运行您的评估:
pnpm eval
npm run eval
yarn eval
bun eval
或者启动 Evalite UI 以使用可视化界面:
pnpm eval:ui
npm run eval:ui
yarn eval:ui
bun eval:ui
UI 界面位于 http://localhost:3006,显示每次评估的追踪信息、评分、输入和输出。
项目结构
我们建议将评估文件放在项目根目录的 test/ 目录中:
your-project/
├── server/
│ └── mcp/
│ ├── tools/
│ │ └── calculate-bmi.ts
│ ├── resources/
│ └── prompts/
├── test/
│ └── mcp.eval.ts # Your MCP eval tests
├── nuxt.config.ts
└── package.json
默认情况下,Evalite 会查找带有
.eval.ts 扩展名的文件。编写高效的评估
测试工具选择
验证模型是否选择了正确的工具:
test/mcp.eval.ts
evalite('Tool Selection', {
data: async () => [
{
input: 'List all available documentation pages',
expected: [{ toolName: 'list-pages' }],
},
{
input: 'Show me the installation guide',
expected: [{ toolName: 'get-page', input: { path: '/getting-started/installation' } }],
},
],
task: async (input) => {
const mcp = await createMCPClient({ transport: { type: 'http', url: MCP_URL } })
try {
const result = await generateText({
model,
prompt: input,
tools: await mcp.tools(),
})
return result.toolCalls ?? []
}
finally {
await mcp.close()
}
},
scorers: [({ output, expected }) => toolCallAccuracy({ actualCalls: output, expectedCalls: expected })],
})
测试多步骤工作流
对于需要多次工具调用的工作流,请增加 maxSteps:
test/mcp.eval.ts
evalite('Multi-Step Workflows', {
data: async () => [
{
input: 'Find the installation page and show me its content',
expected: [
{ toolName: 'list-pages' },
{ toolName: 'get-page', input: { path: '/getting-started/installation' } },
],
},
],
task: async (input) => {
const mcp = await createMCPClient({ transport: { type: 'http', url: MCP_URL } })
try {
const result = await generateText({
model,
prompt: input,
tools: await mcp.tools(),
maxSteps: 5, // 允许多次工具调用
})
return result.toolCalls ?? []
}
finally {
await mcp.close()
}
},
scorers: [({ output, expected }) => toolCallAccuracy({ actualCalls: output, expectedCalls: expected })],
})
分组相关评估
按功能或工具类别组织评估:
test/mcp.eval.ts
// 文档工具
evalite('Documentation Tools', {
data: async () => [
{ input: 'List all docs', expected: [{ toolName: 'list-pages' }] },
{ input: 'Get the intro page', expected: [{ toolName: 'get-page' }] },
],
// ...
})
// API 工具
evalite('API Tools', {
data: async () => [
{ input: 'Fetch user data', expected: [{ toolName: 'get-user' }] },
{ input: 'Create a new post', expected: [{ toolName: 'create-post' }] },
],
// ...
})
提示
- 保持提示词具体明确,以便模型选择预期的工具
- 使用真实的输入,匹配用户提出请求的实际表达方式
- 先从正常路径(happy-path)用例开始,然后再添加边界情况
- 测试参数提取,在提示词中包含具体的值
- 在部署前运行评估,以捕获工具行为中的回归问题