跳到主要内容

AI / Skill / MCP 排障

按现象排查 AI 功能:助手不回答或半路中断、Skill 没被用上或装不上、MCP 客户端连不上——每条都能从产品日志核对。

先看现象,再给做法。这页上的每一条都能从产品自己的日志和报错里核对—— 不用去猜模型当时在想什么。

哪一半坏了​

会坏的是两件互不相干的事,坏法也不一样:

  • 模型那一半——助手、/a2a、各处的 AI 按钮。需要 LLM 配置。 现象是报错卡片、回答慢或者回答空;
  • 数据那一半——/mcp,以及每个回答背后的那些工具。完全不需要模型。 现象是 HTTP 状态码。

一个快速的分界动作:问助手一句*「你能做什么?」*。答得上来,说明模型那一半没问题, 毛病在工具;弹报错卡片,就从模型这边查起。

助手不回答​

你看到的原因
卡片:当前环境没有大模型配置没有任何一条配置同时是「启用」且「默认」。两个开关,同一行
回答吐到一半停了,说请求失败一般是模型自己超时。把那条配置高级设置里的**超时时间(秒)**调大
等很久什么都没有夜莺所在机器根本够不着那个地址——见下一段

单独验证模型这条链路:编辑那条配置,点测试连接,它会拿表单里的值真发一次请求。 失败弹窗会说清是哪一类:

类型该改什么
鉴权Key 不对,或者首尾带了空格。Anthropic 的 Key 以 sk-ant- 开头,OpenAI 以 sk- 开头
端点不存在地址。填到版本根这一级——https://api.openai.com/v1——不是对话路径,也不是光一个域名
被限流提供商那边的额度。去他们控制台看用量
回复里没有内容通常是纯思考模型,预算全花在思考上了。把最大 Tokens 调大,或者换一个非思考模型
看着像网络问题的夜莺所在机器到不了那个地址。在那台机器上验一下,需要就填代理地址

逐字段的说明在配置大模型提供方。

回答不对、很空,或者半路停了​

「达到最大迭代次数」。 工具调用链撞到预算了,默认 25 次。 要么把问题问窄一点,要么在覆盖这类问题的那个 Skill 的 frontmatter 里调大 max_iterations。

你看得到的数据它看不到。 它跑在提问账号的权限上,所以这是权限问题不是 AI 问题: 去查那个账号的角色,以及它所在团队有哪些业务组。模型见 权限继承与 RBAC。

它编字段名、编指标名。 把对象和时间窗点名,并且让它去查而不是去回忆: 「读一下 42 号规则的定义再告诉我」。文档检索工具存在的意义就是让版本相关的名字 从文档里来——出网到 flashcat.cloud 被挡掉时,这个工具会降级,这个毛病会更明显。

对话一长回答就被截断。 把 LLM 配置里的上下文长度填成模型真实的窗口大小; 一次带多少历史是按它算的,留空就按一个保守的固定预算走。

Skill 没被用上​

启用一个 Skill 不等于它会被加载。命中判断看的是描述,所以:

  1. 先看开关——关掉的 Skill 挂着 OFF 标签,永远不被考虑;
  2. 看可见范围。标成仅管理团队可见的 Skill,对团队之外的人是不存在的, 模型也不知道它存在;
  3. 用用户会打出来的话重写描述,把他们会粘贴进来的告警名和报错串都放进去。 绝大多数情况下就是这条;
  4. 找一找近似重复。几个描述差不多的 Skill 会同时命中、同时吃上下文,合并掉。

写法和例子在安装、管理与编写 Skills。

Skill 装不上​

报错怎么办
SKILL.md not found in archive root你把上一级目录打包进去了。多包一层会自动拆,多包两层不会
frontmatter 里 name 不能为空文件要以 --- 开头、YAML 要能解析、name 要有值。三条都要满足
archive size exceeds 10MB limit上传上限。删点附带文件,或者改用 Git 安装
git_url must be an http or https URL不支持 ssh 地址,用 https 的 clone 地址
git_token is required when git_auth_type=token要么填 token,要么把认证方式换回不认证
私有仓库装不上Token 是用 [HTTP.RSA] 的密钥加密存的,那对密钥要先配好。需要用户名的凭据写成 用户名:令牌
拨启用开关时提示要先设管理团队先打开修改,把管理团队设上
删除按钮是灰的先把 Skill 停用。内置 Skill 永远删不掉

