关于 Opik Mcp
Opik 官方 MCP 服务,面向希望通过 AI 编码客户端操作 Opik 这一大模型可观测性与评估平台的工程师。客户端可查看跟踪记录、记录评分并保存提示词版本。
主要功能
- 01读取 Opik 跟踪记录和项目数据
- 02创建跟踪评分并附理由
- 03保存提示词版本
- 04配置支持的 AI 客户端
适用场景
- 01查找项目中的失败跟踪记录
- 02在聊天会话中为跟踪记录评分
- 03保存修订后的提示词版本
- 04将编码客户端连接到 Opik 工作区
MCP 相关
向 MCP 客户端开放 Opik 工作区操作,包括读取跟踪记录和项目、创建评分及保存提示词版本。Opik Cloud 使用托管的 Streamable HTTP 服务;自托管和开源部署可运行本地 stdio 服务。
配置
远程服务无需本地安装。选择你使用的客户端,复制配置或使用一键安装。
https://www.comet.com/opik/api/v1/mcpclaude mcp add --transport http opik https://www.comet.com/opik/api/v1/mcp{"mcpServers":{"opik":{"type":"http","url":"https://www.comet.com/opik/api/v1/mcp"}}}在 Cursor 中打开{"servers":{"opik":{"type":"http","url":"https://www.comet.com/opik/api/v1/mcp"}}}在 VS Code 中打开{"mcpServers":{"opik":{"type":"http","url":"https://www.comet.com/opik/api/v1/mcp"}}}{"mcpServers":{"opik":{"serverUrl":"https://www.comet.com/opik/api/v1/mcp"}}}命令在终端中运行;JSON 粘贴到对应客户端的 MCP 配置后重启。需要授权的服务会在首次连接时提示登录。
工具
详细介绍
Opik MCP 服务
由 Comet 构建的开源 LLM 可观测性与评估平台 Opik 的官方模型上下文协议(MCP)服务。 将你的 AI 宿主(Claude Code、Cursor、VS Code Copilot、Codex、opencode 或任何 MCP 客户端)直接接入 Opik 工作区:读取跟踪记录、记录评分并保存提示词版本,所有操作都可在聊天中完成。
专为已经在使用 Opik、希望通过日常编码所用的同一 AI 助手来操作它的 LLM 工程师打造。
You: "Which traces in project 'demo' failed today?"
Claude: → list(entity_type="trace", project_name="demo") → "Three traces failed…"
You: "Score trace 7f2e… 0.9 on helpfulness with reason 'great recovery'."
Claude: → write(score.create) → done
快速开始
运行一条命令,即可在你机器上的 AI 客户端中设置 Opik,包括 Claude Code。它会查找你的 Opik(保存在 ~/.opik.config 中的实例、运行在 localhost 上的实例,或者询问你要使用哪一个),注册 MCP 服务、安装 Opik 技能包并检查连接。在 Opik Cloud 上无需处理 API 密钥:客户端会在浏览器中登录。此操作需要 uv,且无需 Opik SDK:
uvx opik@latest mcp configure
如果不使用终端(例如通过编码 Agent 或脚本操作),请指定客户端:
uvx opik@latest mcp configure --ai-client claude-code --skills
--ai-client 也支持 codex、cursor、vscode 和 opencode。以这种方式运行时,它会使用保存在 ~/.opik.config 中的 Opik(包括 API 密钥),或使用 localhost 上响应的实例;否则会停止并要求指定 --deployment。
当编码 Agent 收到“安装 opik mcp”的请求时,可通过 uvx opik-mcp@latest --help 获取完整步骤,包括需要向用户询问的内容。这些步骤与下文的使用编码 Agent 安装相同。
手动注册服务(使用手动设置中的客户端命令)会跳过 Opik 检查和技能包安装,因此适用于安装程序不支持的客户端。
| 你的 Opik | 服务 | 传输方式 | 登录 |
|---|---|---|---|
Opik Cloud(www.comet.com) | 托管服务,由 Comet 运行 | Streamable HTTP | 在浏览器中登录(OAuth);无需 API 密钥 |
| 自托管 Comet、开源 Opik | 本地服务,本软件包 | stdio | 环境变量;仅在部署需要时使用 API 密钥 |
客户端会在会话开始时加载 MCP 服务,因此设置完成后请启动新会话。
设置指南、故障排除和常见问题:comet.com/docs/opik/mcp-server。
Opik Cloud:托管服务
Comet 在 https://www.comet.com/opik/api/v1/mcp 运行该服务。客户端通过 HTTP 连接,并在首次使用时打开浏览器供你登录。无需安装、无需 API 密钥,也无需设置工作区:服务会使用你登录时选择的工作区。添加服务后,启动新会话并询问:“列出我的 Opik 项目”。
快速开始命令可为 Claude Code、Codex、Cursor、VS Code Copilot 和 opencode 完成设置,并安装技能包。在 Claude Code 中,插件只需一条命令即可完成相同设置。下方按钮可一键将服务添加到 Cursor 或 VS Code;其他手动注册方式见手动设置。
Claude Code 插件
opik 插件会安装 Opik 技能并注册 MCP 服务,默认使用托管服务:
/plugin install opik --marketplace comet-ml/opik-mcp
在 2.1.275 之前的 Claude Code 版本中,运行 /plugin marketplace add comet-ml/opik-mcp,然后运行 /plugin install opik@opik。技能会以 opik:<skill> 的形式加载,例如 opik:opik-instrument;/mcp 会将服务显示为 plugin:opik:opik-mcp。
安装时会询问 Opik MCP 服务 URL:使用 Opik Cloud 时保留默认值;对于运行 MCP OAuth 服务的自托管 Comet,请输入 https://<host>/opik/api/v1/mcp。之后可通过 /plugin configure opik@opik 更改。启动新会话,然后在 /mcp → Authenticate 中登录。对于其他自托管或开源 Opik,请使用快速开始命令。
claude.ai 聊天会忽略根据设置生成的 URL,因此插件在该环境中只会添加技能。Claude Code 不会自行更新此市场中的插件:运行 /plugin marketplace update opik,然后运行 /plugin update opik@opik;也可以在 /plugin 中为该市场开启自动更新。此市场提供 main 分支,其内容可能领先于最新版本。只有在每次发布时插件版本发生变化,更新才会生效。
如果你之前已在同一 URL 添加过 opik-mcp,Claude Code 会保留你添加的副本,并跳过插件中的副本。如果你添加的是另一个服务,例如本地的 uvx opik-mcp,则两个服务都会加载:运行 claude mcp remove opik-mcp,只保留插件中的服务。技能包中的技能也会与插件中的副本同时加载;运行 npx skills remove --global --agent claude-code 即可移除,届时系统会询问要移除哪些技能。
可自托管和开源的 Opik:本地服务
opik-mcp 在你的机器上运行:客户端通过 uvx opik-mcp 启动它,并
通过 stdio 与它通信。快速开始中的命令会根据你的
~/.opik.config 或本地 Opik 配置它;如需手动注册,请参阅
手动设置。只需安装一次 uv;首次使用时,它会
获取软件包,并在需要时获取 Python 3.13:
curl -LsSf https://astral.sh/uv/install.sh | sh # macOS / Linux
# or: brew install uv
uvx opik-mcp 会复用 uv 缓存的副本,因此启动很快;
uv cache clean opik-mcp 会让下次启动获取最新版本。
uvx opik-mcp@latest 每次启动时都会查询 PyPI,这会多花大约 1.5 秒。Codex
会等待 mcp_optional_startup_grace_ms 指定的时间(默认 1 秒),让服务在
生成第一个工具列表前启动,因此启动较慢可能导致工具未出现在第一轮中。
本 README 中的一次性命令(opik mcp configure、
opik mcp status、--help、--check)都带有 @latest,因此绝不会运行
uv 几个月前缓存的副本。
环境变量用于将服务指向你的 Opik:
| 你的 Opik | 环境变量 |
|---|---|
| 此机器上的开源 Opik | OPIK_URL=http://localhost:5173/api |
| 服务器上的开源 Opik | OPIK_URL=https://<host>/api,只有在部署启用了身份验证时才需要 OPIK_API_KEY |
可自托管的 Comet 平台(Opik UI 位于 https://<host>/opik) | COMET_URL_OVERRIDE=https://<host>、OPIK_WORKSPACE、OPIK_API_KEY |
- 开源版本在
/api提供 API,且只有一个名为default的工作区,因此 不需要设置OPIK_WORKSPACE。COMET_URL_OVERRIDE会将服务指向/opik/api,而开源版本并未提供此路径。 - 可自托管的 Comet 有命名工作区。将
OPIK_WORKSPACE设置为 Opik URL 中/opik/后面的部分;如果未设置,读取操作会使用你帐户的默认工作区, 但不会报错提示。 - 运行 MCP OAuth 服务(默认关闭)的可自托管 Comet 也可以改用托管流程,
地址为
https://<host>/opik/api/v1/mcp。 - 替换所有值。服务会拒绝
<your-workspace>或${input:OPIK_WORKSPACE}等 占位符工作区;占位符 URL 会原样发送,并导致连接失败。 - 在
env块中设置OPIK_MCP_ANALYTICS_SOURCE="",可让可自托管的安装 不在遥测事件中使用云端 Comet 来源标签。
将服务添加到客户端之前,请检查设置:使用相同的环境变量运行服务并添加
--check。它会向 Opik 发起一次调用,并显示工作区及其项目数量,或者说明
需要修复的内容并附上文档链接,然后以 0 或 1 退出。
在新会话开始前,客户端无法为你验证这些信息:即使密钥错误,Claude Code 也会显示 Connected,而 Codex 在此之前不会启动任何内容。
OPIK_URL=http://localhost:5173/api uvx opik-mcp@latest --check
然后将它注册到客户端:手动设置本地服务。
使用编码 Agent 安装
当 AI Agent 被要求安装服务时,例如收到“安装 opik mcp”的指令。目标是
为用户的 Opik 注册服务、安装 Opik 技能包,并让用户完成登录。根据这台
机器上的信息判断使用哪个 Opik,只询问无法自行确定的内容:每条消息只问
一个问题,并在提下一个问题前等待用户回答。第 3 步的安装程序会一次性
完成整个设置,因此运行前请先确定第 1 步和第 2 步的内容。运行
uvx opik-mcp@latest --help 可查看这些步骤。
-
查看现有配置。
uvx opik@latest mcp status它会显示
~/.opik.config中保存的 Opik(URL 和工作区,不包括密钥),以及已配置该服务的客户端。在 Claude Code 中,还要运行claude mcp list:它会显示 claude.ai 连接器和以其他名称添加的条目。它也会打印每个条目的命令;旧的 npx 条目可能包含 API 密钥:不要复述该命令。- 任何名称下的
https://www.comet.com/opik/api/v1/mcp服务(例如 claude.ai 连接器)都表示它已注册:不要重复添加。单独安装技能包即可:npx skills add comet-ml/opik-skills -g --all。如果服务显示! Needs authentication,请转到第 4 步。 - 安装程序会在不询问的情况下替换现有的
opik-mcp条目,例如旧的 npx 服务。运行前请先征求用户同意。
- 任何名称下的
-
找到用户的 Opik。
- 已保存在
~/.opik.config中:使用它,并告诉用户你正在配置哪一个。安装程序会读取该文件,包括 API 密钥,因此不要索要密钥。 - 没有
~/.opik.config:运行curl -s http://localhost:5173/api/is-alive/ping。如果有响应,说明这台机器上运行着开源版 Opik。在沙盒 shell 中(例如 Codex 的 shell),没有响应可能意味着 shell 无法访问网络,而不是没有 Opik。 - 两者都没有:先询问,不要自行选择。项目中的 Opik URL(例如
.env中的OPIK_URL_OVERRIDE)可以让问题变成是非题。否则请问:“你使用的是哪个 Opik:Opik Cloud(www.comet.com)、开源版 Opik(其 URL),还是可自托管的 Comet 平台(其 URL 和工作区)?”
- 已保存在
-
为你正在使用的客户端运行安装程序。 它会安装 Opik 技能包和服务,无论是否带有
--skills;在之后提供给用户运行的命令中保留该标志。对于 Opik Cloud,安装程序会打开浏览器进行登录并等待一分钟,因此请先告知用户。uvx opik@latest mcp configure --ai-client claude-code --skills--ai-client还支持codex、cursor、vscode和opencode。如果 Opik 保存在~/.opik.config中,或正在 localhost 上运行,请直接运行命令:--deployment会将已保存的配置(包括 API 密钥)暂时移开。如果两者都不是,请根据用户在第 2 步中指定的 Opik 添加相应标志:用户的 Opik 添加 Opik Cloud, www.comet.com--deployment cloud开源版 Opik --deployment local;如果不在 localhost 上,再加上--url <url>可自托管的 Comet 平台,URL 中包含 /opik/--deployment self-hosted --url <url> --workspace <workspace>,并在 shell 中设置OPIK_API_KEY如果运行失败(例如 Opik 没有响应),请告诉用户打印出的内容,以及需要检查的事项,例如 VPN 或 URL。不要切换到其他 Opik。
-
登录(适用于 Opik Cloud)。 如果安装程序报告服务尚未登录,请让用户运行
claude mcp login opik-mcp,或在 Claude Code 会话中运行/mcp,而不是由你代为运行:该命令会等待浏览器操作。claude.ai 连接器可通过/mcp登录。登录时会要求指定工作区;如果~/.opik.config中保存了工作区,请告知用户该工作区名称。 -
完成。 说明已安装的内容和剩余步骤。注明技能包名称:Opik 技能,该技能包已为每个项目安装,可教会 Agent 使用 Opik 进行埋点、评估和调试。客户端会在会话启动时加载 MCP 服务和技能:请用户启动新会话,然后尝试 “list my Opik projects”。
无论采用哪种方式:
- 不要让用户将 API 密钥粘贴到聊天中。托管服务不需要密钥;否则,请从 shell 环境(
"$OPIK_API_KEY")中读取,或让用户自行运行命令。 - 不要猜测工作区。它是用户 Opik URL 中
comet.com/opik/之后的部分(如果使用自托管的 Comet,则是/opik/之后的部分)。 - 不要打印
~/.claude.json或~/.opik.config;两者都可能包含 API 密钥。uvx opik@latest mcp status和claude mcp list会显示所需信息,安装程序也会自行读取配置。 - 如果权限检查阻止了某条命令,不要绕过它。向用户提供要运行的命令(在 Claude Code 中,运行提示词前加上
!)。
对于安装程序不支持的客户端,请使用手动设置中的命令手动注册:Opik Cloud 使用托管服务,其余情况使用本地服务。
- 注册本地服务前,请使用将要传入的环境变量运行它,并加上
--check;在 shell 中导出OPIK_API_KEY,不要将其写在命令中:OPIK_URL=http://localhost:5173/api uvx opik-mcp@latest --check。如果成功,它会以退出代码 0 结束并指出检测到的工作区;否则会打印需要修复的内容。注册后,即使密钥错误,Claude Code 也会报告已连接,而 Codex 没有检查功能。 - Claude Code 不允许覆盖现有的
opik-mcp条目,因此请先使用claude mcp remove opik-mcp --scope user将其移除;Codex 的add会替换现有条目。 - 注册后,在 Claude Code 中仅查看状态行:
claude mcp get opik-mcp | grep Status。完整输出会打印env块,其中包含 API 密钥。托管服务会显示! Needs authentication,直到运行claude mcp login opik-mcp。Codex 在会话启动前不会启动服务;codex mcp get opik-mcp会显示已存储的内容,并屏蔽环境变量值。
手动设置(不检查 Opik,不安装技能包)
快速开始中的命令会为 Claude Code、Codex、Cursor、VS Code Copilot 和 opencode 完成所有设置,还会检查你使用的 Opik 并安装技能包。只有在使用其他客户端或想查看安装程序写入的内容时,才需要手动注册。为用户安装的编码 Agent 应运行安装程序:请参阅使用编码 Agent 安装。
托管服务(Opik Cloud)
手动设置 Claude Code
claude mcp add --scope user --transport http opik-mcp https://www.comet.com/opik/api/v1/mcp
然后在 Claude Code 会话中通过 /mcp → Authenticate 登录。这会打开浏览器,由键盘前的用户完成操作;用户也可以在自己的终端中运行 claude mcp login opik-mcp,效果相同。--scope user 会让所有项目都能使用该服务;不加此参数,Claude Code 只会在当前目录中注册该服务。通过 SSH 连接时,claude mcp login opik-mcp --no-browser 会打印登录 URL,供你在自己的机器上打开;最后一步需要交互式终端(ssh -t)。
手动设置 Codex
codex mcp add opik-mcp --url https://www.comet.com/opik/api/v1/mcp
add 会打开登录页面;codex mcp login opik-mcp 也会再次打开该页面。在 ~/.codex/config.toml 中,同一服务的配置如下:
[mcp_servers.opik-mcp]
url = "https://www.comet.com/opik/api/v1/mcp"
手动设置 Cursor
使用托管服务下方的按钮,或将以下内容添加到 ~/.cursor/mcp.json:
{
"mcpServers": {
"opik-mcp": {
"url": "https://www.comet.com/opik/api/v1/mcp"
}
}
}
手动设置 VS Code Copilot
使用托管服务下方的按钮,或将以下内容添加到工作区中的 .vscode/mcp.json,或添加到用户的 mcp.json(MCP: Open User Configuration):
{
"servers": {
"opik-mcp": {
"type": "http",
"url": "https://www.comet.com/opik/api/v1/mcp"
}
}
}
其他客户端
任何支持 URL 的客户端都可以使用托管服务:
npx add-mcp https://www.comet.com/opik/api/v1/mcp --name opik-mcp
只能启动本地命令的客户端,可以通过 npx -y mcp-remote https://www.comet.com/opik/api/v1/mcp 访问该服务。
使用 API 密钥连接 Opik Cloud
如果无法完成浏览器登录,例如 Agent 通过脚本在无人值守的情况下运行,或客户端不支持 MCP OAuth,请改用
comet.com/api/my/settings/ 中的 API 密钥,
并让本地服务指向 Opik Cloud:
claude mcp add --scope user opik-mcp \
--env OPIK_API_KEY="$OPIK_API_KEY" \
--env OPIK_WORKSPACE=<workspace> \
-- uvx opik-mcp
其他客户端也在其 env 块中使用相同的两个变量。将
OPIK_WORKSPACE 设为 Opik URL 中 comet.com/opik/ 后面的路径段
(https://www.comet.com/opik/acme-ai/projects → acme-ai)。如果未设置,
服务会发送 default,Comet 会将其解析为你账户的默认
工作区,因此读取操作可能会来自错误的工作区,且不会报错。
本地服务(自托管和开源 Opik)
示例使用本地开源版 Opik。对于自托管的 Comet,请替换为表格 中的三个变量。添加服务后,启动新会话 并询问:“列出我的 Opik 项目”。
手动配置 Claude Code
claude mcp add --scope user opik-mcp --env OPIK_URL=http://localhost:5173/api -- uvx opik-mcp
对于自托管的 Comet,请在 shell 的 OPIK_API_KEY 中设置密钥:
claude mcp add --scope user opik-mcp \
--env COMET_URL_OVERRIDE=https://<host> \
--env OPIK_WORKSPACE=<workspace> \
--env OPIK_API_KEY="$OPIK_API_KEY" \
-- uvx opik-mcp
或者直接编辑 ~/.claude.json:
{
"mcpServers": {
"opik-mcp": {
"type": "stdio",
"command": "uvx",
"args": ["opik-mcp"],
"env": {
"OPIK_URL": "http://localhost:5173/api"
}
}
}
}
服务启动后,claude mcp get opik-mcp 会显示 ✔ Connected。这并不能
证明 URL 或密钥正确,因为只有调用工具才会连接到 Opik;
--check 才能验证。它还会打印 env 块,其中包含 API 密钥。
手动配置 Codex
codex mcp add opik-mcp --env OPIK_URL=http://localhost:5173/api -- uvx opik-mcp
或者编辑 ~/.codex/config.toml:
[mcp_servers.opik-mcp]
command = "uvx"
args = ["opik-mcp"]
env = { OPIK_URL = "http://localhost:5173/api" }
# On a self-hosted Comet, forward the key from the environment Codex starts in,
# so it stays out of this file:
# env_vars = ["OPIK_API_KEY"]
# Time allowed for the server to start (default 10 s); the first start
# downloads the package.
startup_timeout_sec = 30
Codex 只会向本地服务提供 env 中的变量和 env_vars 中的名称,因此,仅在 shell 中导出的密钥不会传递给服务。
手动配置 Cursor
将以下内容添加到 ~/.cursor/mcp.json(全局)或 .cursor/mcp.json(项目),或者使用
Cmd+Shift+J → Features → Model Context Protocol:
{
"mcpServers": {
"opik-mcp": {
"type": "stdio",
"command": "uvx",
"args": ["opik-mcp"],
"env": {
"OPIK_URL": "http://localhost:5173/api"
}
}
}
}
Cursor 的 60s 超时。 Cursor 对工具调用设置了硬性超时,即使收到进度通知也不会重置。 请参阅已知宿主限制。
手动配置 VS Code Copilot
将以下内容添加到工作区中的 .vscode/mcp.json,或添加到用户的 mcp.json
(MCP: Open User Configuration):
{
"servers": {
"opik-mcp": {
"type": "stdio",
"command": "uvx",
"args": ["opik-mcp"],
"env": {
"OPIK_URL": "http://localhost:5173/api"
}
}
}
}
MCP Inspector(手动测试)
OPIK_URL=http://localhost:5173/api npx @modelcontextprotocol/inspector uvx opik-mcp
从 npx opik-mcp 迁移?
TypeScript 服务(npm opik-mcp@2)已弃用,并将于 2026-11-15 停止处理
请求。全新安装请运行快速入门中的命令;uvx opik-mcp 是客户端用于启动服务的命令,而不是安装程序。要迁移现有的 Opik Cloud 配置,
请切换到托管服务并移除 API 密钥。否则,请在 MCP 客户端
配置中将 npx -y opik-mcp 替换为 uvx opik-mcp。部分环境变量已重命名,命令行标志也不再读取:请参阅迁移
指南。
支持政策:DEPRECATED.md。
TypeScript 源码位于 git 标签 legacy-typescript-final。
工具
opik-mcp 提供了一组精简、面向结果的工具,覆盖完整
生命周期(读取 → 标注 → 整理 → 编写 → 迭代)。
| 工具 | 用途 |
|---|---|
read | 按 ID、名称或 opik:// URI 通用读取 |
list | 通用列表,可选名称筛选和分页 |
write | 通用写入——记录 traces/spans、评分、评论、保存提示词、管理数据集和实验 |
schema | 检查写入操作的 schema(供大模型构造有效负载) |
read_skill | 读取此服务附带的一项 Opik Agent 技能 |
read
用于回答任何“向我展示 X”的问题。接受 entity_type,以及 id
(UUID,或对于支持名称的类型,使用名称)或完整的 opik:// URI。复合读取
(trace、prompt、thread、agent_insights_issue)会内嵌其子项,因此
单次调用即可返回完整信息。
你指定的记录会完整返回。内联子项则不会:它们的正文通过后端的 truncate=true 获取,因此 ClickHouse 中超过约 10 KB 的字段会被截断,base64 图片会替换为 "[image]"——否则,同一附件在 200 个 span 中回显,读取成本就会超过其他所有内容。答案会在 spanBodies / messageBodies 中说明这一点;任何子项都可以通过其自身的 read("span", id) 或 read("trace", trace_id) 再次完整读取,因为这些请求命中的端点根本没有 truncate 参数。
内联集合的长度也有限制:200 个 span、200 个回合、100 个提示词版本。超过限制时,spansTruncated / messagesTruncated / versionsTruncated 会是 true,旁边的 moreSpans / moreMessages / moreVersions 行会给出数量,以及从内联部分停止处继续读取的确切 list(...) 调用。
支持的实体: project、trace、span、dataset、dataset_item、experiment、prompt、thread、agent_insights_issue。project、experiment、prompt、dataset 支持按名称查找(速度较慢——需要两次 API 调用——且可能返回多个匹配项)。thread 和 agent_insights_issue 属于项目范围:传入 project_id 或 project_name,或者传入包含项目信息的链接/URI。dataset 和 dataset_item 以前称为 test_suite 和 test_suite_item;旧名称仍可解析,但不会对外展示,新代码应使用新名称。
read(entity_type="trace", id="7f2e3c8a-…")
read(entity_type="project", id="demo") # name lookup
read(entity_type="trace", id="opik://traces/7f2e3c8a-…")
read(entity_type="agent_insights_issue", id="<issue-uuid>", project_id="<project-uuid>")
read(
entity_type="agent_insights_issue",
id="https://www.comet.com/opik/<ws>/projects/<pid>/diagnostics?issue=<id>",
)
从 Opik UI 复制的链接可用作 id:thread 链接或 Diagnostics 页面链接包含项目信息,因此无需 project_id,实体类型也会从链接中获取。
一次 project 读取就能回答“我的项目运行情况如何”。它会返回 {project, summary, vocabulary, contains, url}:记录,以及 Logs 页面以卡片显示的四项指标(trace 数量、错误率、平均时长、总成本),统计范围为最近 7 天与之前 7 天的对比,仅包含 SDK 流量,与屏幕上显示的内容一致。since / until 可以调整此时间范围;UI 打开时使用的是 since="30d"。如果某个时段没有 trace,期间的比率或平均值会返回 null,因为没有流量的一周显示 0% 错误率,看起来就像运行状况良好的一周。
在询问其他内容之前,你需要先查看 vocabulary:它是项目反馈评分名称、token 使用键,以及为其 trace 评分的自动化规则组成的映射。这些名称需要填入筛选条件或下文的 series=;如果凭猜测填写,返回的空页面看起来就像是好消息。评分名称和规则有数量上限,但始终会报告实际总数,并指出用于获取其余内容的调用;使用键则会完整列出,因为没有其他方式能枚举它们。contains 会列出最新的实验、数据集、提示词版本和优化运行,因此无需再调用四次就能了解“这里最近发生了什么”。加载失败的部分会明确说明,而不会看起来像空内容;空部分则会省略。
agent_insights_issue 读取会返回 {issue, example_trace_ids, details}:Diagnostics 问题记录(名称、描述、原因、建议的修复方法、严重性、状态)、展示该问题的去重 trace ID(与 Diagnostics 页面显示的样本相同——使用 read("trace", id) 打开其中一个),以及按天汇总的数据。不会内联 trace 正文,因此读取只需一次后端调用。since / until 可以缩小按天汇总行的范围;默认范围为全部时间。如果服务端知道 Opik URL 和会话的工作区,读取结果还会包含 url(问题的 Diagnostics 页面)和 trace_url_template(指向任一示例 trace 的深层链接),方便助手提供可点击的内容;如果 OAuth 会话无法解析其工作区,则会省略链接,而不会猜测。
追踪本身不包含 URL——无法从 read 或 list 返回的字段推导出链接,猜测链接格式也会返回 404。会话说明中提供了相应的模板:.../v1/session/redirect/projects/?trace_id={trace_id}&path=...,因此助手只需填入 ID 并提供链接即可。链接会经过 opik-backend 的重定向,由它根据追踪解析项目和工作区,因此即使无法使用直接项目 URL,也能正常工作;这也包括尚未解析工作区的 OAuth 会话。这与 Python SDK 为追踪打印的链接相同。
list
分页浏览或搜索集合。项目范围内的类型(trace、span、thread、agent_insights_issue、dataset_item、prompt_version)需要指定父级:项目 UUID 或名称、数据集 UUID,或提示词 UUID。
list(entity_type="experiment", page=1, size=25)
list(entity_type="experiment", name="rerank") # name substring filter
list(entity_type="agent_insights_issue", project_name="demo") # open Diagnostics issues
list(entity_type="agent_insights_issue", project_id="<uuid>", status="resolved")
list(entity_type="trace", project_name="demo") # latest traces of one project
list(
entity_type="trace", project_name="demo", filters="error_info is_not_empty AND duration > 5000"
)
list(
entity_type="span",
project_name="demo", # spans across the whole project
filters='type = "llm" AND usage.total_tokens > 10000',
)
list(
entity_type="thread",
project_name="demo",
filters="number_of_messages > 20 AND feedback_scores.helpfulness < 0.5",
)
list(entity_type="experiment", filters='dataset_id = "<dataset-uuid>" AND tags contains "baseline"')
筛选器。 trace、span、thread、experiment 和 dataset_item 接受 OQL 字符串,语法与 SDK 的 search_traces(filter_string=…) 相同:
<field>[.<key>] <op> <value> [AND ...]
ops: = != > >= < <= contains not_contains starts_with ends_with is_empty is_not_empty in not_in
字符串使用双引号,数字不加引号,duration 的单位为毫秒,日期使用带时区的 ISO-8601 时间点("2026-09-08T10:00:00Z")。分数和字典需要指定键:feedback_scores.accuracy < 0.5、metadata.environment = "prod"。唯一的连接符是 AND。
与 UI 的 Logs 页面一样,追踪、跨度和线程列表会添加 source = "sdk",以免评估器、游乐场和实验追踪造成干扰;如需查看这些内容,请自行指定 source。输出的第一行会回显已应用的筛选器。
无效筛选器会在到达后端之前报错,并说明如何修正:语法错误的位置、最接近的字段名称、该字段类型的有效运算符,或预期的值格式。具有固定值集合的字段(source、跨度 type、线程 status、visibility_mode)也会进行校验,包括 in 列表中的每个元素。后端会自行校验的只有 source;遇到未知值时,它会返回 500 而不是 400,因此 source = "SDK" 中的大写字母原本会导致含糊不清的服务器错误。其他字段会按字符串比较,并返回空页;当实际含义是“没有此类值”时,这看起来就像“没有匹配项”。调用 schema("list.trace")(或 list.span、list.thread、list.experiment)可查看完整字段参考,包括接受的值。
在数据集中查找一个案例。 list(entity_type="dataset_item", dataset_id=…) 会筛选案例本身:data.<key> 用于数据集创建时使用的键,full_data 用于匹配整个载荷中的子字符串(会扫描全部数据——可以指定键时尽量指定),此外还可使用 id、tags、source、trace_id、span_id 和时间戳。data.<key> 只接受六种字符串运算符(=、!=、contains、not_contains、starts_with、ends_with);后端会对比较操作返回 400,因此此类操作会在调用前被拒绝。该端点不支持排序或自由文本搜索——sort 会被拒绝,而不会被忽略。read(entity_type="dataset_item", id=…) 会返回一个完整案例,可用来读取表格中被截断的值。
list(entity_type="dataset_item", dataset_id="<uuid>", filters='data.question contains "install"')
list(
entity_type="dataset_item", dataset_id="<uuid>", filters='trace_id = "<trace-uuid>"'
) # the case made from that trace
read(entity_type="dataset_item", id="<item-uuid>") # the case, uncut
指定 experiment_ids 后,相同的列表会用于比较——也就是附带各次运行的案例——并会筛选运行数据(feedback_scores.<name>、output、duration)。两者使用不同的字段集和后端端点:schema("list.dataset_item_case") 对应数据集自身的案例,schema("list.dataset_item") 对应比较结果。
排序。 trace、span、thread 和 experiment 接受 sort="<field> [asc|desc]";默认按降序排序,且只支持一个字段:sort="duration desc"、sort="total_estimated_cost"、sort="feedback_scores.accuracy asc"、sort="usage.total_tokens"。调用前会根据实体可排序字段列表校验字段,因为后端会静默忽略无法排序的字段。在超大型工作区中,后端会完全取消排序;发生这种情况时,页眉会注明。
dataset_item 仅在作为比较项(与 experiment_ids 一起)时支持排序:items 端点不接受排序参数,因此对普通列表进行排序会被拒绝,而不是忽略。
时间窗口与搜索。 trace、span 和 thread 接受 since 和 until,每个参数可以是相对时间段("30m"、"1h"、"7d"),也可以是带时区的 ISO-8601 时间点,因此查询“过去一小时”无需进行时钟运算。时间窗口依据记录创建时间,对后端而言开销较低;对于实时流量,它与 start_time 的误差在几秒以内。如需精确边界,请在 filters 中设置 start_time。这三种类型也都接受 search,可在 id、name、input、output、metadata、tags 和 thread id 中任意位置匹配自由文本。搜索会扫描后端的整个项目,因此大型项目的首次调用可能需要几十秒。这类调用的超时设为 60 秒。添加 since 后,搜索会再次变快。
读取表格。 时长标记为 duration_ms / ttft_ms,并以整数毫秒显示;在 filters 和 sort 中,该字段仍为 duration。时间戳显示到秒,成本以普通小数显示。项目行包含 last_updated_trace_at,便于查看哪个项目有实时流量;thread 行包含首条消息。在时间窗口下返回空页时,会说明该项目最近一次 trace 的时间;在默认的 source = "sdk" 下返回空页时,会说明如何查看其他来源。拼错的 project_name 会返回最接近的现有名称。
list(
entity_type="trace",
project_name="demo",
since="1h",
filters="error_info is_not_empty",
sort="duration desc",
)
list(entity_type="trace", project_name="demo", search="order-42")
Diagnostics 问题。 agent_insights_issue 是通过 MCP 查看 Diagnostics 页面的入口:它返回 Opik 的 Diagnostics 作业为某个项目归类的重复故障,并按照 UI 的排序方式排列(最近出现的排在最前)。列包括 severity、status、total_occurrences(历史总数)、latest_count(最近一个报告日的数量,也是问题自身描述中引用的数字)和 last_seen。默认列出未解决的问题;其余问题可传入 status="resolved" 或 status="closed"。read 和 list 也接受 issue,这是 UI 对这些问题的称呼;长名称则用于 entity_type 枚举,因此该实体不会在其中重复出现。总数为历史累计,以便与 UI 保持一致;与 traces 相同的 since / until 可缩小时间窗口,但由于 Diagnostics 按天汇总,窗口会截断到 UTC 报告日。
列表为空时会说明原因,因为“没有故障”和“没有人启用 Diagnostics”在其他情况下显示相同。有五种状态:此部署不提供 Diagnostics、此项目未启用、已关闭、已启用但近期未扫描,或已启用且无问题,并附上最近一次扫描的时间。可采取操作的状态会说明要调用的操作;每种状态都会链接到项目的 Diagnostics 页面。
列表非空时会注明日期。问题来自最近一次扫描的归类,因此回复末尾会显示 Report covers data through <time>;如果你请求的时间窗口超出该范围,还会指出未覆盖的时间段以及如何补齐:如果重新扫描覆盖范围足够早,则使用 trigger;否则使用它提供的 since 查询原始 traces。对于每天夜间扫描的项目,如果请求一周的数据,归类结果会缺少最后一天;这里会对此作出说明。
write("agent_insights_job.enable", {"project_name": "demo"}) 会启用 Diagnostics。此后它会每日扫描,重复调用也安全。write("agent_insights_job.trigger", …) 会立即扫描最近 24 小时,无需等待夜间运行。两者要求的权限与读取问题相同;如果部署不提供 Diagnostics,两者都会拒绝执行。
问题的整个生命周期可以通过
write("agent_insights_issue.resolve", {"issue_id": "<uuid>", "project_name": "demo"})
将其标记为已处理;若问题不值得处理,则使用 …close,使用 …reopen 则可将问题重新放回待处理列表。这三个操作所需的权限相同,并会返回问题转移到的视图链接,因为已解决的问题不会显示在默认页面上。是否修复故障需要自行判断,所以只有在你提出要求时才使用这些操作:助手在问题排查期间不应擅自整理列表。
随时间变化的指标。 project_metric 会将项目的某项指标绘制成按时间分段的表格,其中包括 trace、span 和 thread 数量、时长、错误率、成本、令牌用量和反馈评分。它回答的是概览之后的那个问题:何时发生了变化。
list(entity_type="project_metric", project_name="demo", metric_type="trace_count")
list(
entity_type="project_metric",
project_name="demo",
metric_type="trace_error_rate",
since="14d",
interval="daily",
)
list(
entity_type="project_metric", project_name="demo", metric_type="span_count", breakdown="model"
) # one column per model
list(
entity_type="project_metric",
project_name="demo",
metric_type="span_duration",
breakdown="model",
series="p99",
) # the p99 of each model
行代表时间段,而非记录,因此会拒绝 page、size 和 sort,而不是忽略它们。interval 可以是 hourly、daily、weekly 或 total;若未指定,则会像 Metrics 标签页一样根据时间范围选择——最多 3 天按小时,最多 30 天按天,超过 30 天按周——因此默认图表无论时间范围多长都只有几十行;按小时查看一个月(721 行)则需要主动指定。since / until 与其他地方接受的格式相同,默认范围为最近 7 天。filters 使用指标所属实体的字段,因此 span 指标会按 span 字段进行筛选。
breakdown 会按 tags、name、error_info、error_type、model、provider、span_type、guardrail_name 或 metadata.<key> 拆分每个时间段。并非每项指标都支持其中的每种拆分方式,且有 7 项指标完全不支持;该工具会在调用后端前确认支持情况,并在存在能回答相同问题的指标时指出其名称。有三类指标会同时返回多个系列(时长按 p50/p90/p99、每个名称对应的反馈评分、每个键对应的令牌用量),而后端分组时每次只能绘制其中一个系列,因此需要用 series= 选择:百分位数、评分名称或用量键。时长默认使用 p50,令牌用量默认使用 total_tokens,并会在首行回显所用的值。
空时间段会被省略,并在下方统计数量,因此安静的月份只会显示几行,而不会出现一列零值;没有 trace 的时间段不会显示速率,而不是将其报告为零。
使用 schema("list.project_metric") 查看指标表、时间间隔以及各指标的分组矩阵。
项目名称。 score_name 会列出项目中记录的反馈评分名称,online_rule 会列出该项目配置的自动化规则评估器;大多数这类名称都来自这里。两者都是 read("project", …) 中包含的同一批完整分页列表,适用于概览中的列表受限、无法满足需求的情况。
list(entity_type="score_name", project_name="demo")
list(entity_type="online_rule", project_name="demo")
write
通用写入分发器。传入 operation 和 data,分发器会验证负载、应用合适的 REST 动词,并返回后端响应。
操作:
| 操作 | 功能 |
|---|---|
trace.create | 记录单条 trace(或批量记录)。作为 spans、scores 和 comments 的父级。 |
trace.update | 完成或修改现有 trace。 |
span.create | 在现有 trace 上记录 span(或批量记录)。 |
score.create | 为 trace、span 或 thread 添加数值反馈评分。 |
comment.create | 为 trace、span 或 thread 添加自由文本评论。 |
prompt_version.save | 保存新的提示词版本(如果不存在,则按名称创建提示词)。 |
dataset.create | 创建数据集——type: "test_suite" 会将其设为评估测试套件。 |
dataset_item.upsert | 将条目插入或更新到数据集(始终使用 envelope 结构)。 |
experiment.create | 创建与数据集关联的实验。 |
experiment_item.create | 将 trace 和 dataset_item 行关联到实验。 |
thread.close | 关闭 thread(将其标记为非活跃)。传入 thread_id 和项目。 |
thread.open | 重新打开已关闭的 thread。传入 thread_id 和项目。 |
agent_insights_job.enable | 为项目开启 Diagnostics(每日扫描,可安全重复执行)。 |
agent_insights_job.trigger | 立即运行 Diagnostics 扫描,范围为过去 24 小时。 |
agent_insights_issue.resolve | 将 Diagnostics 问题标记为已处理(先询问用户)。 |
agent_insights_issue.close | 将 Diagnostics 问题标记为无需采取行动(先询问用户)。 |
agent_insights_issue.reopen | 将已解决或已关闭的 Diagnostics 问题重新放回未处理列表。 |
write(
operation="score.create",
data={
"target": "trace",
"target_id": "7f2e3c8a-…",
"name": "helpfulness",
"value": 0.9,
"reason": "great recovery",
},
)
schema
调用写入操作之前,先检查其确切的 JSON 结构和必填字段——当你不确定 data 应采用什么格式时,这很有用。返回 schema、OAuth 作用域和一个通过验证的示例。仅查询,不会调用后端。
schema(operation="score.create")
schema(operation="prompt_version.save")
同一工具还会针对 list.trace、list.span、list.thread 和 list.experiment,返回该实体对应的 list 工具参考信息:每个可筛选字段的类型和有效运算符、可排序字段、是否支持时间范围和全文搜索,以及两个筛选示例。
schema(operation="list.trace")
配置
这些设置用于配置本地服务;每项设置都是一个环境变量。Opik Cloud 上的托管服务不使用这些设置。
身份 / 端点
| 变量 | 默认值 | 说明 |
|---|---|---|
OPIK_API_KEY | — | 用于可自托管的 Comet,或在未使用托管服务时用于 Opik Cloud 的 API key。开源 Opik 无需此项,除非部署额外启用了身份验证。 |
OPIK_WORKSPACE | 未设置 | 工作区名称。在云端使用 API key 时,若未设置,则会发送 default,并解析为你账号的默认工作区——如果你使用其他工作区,请显式设置,否则读取操作可能会静默地从错误的工作区获取数据。使用 OAuth 时以及在本地 / OSS 环境中请保持未设置(这些环境中只有 default 工作区)。 |
COMET_WORKSPACE | — | OPIK_WORKSPACE 的弃用别名(用于向后兼容)。若两者都已设置,则以 OPIK_WORKSPACE 为准。 |
COMET_WORKSPACE_ID | 未设置 | 可选的工作区 UUID。设置后会写入分析事件,并优先于解析得到的工作区 ID。极少需要设置——OAuth 安装会自动从令牌中获取 UUID。 |
COMET_URL_OVERRIDE | https://www.comet.com | 设置为你自托管的 Comet 主机,或用于预发布环境的 https://dev.comet.com。 |
OPIK_URL | 由 COMET_URL_OVERRIDE + /opik/api 派生 | 用于开源 Opik,因为它在 /api 提供 API(本地地址为 http://localhost:5173/api)。在 Comet 平台上,只有当 Opik 所在主机 / 路径与 Comet UI 不同时才需要覆盖此设置。 |
OPIK_DEFAULT_PROJECT_NAME | 未设置 | 设置后,每个会话的 instructions 块都会告知大模型,除非用户指定其他项目,否则每次工具调用都将此值作为 project_name 传入。 |
服务 / 传输方式
| 变量 | 默认值 | 说明 |
|---|---|---|
OPIK_MCP_TRANSPORT | stdio | 对于由宿主启动的服务,使用 stdio;要监听端口,使用 streamable-http。 |
OPIK_MCP_HOST | 127.0.0.1 | uvicorn 绑定的主机(仅限 streamable-http)。 |
OPIK_MCP_PORT | 8080 | uvicorn 绑定的端口(仅限 streamable-http)。 |
OPIK_MCP_RELOAD | false | 设为 true 可启用 uvicorn --reload(仅用于开发)。 |
OPIK_MCP_AS_URL | 未设置 | OAuth 授权服务器 URL,会在 /.well-known/oauth-protected-resource(RFC 9728)中公布,并用作 AS 发现探测的代理目标。MCP 宿主要通过 HTTP 启动 OAuth 流程,就必须设置此项。 |
OPIK_MCP_RESOURCE_URI | 未设置 | 此服务的规范公共 URI,会在受保护资源元数据中作为 resource 公布,并用于生成 WWW-Authenticate 提示。 |
OPIK_MCP_OAUTH_VALIDATION_CACHE_TTL_S | 30 | opik-backend 的令牌内省返回“有效”后,该结果的可信时长;同一 OAuth 令牌的后续请求在此时长结束后会再次发起内省。此设置限制了逐请求验证带来的后端负载,以及过期令牌仍被转发的时间窗口(后端首次返回 401 时,此窗口也会结束)。如果后端报告了令牌自身的 expires_at,则缓存时长不会超过该时间。 |
OPIK_MCP_LOG_LEVEL | INFO | stderr 日志记录器的阈值。 |
选择传输方式
HTTP 传输有两种 Bearer 凭据形式,也对应两种契约。opik_mcp_at_… OAuth
访问令牌会针对 opik-backend 的令牌内省端点逐请求验证(结果会缓存,参见
OPIK_MCP_OAUTH_VALIDATION_CACHE_TTL_S);过期或已撤销的令牌会收到 HTTP 401
响应,其中包含 WWW-Authenticate: Bearer error="invalid_token"。MCP 宿主会据此
启动静默的 refresh_token 授权流程。Opik API 密钥不会在本地验证:它会原样
转发给 opik-backend,后者是唯一的强制执行点。请根据部署方式选择传输方式:
| 场景 | 传输方式 |
|---|---|
| Opik Cloud | 无需运行任何服务:托管服务就是由 Comet 通过 HTTP 运行的此服务 |
| MCP 客户端与 Opik 位于同一台机器上(本地 OSS 安装) | stdio(推荐——最简单,无需端口,也无需设置 OAuth) |
| 本地 MCP 客户端 → 可自托管的 Opik | 使用适用于该部署的环境变量并采用 stdio,或使用 OAuth 并采用 HTTP(OPIK_MCP_AS_URL 指向后端) |
| opik-mcp 部署在与 opik-backend 相同的边缘服务之后 | HTTP——每个请求的 Bearer 凭据都由后端验证 |
本地 OSS 安装须知:OSS 后端不会对请求进行身份验证,因此置于其前方的 HTTP
opik-mcp 与 OSS REST API 本身一样开放。在共享网络中,请保留默认的 127.0.0.1
绑定地址(并优先使用 stdio)。
遥测
| 变量 | 默认值 | 说明 |
|---|---|---|
OPIK_MCP_ANALYTICS_ENABLED | true | 设为 false 可停用所有非 Sentry 遥测。 |
| `OPIK_MCP_SENTRY_ENABLED | true | 设为 false 可停用所有 Sentry 遥测。 |
| ======= |
已知宿主限制
不同宿主允许单次工具调用运行的时长各不相同:
- Claude Code — 未记录工具调用超时时间。推荐使用。
- Cursor — 硬性超时时间为 60s,且不会因进度更新而重置 (上游 bug)。
- MCP Inspector — 总时长受
MAX_TOTAL_TIMEOUT限制(默认 60s)。 对于耗时较长的操作,可在 Inspector UI 中调高该值。
如果调用卡住,请设置 OPIK_MCP_LOG_LEVEL=DEBUG 以记录完整请求日志。
故障排查
配置是否正常? 使用客户端配置中的环境变量运行服务,并加上
--check:OPIK_URL=http://localhost:5173/api uvx opik-mcp@latest --check。它会列出工作区和检测到的项目,或说明需要修复什么。服务本身的错误信息也会指出需要更改的内容,并附上相关文档页面的链接。
未读取到 OPIK_API_KEY — 该变量没有传递给服务进程。在 Claude Code / Cursor / VS Code 中,环境变量只有放在 MCP 服务配置的 env 块中才会生效,而不是放在 shell 中;Codex 也会转发 env_vars 中列出的变量名。编辑配置后,请开启新会话,因为客户端会在会话启动时读取配置。
请求发送到开源版 Opik 的 /opik/api — COMET_URL_OVERRIDE 用于自托管的 Comet 平台。开源版的 API 位于 /api:请改为设置 OPIK_URL=http://localhost:5173/api(或 https://<host>/api)。当主机是本机时,服务会在启动时对此发出警告,而 --check 会返回“No Opik API at …”。
Cursor 调用在 60s 后超时 — 这是 Cursor 的已知问题,与 opik-mcp 无关。可以缩小调用范围(减小 size,缩短时间窗口),或者在没有硬性超时限制的 Claude Code 中执行相同操作。
服务未显示、无法打开登录页面、工作区错误、找不到 uvx。
这些问题已在文档的故障排查部分中说明。
uvx opik@latest mcp status 会列出所有已配置该服务的客户端,并指出其配置是否已偏离。
开发
git clone [email protected]:comet-ml/opik-mcp.git
cd opik-mcp
make install # uv sync --locked --extra dev
make check # lint + typecheck + test
make run-dev # uvicorn with --reload + DEBUG logs
make inspect # MCP Inspector against the running server
常用目标:
| 目标 | 功能 |
|---|---|
make install | uv sync --locked --extra dev |
make run | 运行 MCP 服务(默认使用 stdio)。 |
make run-dev | 以 DEBUG 日志级别运行,并启用 uvicorn --reload。 |
make dev | 通过 mcp dev 运行(Inspector 开发模式封装器)。 |
make inspect | 启动 MCP Inspector 并连接到正在运行的服务。 |
make test | uv run pytest -q。 |
make lint | ruff check + 格式检查。 |
make format | ruff format + ruff check --fix。 |
make typecheck | mypy。 |
make check | lint + typecheck + test。 |
仓库布局:
opik-mcp/
├── src/opik_mcp/ ← server, tools, analytics
├── tests/ ← pytest suites
├── scripts/ ← live-BE smoke + MCP-session smoke
├── legacy/typescript/ ← migration guide for the deprecated v2 TS server (source: tag `legacy-typescript-final`)
├── pyproject.toml
└── Makefile
获取帮助
- 遇到错误或有功能请求,请提交 issue
- SDK / 后端文档请参阅 Opik 文档
- 有问题请前往 Comet 社区 Slack
许可证
Apache-2.0。
评论
一个开放协议,规定了 AI 应用如何以统一方式连接外部工具与数据源。客户端负责与模型对话,MCP 服务负责提供工具、资源和提示模板,两者通过标准消息通信,同一个服务可以被不同客户端复用。