Skill 脚本跑不起来​

脚本执行有两道互不相干的门,报错会告诉你撞的是哪一道。

「没有可运行的脚本」。 运行器按 main.py、main.sh、顶层唯一的 .py 或 .sh 这个顺序找。多于一个就得你自己指定。

执行被拒绝。 你设了 RequireIsolation = true,而这台机器搭不出真沙箱。 这是配置在按预期工作。要么在 Linux 上提供一份 python-base 根文件系统, 要么接受这台机器不跑 Skill 脚本。

跑起来了,但启动日志里有 SKILL EXECUTION RUNNING WITHOUT ISOLATION (unsafe-exec)。 脚本是直接在夜莺所在主机上跑的,而且没有网络。就这么放着之前, 先读一遍安装、管理与编写 Skills里的安全那一节。

每次执行都会打 sandbox audit: exec_id=... engine=... network=... exit_code=..., 非零退出码就在这行里。

MCP 客户端连不上​

现象原因和做法
401,响应体是纯文本 unauthorizedToken 不对或者已被删。如果所有 Token 都不行,那是 [HTTP.TokenAuth] 关着——启动日志里有 [A2A] HTTP.TokenAuth.Enable=false
405,带 Allow: POST客户端发的是 GET /mcp。无状态模式没有独立 SSE 流,客户端要按 Streamable HTTP 配,不是旧的 SSE 传输
415 或 400缺请求头。Content-Type: application/json 和 Accept: application/json, text/event-stream 两个都要
403 且提到 host反向代理没设 proxy_set_header Host,触发了 SDK 自带的 DNS rebinding 防护
代理返回 404,或者本该是 JSON 的地方回了一段 HTML请求根本没到 n9e。/mcp 在根路径,不在 /api/n9e 下面,只转发 /api/n9e/* 的代理不会把它放过去——加一段 location /mcp
连上大约 60 秒后断开nginx 的默认值。加 proxy_buffering off,并把 proxy_read_timeout、proxy_send_timeout 放到一小时

一份满足上面所有条件的代理配置在启用 MCP 端点。 想把客户端从嫌疑里排除掉,就用那页的 curl 复现一遍。

连上了,但工具不对​

现象原因
一个工具都没有MCPToolsets 里的名字全被丢掉了。启动日志里每个坏名字对应一条 [MCP] ignoring unknown toolset——一份全是错别字的白名单换来的是零个工具,它不会回退成「全放开」
工具比预期少MCPToolsets 收得比你以为的窄,或者写工具没开。只读是 42 个,全开是 74 个
明明开了写工具却没有MCPEnableWriteTools = true 要重启才生效。之后 tools/list 应该返回 74 个
工具在,但每次调用都被拒Token 主人没有对应权限点,或者他所在团队够不着被点名的那个业务组。让它调一次 list_busi_groups,和那个账号在界面上看到的对比
出现了你不想要的工具收窄 MCPToolsets。没有按单个工具开关的机制

A2A 调用卡住或者没返回​

/a2a 驱动的就是内置助手,所以它需要一份能用的 LLM 配置—— 前两节的内容在这里要先适用一遍。

现象原因
请求挂了几十秒正常。模型在思考、在调工具;服务端每 30 秒发一次状态心跳,防止网关掐连接
网关还是把它掐了把 proxy_read_timeout 调大、proxy_buffering 关掉——网关自己的超时是 60 秒的话,心跳救不了
明明跑完了,tasks/get 却说任务不存在任务状态在 Redis 里,TTL 24 小时。对话本身还在数据库里
Agent Card 公布的是个内网地址BaseURL 留空了,是从请求头猜出来的。显式写上

更多在 A2A 端点。

下一步​