dsh-unity-mcp-bridge 0.6.0 → 0.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -9,7 +9,7 @@ A DeepSeek Harness (DSH) plugin that bridges a Unity MCP server (`com.ivanmurzak
9
9
  - Dormant from boot: no connection, no Unity tools — two hook tools, ~224 tokens.
10
10
  - `/unity-mcp-tools` then `unity_mcp_activate` connects and registers `mcp__unity__*`.
11
11
  - Enabled commands take effect on the **next** step; `unity_tools_restore` disables them and disconnects.
12
- - Ships the command catalog for plugin 1.2.0 (18 commands, RQL-first) and the `/unity-mcp-install` / `/unity-mcp-check` skills.
12
+ - Ships the command catalog for plugin 1.6.0 (19 commands, RQL-first; regenerable from the offline package via `/unity-mcp-update-tools`) and the `/unity-mcp-install` / `/unity-mcp-check` / `/unity-mcp-update` / `/unity-mcp-update-tools` skills.
13
13
  - `resyncAfterTools`: after a management-tool call the bridge re-fetches `tools/list` itself, because DSH's long-lived session never receives `list_changed`.
14
14
 
15
15
  ## Install
@@ -35,7 +35,9 @@ Uninstall: `dsh plugin --profile <profile> remove dsh-unity-mcp-bridge`
35
35
  | Entry | What it does |
36
36
  |---|---|
37
37
  | `/unity-mcp-install` | Installs the Unity-side plugin and the MCP Server into the workspace's Unity project |
38
- | `/unity-mcp-check` | Pins both ends to port 20000, sets the AI agent, initializes the minimal tool set, checks versions |
38
+ | `/unity-mcp-check` | Checks plugin install, port 20000, DSH bundle loading, minimal tool set and catalog version, then runs the connect test |
39
+ | `/unity-mcp-update` | Checks the official CLI, the local `vendor/` offline package and the Unity plugin for updates; upgrades only after you agree |
40
+ | `/unity-mcp-update-tools` | Refreshes the offline package and regenerates the `/unity-mcp-tools` command and extension indexes |
39
41
  | `/unity-mcp-tools` | Opens Unity capability: activate → find the command → enable only what the task needs |
40
42
  | `unity_tools_restore` | Disables everything except the management tool and returns to dormant |
41
43
 
package/README.zh.md CHANGED
@@ -9,7 +9,7 @@ English → [README.md](README.md)
9
9
  - 开机即休眠:不连接、不注册任何 Unity 工具,只有 2 个钩子工具(约 224 tokens)。
10
10
  - `/unity-mcp-tools` → `unity_mcp_activate` 才连接并注册 `mcp__unity__*`。
11
11
  - 开启的命令**下一步**才生效;`unity_tools_restore` 关闭它们并断开,回到休眠。
12
- - 随包发布插件 1.2.0 的命令目录(18 个命令,RQL-first)与 `/unity-mcp-install`、`/unity-mcp-check` 两个技能。
12
+ - 随包发布插件 1.6.0 的命令目录(19 个命令,RQL-first;`/unity-mcp-update-tools` 可按新离线包重生成)与 `/unity-mcp-install`、`/unity-mcp-check`、`/unity-mcp-update`、`/unity-mcp-update-tools` 四个技能。
13
13
  - `resyncAfterTools`:管理工具调用返回后桥接自己重拉 `tools/list`,不依赖 DSH 长会话收不到的 `list_changed` 通知。
14
14
 
15
15
  ## 安装
@@ -35,7 +35,9 @@ dsh plugin --profile <profile> add git+https://github.com/xiake-1/dsh-unity-mcp-
35
35
  | 入口 | 作用 |
36
36
  |---|---|
37
37
  | `/unity-mcp-install` | 给工作区里的 Unity 工程装上 Unity 侧插件与 MCP Server |
38
- | `/unity-mcp-check` | 两端统一到 20000 端口、配好 AI agent、初始化最小工具集、比对版本 |
38
+ | `/unity-mcp-check` | 检查插件安装、端口 20000(不是就改)、DSH bundle 加载、工具集初始化、命令目录版本,再实测连通 |
39
+ | `/unity-mcp-update` | 检查 CLI、本地离线包(`vendor/`)与 Unity 插件的新版本,问过你才更新 |
40
+ | `/unity-mcp-update-tools` | 把离线包刷到最新并重生成 `/unity-mcp-tools` 的命令索引与扩展索引 |
39
41
  | `/unity-mcp-tools` | 打开 Unity 能力:激活 → 找到命令 → 只开本次要用的 |
40
42
  | `unity_tools_restore` | 关闭除管理工具外的全部工具并断开,回到休眠 |
41
43
 
package/docs/DETAILS.md CHANGED
@@ -53,9 +53,11 @@ dsh plugin --profile <profile> add file:<path-to-this-checkout>
53
53
  | `keepEnabledTools` | `[]` | 恢复时额外保留的原始工具名(除 `tool-set-enabled-state` 之外)。 |
54
54
  | `registerCatalogSkill` | `true` | 是否注册随包的命令目录技能。 |
55
55
  | `skillName` | `unity-mcp-tools` | 技能名 / 斜杠命令。 |
56
- | `registerHelperSkills` | `true` | 是否注册两个辅助技能。 |
56
+ | `registerHelperSkills` | `true` | 是否注册四个辅助技能。 |
57
57
  | `installSkillName` | `unity-mcp-install` | 安装 Unity 侧插件的技能名。 |
58
- | `checkSkillName` | `unity-mcp-check` | 检查连通性的技能名。 |
58
+ | `checkSkillName` | `unity-mcp-check` | 检查「插件已装 / 端口 20000 / DSH bundle 加载 / 工具集 / 命令目录 / 能连上 DSH」的技能名。 |
59
+ | `updateSkillName` | `unity-mcp-update` | 检查并(经用户同意后)更新官方 CLI、本地 `vendor/` 离线包与 Unity 插件的技能名。 |
60
+ | `updateToolsSkillName` | `unity-mcp-update-tools` | 刷新本地离线包并重生成命令目录与扩展索引的技能名。 |
59
61
  | `helperSkillsModelInvocable` | `true` | 辅助技能与目录不同,会提供给模型。 |
60
62
  | `helperSkillsUserInvocable` | `true` | 同时也是用户斜杠命令。 |
61
63
 
@@ -70,7 +72,7 @@ boot ──► DORMANT ──(/unity-mcp-tools ─► unity_mcp_activate)──
70
72
  2 hook tools bridged mcp__unity__* tools
71
73
  ```
72
74
 
73
- 每个已开启命令的完整 JSON Schema 都会进入**之后每一次**模型请求;关闭的命令贡献为零。开启是临时、可回收的成本——忘记第 4 步才会变成永久成本。恢复工具的存在就是为了让第 4 步不必枚举所有已注册名字(数量本身随版本变:0.9x 是 73 个,1.2.0 是 18 个)。
75
+ 每个**可见**命令的完整 JSON Schema 都会进入**之后每一次**模型请求;隐藏的命令贡献为零(1.6.0 起叫“可见性”,隐藏的工具仍可按名调用但不再列给模型)。开启是临时、可回收的成本——忘记第 4 步才会变成永久成本。恢复工具的存在就是为了让第 4 步不必枚举所有已注册名字(数量本身随版本变:0.9x 是 73 个,1.2.0 是 18 个,1.6.0 是 19 个;默认可见数都是 7)。
74
76
 
75
77
  ---
76
78
 
@@ -79,9 +81,11 @@ boot ──► DORMANT ──(/unity-mcp-tools ─► unity_mcp_activate)──
79
81
  | 技能 | 内容 |
80
82
  |---|---|
81
83
  | `/unity-mcp-install` | 检查 `unity-mcp-cli` 是否在本机(缺则 `npm install -g unity-mcp-cli`),并核对 **CLI / Unity 插件 / MCP Server 三者 lockstep**(老 CLI 的 AI agent 列表会缺项,例如没有 `kilo-code`)。在工作区内按 `ProjectSettings/ProjectVersion.txt` 定位 Unity 工程;`Packages/manifest.json` 里已有 `com.ivanmurzak.unity.mcp` 就报告,否则 `unity-mcp-cli install-plugin <project> --with-server`(同时把 `GameDev-MCP-Server` 二进制放进 CLI 托管目录 `~/.ai-game-dev/server/<rid>/`),再重读 manifest 验证。GitHub 下载失败时走本机系统代理(Clash):端口从注册表读而不是猜,`NODE_USE_ENV_PROXY=1` 必需(Node 24 的全局 `fetch` 否则忽略 `HTTP_PROXY`),`NO_PROXY` 必须让 OpenUPM/npm 直连。最后手段:带断点续传的代理下载 + 对 release `SHA256SUMS` 校验 + `--server-source` 安装。仓库带 `vendor/` 离线包时优先离线:`tools/offline-package.mjs install` 写 Unity 官方支持的 `file:` 本地 tarball 依赖(自动备份 manifest),Server 来自缓存 zip,全新工程不联网即可装好。 |
82
- | `/unity-mcp-check` | 把两端统一到 **20000**:Unity 侧 `unity-mcp-cli bootstrap-local --url http://localhost:20000/`(改项目自己的 `UserSettings/AI-Game-Developer-Config.json`,先带时间戳备份 + `--dry-run` 比对);DSH 侧 `unity-mcp` 行漂移就纠正回 `http://localhost:20000/mcp`;仍钉旧端口的其他客户端只报告、不静默改。**再把 AI agent 配成 Kilo Code**:`unity-mcp-cli configure <project> --agent kilo-code --url http://localhost:20000` 写 `.kilocode/mcp.json`(`url` 为 `http://localhost:20000/p/<pin>`);`setup-mcp` 的列表没有 `kilo-code`,所以走 `configure --agent`,托管二进制缺失时回退到项目自己的 `Library/mcp-server/<rid>/gamedev-mcp-server.exe`。然后把 Unity 工具集初始化成只留 `tool-set-enabled-state`:两次 `configure` 调用——先 `--disable-all-tools`,再 `--enable-tools tool-set-enabled-state`,**不能合并成一条**(disable-all 优先,会把唯一能撤销它的管理工具也关掉)。最后探测端口与 HTTP 端点,并用 `unity_mcp_activate` 实测。之前还会跑 `tools/offline-package.mjs check`,比对**上游最新 / `vendor/` 缓存 / 项目已装**(外加 CLI)并给出优先走代理的更新路径——只报告,不自行升级。 |
84
+ | `/unity-mcp-check` | 链路体检:**① Unity 工程里是否装了插件**(`Packages/manifest.json` 依赖 + `Library/PackageCache/com.ivanmurzak.unity.mcp@*`);**② 端口是否为 20000**(Unity 侧读项目 `UserSettings/AI-Game-Developer-Config.json` 的 `host`,不是 20000 就 `bootstrap-local --url http://localhost:20000/` 改过来,先备份再改,改完必须让 Unity 重载;DSH 侧只看 profile 有没有把 url 覆盖成别的端口);**③ DSH 依赖与 bundle**(`package.json` 依赖 + `dsh.profile.bundles` + bundle patch 里的 `unity-mcp` 行,确认没有第二份同 `serverName` 的 stock `dsh-mcp-client`);**④ 工具集**(`configure --list` 确认只剩 `tool-set-enabled-state`;初始化必须分两条:先 `--disable-all-tools` 再 `--enable-tools tool-set-enabled-state`,合并会把唯一的开关一起关掉);**⑤ 命令目录版本自检**(`skills/unity-mcp-tools/SKILL.md` 标题行版本 vs 项目 `PackageCache` 里的包版本,不一致就重生成 + 重启 `dsh web`);**⑥ 连通性**(`unity_mcp_activate` 实测,`ECONNREFUSED` = 没人听、404/405 = 端点不对、401/403 = token 不对)。不做版本检查与升级(→ `/unity-mcp-update`),也不配 AI agent。 |
85
+ | `/unity-mcp-update` | 检查并更新三样东西:**官方 CLI**(npm `unity-mcp-cli`)、**本地离线包**(插件自带 `vendor/`:插件 tarball + `GameDev-MCP-Server` zip + `SHA256SUMS` + `manifest.json`)、**Unity 内插件**(`com.ivanmurzak.unity.mcp`,Server 跟随插件钉住的版本)。`tools/offline-package.mjs check --project <proj> --cli-version (unity-mcp-cli --version)` 一次比「上游最新 / `vendor/` / 项目已装 / 本机 CLI」四层,只读不改。**有更新先问用户**(列出目标版本、会动哪些文件、需要重启什么),用户明确同意才更新:CLI `npm install -g unity-mcp-cli` → 离线包 `fetch --plugin-version <latest>`(只动 `vendor/`,可单独执行,不动工程、不用重启)→ 工程 `install --project`(自动备份 manifest)+ Server 按插件钉住的版本 `install-plugin --with-server --server-source <vendor zip>` → 重生成命令目录并重启 `dsh web`。用户不同意就只给报告与可复制命令。 |
86
+ | `/unity-mcp-update-tools` | 只刷新「知识层」:把 `vendor/` 离线包升到上游最新(`offline-package.mjs fetch`,SHA256 校验 + 断点续传,Server 按新插件钉住的版本),再**依据新离线包**重生成 `skills/unity-mcp-tools/SKILL.md`、`reference/*.md` 与 `reference/extensions.md`。生成器直接读 tarball 解出的包目录(`-PackageRoot`,版本取自包内 `package.json`),不需要 Unity 工程。`extensions.md` 列出插件包 `extensions.catalog.json` 里的 10 个可选扩展及各自会带的命令(扩展命令本身仍不进索引,装完用 `unity-tool-list` 取实时清单)。只改 `<bridge>`,不碰工程内插件;最后提示重启 `dsh web`。 |
83
87
 
84
- 两者都遵循官方安装流程 <https://ai-game.dev/engines/unity>。设 `registerHelperSkills: false` 可不发布它们。
88
+ 四者都遵循官方安装流程 <https://ai-game.dev/engines/unity>。设 `registerHelperSkills: false` 可不发布它们。
85
89
 
86
90
  ---
87
91
 
@@ -89,10 +93,12 @@ boot ──► DORMANT ──(/unity-mcp-tools ─► unity_mcp_activate)──
89
93
 
90
94
  上游 `com.ivanmurzak.unity.mcp` 已发 **180 个 release**(`0.8.3` 2025-06-23 → `1.5.0` 2026-10-24)。改动最大的是 **`1.0.0`(2026-10-15):RQL 取代数据类工具**——两条 `feat(rql)!` breaking 把 0.9x 的 73 个细粒度命令缩成 18 个(`rql-query` / `rql-mutate` / `rql-schema`),命令目录必须跨这个版本重生成。其余大改造:`0.81.0`(MCP Server 拆成共享的 `GameDev-MCP-Server`,从此独立编号)、`0.84.0`/`0.85.0`(鉴权重做:`ConnectionConfig.Token` 迁移、`cloudToken` 移除)、`1.1.0`(扩展包独立发布,现为 `2.0.x`)、`1.3.0`(`script-execute` 换 Code-Exec、CLI editor sessions、McpPlugin 8.11.0 工具超时)、`1.5.0`(独立 CLI 与 App skills)。
91
95
 
92
- `vendor/` 缓存可安装产物,让新 Unity 工程不碰 GitHub 也能装(明细见 [vendor/README.md](../vendor/README.md)):插件 tarball `com.ivanmurzak.unity.mcp-1.5.0.tgz`(833,033 B)与 `gamedev-mcp-server-win-x64-9.2.17.zip`(45,558,728 B,对 release `SHA256SUMS` 校验)。**lockstep 是读出来的,不是猜的**:`tools/offline-package.mjs` 从 tarball 里取 `McpServerManager.ServerVersion`(插件 `1.5.0` 钉 Server `9.2.17`),CLI 与插件同号。
96
+ `vendor/` 缓存可安装产物,让新 Unity 工程不碰 GitHub 也能装(明细见 [vendor/README.md](../vendor/README.md)):插件 tarball `com.ivanmurzak.unity.mcp-1.6.0.tgz`(960,306 B)与 `gamedev-mcp-server-win-x64-9.3.0.zip`(44,088,479 B,对 release `SHA256SUMS` 校验)。**lockstep 是读出来的,不是猜的**:`tools/offline-package.mjs` 从 tarball 里取 `McpServerManager.ServerVersion`(插件 `1.6.0` 钉 Server `9.3.0`),CLI 与插件同号。
97
+
98
+ 日常的「有没有新版本 / 要不要升级」走 `/unity-mcp-update`:先只读跑下面的 `check`(四层:上游最新 / `vendor/` / 项目已装 / 本机 CLI),有更新先问用户,同意后才 `fetch` 刷新本地离线包、再 `install` 进工程。
93
99
 
94
100
  ```powershell
95
- # 三层比对:上游最新 / vendor 缓存 / 项目已装
101
+ # 四层比对:上游最新 / vendor 缓存 / 项目已装 / 本机 CLI
96
102
  node "<plugin>\tools\offline-package.mjs" check --project <unity-project> --cli-version (unity-mcp-cli --version)
97
103
 
98
104
  # 刷新:优先代理(GitHub release 资产是最不稳的一条),断点续传 + SHA256 校验
@@ -101,8 +107,8 @@ node "<plugin>\tools\offline-package.mjs" fetch
101
107
 
102
108
  # 装进新的 Unity 工程
103
109
  node "<plugin>\tools\offline-package.mjs" install --project <unity-project>
104
- unity-mcp-cli install-plugin <unity-project> --with-server --server-version 9.2.17 `
105
- --server-source "<plugin>\vendor\gamedev-mcp-server-win-x64-9.2.17.zip"
110
+ unity-mcp-cli install-plugin <unity-project> --with-server --server-version 9.3.0 `
111
+ --server-source "<plugin>\vendor\gamedev-mcp-server-win-x64-9.3.0.zip"
106
112
  ```
107
113
 
108
114
  `install-plugin` **没有** `--plugin-source`;离线路径是 Unity 官方支持的 `file:` 本地 tarball 依赖。CLI 不会覆盖 `file:` / `git+` / `http:` 依赖(`dist/utils/manifest.js` 的 `nonSemverPrefixes`),所以之后重跑 `install-plugin` 也安全。
@@ -111,13 +117,18 @@ unity-mcp-cli install-plugin <unity-project> --with-server --server-version 9.2.
111
117
 
112
118
  ## 重新生成命令目录 / Regenerating the catalog
113
119
 
114
- `tools/generate-unity-mcp-catalog.ps1` 扫描已安装的 `com.ivanmurzak.unity.mcp@*` 包,重写 `skills/SKILL.md` 与 `skills/reference/*.md`(分类取自插件自己的 `[AiTool(Title = ...)]` 属性)。升级 Unity 插件后重跑,再重启 `dsh web`。
120
+ `tools/generate-unity-mcp-catalog.ps1` 扫描插件包源码,重写 `skills/unity-mcp-tools/SKILL.md`、`skills/unity-mcp-tools/reference/<分类>.md` 与 `reference/extensions.md`(分类取自插件自己的 `[AiTool(Title = ...)]` 属性;扩展清单取自包内 `extensions.catalog.json`)。升级插件后重跑,再重启 `dsh web`。
115
121
 
116
122
  ```powershell
123
+ # 从 Unity 工程里已解析的包生成
117
124
  powershell -NoProfile -ExecutionPolicy Bypass -File tools/generate-unity-mcp-catalog.ps1 -ProjectRoot <your-unity-project>
125
+
126
+ # 或直接从 vendor 离线包生成(不需要 Unity 工程;版本取自包内 package.json)
127
+ tar -xzf vendor/com.ivanmurzak.unity.mcp-<ver>.tgz -C <临时目录>
128
+ powershell -NoProfile -ExecutionPolicy Bypass -File tools/generate-unity-mcp-catalog.ps1 -PackageRoot <临时目录>/package
118
129
  ```
119
130
 
120
- 插件 1.2.0 不再把工具描述写成字符串字面量,而是常量引用(如 `[Description(RqlGuide.QueryDescription)]`),`RqlGuide` 还会把字面量与其他常量拼接。生成器会求值这些常量,RQL 语言手册因此能落到 `reference/rql.md`:`-BodyTools`(默认 `rql-*`)决定哪些命令带上插件自己的 `[AiToolBody]`/`[AiSkillBody]` 正文,于是机械类命令保持一行,语言类工具带完整指南。脚本必须存为 **带 BOM 的 UTF-8**——Windows PowerShell 5.1 会把无 BOM 的 UTF-8 当 ANSI,中文会变成解析错误。
131
+ 插件 1.2.0 不再把工具描述写成字符串字面量,而是常量引用(如 `[Description(RqlGuide.QueryDescription)]`),`RqlGuide` 还会把字面量与其他常量拼接。生成器会求值这些常量,RQL 语言手册因此能落到 `reference/rql.md`:`-BodyTools`(默认 `rql-*`)决定哪些命令带上插件自己的 `[AiToolBody]`/`[AiSkillBody]` 正文,于是机械类命令保持一行,语言类工具带完整指南。脚本必须存为 **带 BOM 的 UTF-8**——Windows PowerShell 5.1 会把无 BOM 的 UTF-8 当 ANSI,中文会变成解析错误。扩展是独立 UPM 包,生成器只扫基础包,所以扩展命令不进索引,`extensions.md` 只回答「可选哪些扩展 + 各带哪些命令」。
121
132
 
122
133
  ---
123
134
 
package/lib/index.js CHANGED
@@ -845,12 +845,16 @@ const Config = z.union([z.object({
845
845
  // model never sees or auto-loads it, and Unity capability never turns on by itself.
846
846
  skillModelInvocable: z.boolean().default(false),
847
847
  skillUserInvocable: z.boolean().default(true),
848
- // Shipped helper skills: put the Unity-side plugin in (`/unity-mcp-install`) and prove the
849
- // bridge actually reaches it (`/unity-mcp-check`). Model-visible by default: they are the
850
- // on-ramp and the doctor, not the Unity capability itself.
848
+ // Shipped helper skills: put the Unity-side plugin in (`/unity-mcp-install`), prove the
849
+ // bridge actually reaches it (`/unity-mcp-check`), check/offer updates (`/unity-mcp-update`),
850
+ // and refresh the offline package + this command catalog (`/unity-mcp-update-tools`).
851
+ // Model-visible by default: they are the on-ramp and the doctor, not the Unity capability
852
+ // itself.
851
853
  registerHelperSkills: z.boolean().default(true),
852
854
  installSkillName: z.string().default("unity-mcp-install"),
853
855
  checkSkillName: z.string().default("unity-mcp-check"),
856
+ updateSkillName: z.string().default("unity-mcp-update"),
857
+ updateToolsSkillName: z.string().default("unity-mcp-update-tools"),
854
858
  helperSkillsModelInvocable: z.boolean().default(true),
855
859
  helperSkillsUserInvocable: z.boolean().default(true),
856
860
  reconnect: Reconnect
@@ -876,12 +880,16 @@ const Config = z.union([z.object({
876
880
  // model never sees or auto-loads it, and Unity capability never turns on by itself.
877
881
  skillModelInvocable: z.boolean().default(false),
878
882
  skillUserInvocable: z.boolean().default(true),
879
- // Shipped helper skills: put the Unity-side plugin in (`/unity-mcp-install`) and prove the
880
- // bridge actually reaches it (`/unity-mcp-check`). Model-visible by default: they are the
881
- // on-ramp and the doctor, not the Unity capability itself.
883
+ // Shipped helper skills: put the Unity-side plugin in (`/unity-mcp-install`), prove the
884
+ // bridge actually reaches it (`/unity-mcp-check`), check/offer updates (`/unity-mcp-update`),
885
+ // and refresh the offline package + this command catalog (`/unity-mcp-update-tools`).
886
+ // Model-visible by default: they are the on-ramp and the doctor, not the Unity capability
887
+ // itself.
882
888
  registerHelperSkills: z.boolean().default(true),
883
889
  installSkillName: z.string().default("unity-mcp-install"),
884
890
  checkSkillName: z.string().default("unity-mcp-check"),
891
+ updateSkillName: z.string().default("unity-mcp-update"),
892
+ updateToolsSkillName: z.string().default("unity-mcp-update-tools"),
885
893
  helperSkillsModelInvocable: z.boolean().default(true),
886
894
  helperSkillsUserInvocable: z.boolean().default(true),
887
895
  reconnect: Reconnect
@@ -1021,8 +1029,8 @@ function registerCatalogSkill(ctx, config) {
1021
1029
  let parsed;
1022
1030
  let baseDir;
1023
1031
  try {
1024
- baseDir = fileURLToPath(new URL("../skills/", import.meta.url));
1025
- parsed = parseSkillFile(readFileSync(new URL("../skills/SKILL.md", import.meta.url), "utf8"));
1032
+ baseDir = fileURLToPath(new URL("../skills/unity-mcp-tools/", import.meta.url));
1033
+ parsed = parseSkillFile(readFileSync(new URL("../skills/unity-mcp-tools/SKILL.md", import.meta.url), "utf8"));
1026
1034
  } catch (error) {
1027
1035
  sctx.logger.warn(`unity-mcp-bridge: catalog skill files unreadable: ${String(error)}`);
1028
1036
  return;
@@ -1071,9 +1079,12 @@ function registerCatalogSkill(ctx, config) {
1071
1079
  }
1072
1080
  }
1073
1081
  /**
1074
- * The two shipped operational helper skills. `/unity-mcp-install` gets the Unity-side plugin
1075
- * into the workspace's Unity project; `/unity-mcp-check` proves the bridge actually reaches it
1076
- * and fixes the profile URL when the project listens somewhere other than the default port.
1082
+ * The four shipped operational helper skills. `/unity-mcp-install` gets the Unity-side plugin
1083
+ * into the workspace's Unity project; `/unity-mcp-check` only proves the three things it owns
1084
+ * (plugin installed, port 20000, bridge reaches DSH); `/unity-mcp-update` checks the official CLI
1085
+ * and the Unity plugin for new versions and updates them once the user agrees;
1086
+ * `/unity-mcp-update-tools` refreshes the offline `vendor/` package and regenerates this
1087
+ * command catalog (index + extension list) from it.
1077
1088
  * Same best-effort contract as the catalog skill: no skill registry, no skills, no failure.
1078
1089
  */
1079
1090
  const HELPER_SKILLS = [
@@ -1086,6 +1097,16 @@ const HELPER_SKILLS = [
1086
1097
  label: "check",
1087
1098
  file: "../skills/unity-mcp-check/SKILL.md",
1088
1099
  nameKey: "checkSkillName"
1100
+ },
1101
+ {
1102
+ label: "update",
1103
+ file: "../skills/unity-mcp-update/SKILL.md",
1104
+ nameKey: "updateSkillName"
1105
+ },
1106
+ {
1107
+ label: "update-tools",
1108
+ file: "../skills/unity-mcp-update-tools/SKILL.md",
1109
+ nameKey: "updateToolsSkillName"
1089
1110
  }
1090
1111
  ];
1091
1112
  function registerHelperSkills(ctx, config) {
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "dsh-unity-mcp-bridge",
3
- "version": "0.6.0",
4
- "description": "Opt-in Unity-MCP bridge for DeepSeek Harness: dormant by default, /unity-mcp-tools activates it, ships the 1.2.0 command catalog plus /unity-mcp-install and /unity-mcp-check.",
3
+ "version": "0.8.0",
4
+ "description": "Opt-in Unity-MCP bridge for DeepSeek Harness: dormant by default, /unity-mcp-tools activates it, ships the 1.6.0 command catalog plus /unity-mcp-install, /unity-mcp-check, /unity-mcp-update and /unity-mcp-update-tools.",
5
5
  "type": "module",
6
6
  "main": "lib/index.js",
7
7
  "repository": {
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  name: unity-mcp-check
3
- description: 检查 DSH 的 unity-mcp-bridge 与 Unity 项目的 MCP 插件是否连通:两端端口统一到 20000(项目侧不是 20000 就用 bootstrap-local 改过来)、把 AI agent 配成 Kilo Code(写 .kilocode/mcp.json,端口跟着 20000)、按 reference/tool.md 把 Unity 工具集初始化为只留 tool-set-enabled-state、自检 /unity-mcp-tools 的命令目录是否按当前插件版本生成(命令名随版本变)、用 tools/offline-package.mjs check 比对「上游最新 / vendor 离线包 / 项目已装」三层版本并给出更新路径(下载新版本优先走代理,断点续传 + SHA256 校验),再用 unity_mcp_activate 实测。
4
- whenToUse: 用户要求「检查 / 排查 Unity-MCP 连接」或「AI Game Developer / Unity-MCP 有没有新版本、要不要升级」,或 unity_mcp_activate 连不上、/unity-mcp-tools 激活失败、刚跑完 /unity-mcp-install 时。
3
+ description: 检查 DSH 的 unity-mcp-bridge 与 Unity 项目这条链路是否就绪:Unity 插件是否安装成功、两端端口统一到 20000(项目侧不是 20000 就用 bootstrap-local 改过来)、DSH 侧依赖与 bundle 是否加载插件行、Unity 工具集是否初始化成只留 tool-set-enabled-state、/unity-mcp-tools 的命令目录是否按当前插件版本生成,最后用 unity_mcp_activate 实测能否连上 DSH。不做版本检查与升级(用 /unity-mcp-update),也不配 AI agent。
4
+ whenToUse: 用户要求「检查 / 排查 Unity-MCP 连接」、unity_mcp_activate 连不上、/unity-mcp-tools 激活失败、刚跑完 /unity-mcp-install 时;问「有没有新版本 / 要不要升级」请用 /unity-mcp-update。
5
5
  ---
6
6
 
7
7
  # 检查 DSH ↔ Unity-MCP 连接
@@ -12,32 +12,41 @@ whenToUse: 用户要求「检查 / 排查 Unity-MCP 连接」或「AI Game Devel
12
12
  |---|---|---|
13
13
  | DSH | 桥接插件 `dsh-unity-mcp-bridge` | `%DSH_HOME%\profiles\%DSH_PROFILE%\`:`package.json` 的依赖 **和 `dsh.profile.bundles` 里的包名**(决定 bundle 是否加载);`unity-mcp` 行由插件自带的 `node_modules\dsh-unity-mcp-bridge\cordis.patch.yml` 插入(`url` 默认 `http://localhost:20000/mcp`),profile 自己的 `cordis.patch.yml` 只在需要覆盖端点时出现 |
14
14
  | Unity | 包 `com.ivanmurzak.unity.mcp` 起的 MCP 服务器 | 项目 `UserSettings\AI-Game-Developer-Config.json` 的 `host`(必须是 `http://localhost:20000`) |
15
- | AI agent | 客户端侧的 MCP 配置(本技能默认 **Kilo Code**) | 项目 `.kilocode\mcp.json` 的 `mcpServers.*.url`(端口必须是 20000)+ 同文件所在项目的 `skillsPath`(`.kilocode\skills`) |
16
15
 
17
- > **20000 是唯一标准端口。** 哪一端不是 20000,就把**那一端**改成 20000:Unity 侧用 `unity-mcp-cli bootstrap-local`,DSH 侧的默认 `url` 由插件 bundle patch 提供、本来就是 20000(出现别的端口说明 profile 里有覆盖行,改或删那一行),AI agent 侧重新跑 `configure --agent`(见第 5 步,它会跟着 `--url` 的端口走)。
16
+ 检查项:① 插件是否装上 ② 端口是否 20000(不是就改)③ DSH 依赖与 bundle 是否加载插件行 ④ 工具集是否最小 ⑤ 命令目录是否跟得上插件版本 ⑥ 能否连上 DSH。
18
17
 
19
- ## 1. DSH 侧现状
18
+ 版本新旧、是否升级 → `/unity-mcp-update`;装插件 → `/unity-mcp-install`;配 AI agent 不在本技能范围内。
19
+
20
+ ## 0. 定位 Unity 项目
21
+
22
+ 找 `ProjectSettings\ProjectVersion.txt`(排除 `Library` / `Temp` / `obj` / `node_modules` / `.git`),取唯一那个;0 个或多个就停下来问用户。
20
23
 
21
24
  ```powershell
22
- $prof = $env:DSH_PROFILE_DIR # 例如 C:\Users\<you>\.dsh\profiles\desktop
23
- # 依赖 + bundle 列表:两者都在,bundle 才会被加载
24
- Get-Content (Join-Path $prof 'package.json') -Raw | Select-String 'dsh-unity-mcp-bridge'
25
- # 生效的 unity-mcp 行:默认由插件自带的 bundle patch 插入
26
- Select-String -Path (Join-Path $prof 'node_modules\dsh-unity-mcp-bridge\cordis.patch.yml') `
27
- -Pattern 'id: unity-mcp' -Context 0,12
28
- # profile 层若有覆盖行,以它为准
29
- Select-String -Path (Join-Path $prof 'cordis.patch.yml') -Pattern 'unity-mcp' -Context 0,12
25
+ $ws = (Get-Location).Path
26
+ $projects = Get-ChildItem $ws -Directory -Recurse -Depth 4 -ErrorAction SilentlyContinue |
27
+ Where-Object { Test-Path (Join-Path $_.FullName 'ProjectSettings\ProjectVersion.txt') } |
28
+ Where-Object { $_.FullName -notmatch '\\(Library|Temp|obj|node_modules|\.git)\\' } |
29
+ Select-Object -ExpandProperty FullName -Unique
30
+ $projects
30
31
  ```
31
32
 
32
- 确认四件事:依赖在不在、`dsh.profile.bundles` 里有没有 `dsh-unity-mcp-bridge`、生效的 `url:` 是不是 `http://localhost:20000/mcp`、`serverName`(默认 `unity`)。同时确认**没有**第二份指向同一 `serverName` 的 stock `@deepseek-ai/dsh-mcp-client` 配置。
33
+ ## 1. 插件是否安装成功
33
34
 
34
- > 依赖和 bundles 都在、插件页却显示「已安装,未生效」→ 看 bundle patch 是不是空的。0.4.0 及以前它故意是 `[]`,要求使用者把行手写进 profile 层;桌面端会把 profile 层的 `cordis.patch.yml` 当成自己设置的导出文件重写,手写行下次重启就没了。0.5.0 起这一行随 bundle 提供,不再依赖 profile 层。
35
+ ```powershell
36
+ $manifest = Join-Path $proj 'Packages\manifest.json'
37
+ Select-String -Path $manifest -Pattern 'com\.ivanmurzak\.unity\.mcp'
38
+ Get-ChildItem (Join-Path $proj 'Library\PackageCache') -Directory -Filter 'com.ivanmurzak.unity.mcp@*' -ErrorAction SilentlyContinue
39
+ ```
35
40
 
36
- ## 2. 定位 Unity 项目
41
+ - manifest 依赖 **和** `Library\PackageCache` 里都有 → 已装(依赖可能是 `file:` 本地包,属正常)。
42
+ - 只有 manifest、没有 `PackageCache` → Unity 还没解析包:让 Unity 打开/重新加载项目一次再看。
43
+ - 两处都没有 → **未装**:报告后交给 `/unity-mcp-install`,不要在这里装。
37
44
 
38
- 找 `ProjectSettings\ProjectVersion.txt`(排除 `Library` / `Temp` / `node_modules` / `.git`),取唯一那个;0 个或多个就停下来问用户。
45
+ ## 2. 端口是不是 20000(不是就改)
39
46
 
40
- ## 3. 读两端的端口
47
+ **20000 是唯一标准端口。** 哪一端不是 20000,就把**那一端**改成 20000。
48
+
49
+ ### 2.1 读现状
41
50
 
42
51
  ```powershell
43
52
  # Unity 侧:项目配置里的 host / token(configure --list 也会打印 Host)
@@ -49,16 +58,17 @@ Get-Content (Join-Path $proj 'UserSettings\AI-Game-Developer-Config.json') -Raw
49
58
  Select-String -Path (Join-Path $proj 'Library\mcp-server\win-x64\logs\server-log.txt') `
50
59
  -Pattern 'Start listening on port' | Select-Object -Last 1
51
60
 
52
- # DSH 侧:生效的 url(bundle 默认,profile 层的覆盖行优先)
61
+ # DSH 侧:生效的 url(bundle 默认 20000/mcp;profile 层覆盖行优先)
62
+ $prof = $env:DSH_PROFILE_DIR
53
63
  Select-String -Path (Join-Path $prof 'node_modules\dsh-unity-mcp-bridge\cordis.patch.yml') -Pattern 'url:'
54
- Select-String -Path (Join-Path $prof 'cordis.patch.yml') -Pattern 'url:'
64
+ Select-String -Path (Join-Path $prof 'cordis.patch.yml') -Pattern 'unity-mcp' -Context 0,12
55
65
  ```
56
66
 
57
67
  `unity-mcp-cli status $proj` 会同时列出 **Config Server**(项目配置里的地址,就是 Unity 插件对外服务的地址)和它自己的 **Local MCP Server** 地址 —— **以 Config Server 为准**,不要被另一个端口带跑。
58
68
 
59
- ## 4. 把两端统一到 20000
69
+ ### 2.2 Unity 侧不是 20000 → 改成 20000
60
70
 
61
- **Unity 侧不是 20000 时**(改写项目自己的配置,不是改 DSH):
71
+ 改写项目自己的配置,不是改 DSH。需要 `unity-mcp-cli`;缺了就按 `/unity-mcp-install` 第 2 步装(`npm install -g unity-mcp-cli`)。
62
72
 
63
73
  ```powershell
64
74
  # 先看它会改什么,不落盘
@@ -73,70 +83,59 @@ unity-mcp-cli bootstrap-local $proj --url 'http://localhost:20000/' --token '<
73
83
  - 该命令把配置里的 `host` 改成 `http://localhost:20000`(`connectionMode` 保持 `Custom`,或从 Cloud 切到 Custom),**幂等**,可重复执行。
74
84
  - token 用**项目里已有的那个**,不要凭空生成;`--dry-run` 的 diff 要念给用户看。
75
85
  - **必须让 Unity 重新加载项目**(或重启编辑器),服务器才会在新端口上监听 —— 只改文件不算生效。
76
- - ⚠️ 顺手检查还有谁 pin 了旧端口(项目里的 `.kilocode\mcp.json`、其它 MCP 客户端配置),一并改成 20000,否则那些客户端会连不上。Kilo Code 那份**不要手改**,走第 5 步的 `configure --agent` 重配(它会连 pin 一起重写)。**改动了哪些文件必须报给用户。**
77
- - 如果用户明确要求保留项目原端口(例如别的客户端已经固定用它),**停下来问**,不要强行统一 —— 本技能的默认策略是统一到 20000。
86
+ - 用户明确要求保留项目原端口时**停下来问**,不要强行统一。
78
87
 
79
- **DSH 侧不是 20000 时**:bundle 默认本来就是 20000,所以先找**覆盖行**——profile 层 `cordis.patch.yml` 里的 `unity-mcp` 条目(旧版本插件留下的是一整个 `- insert:` 块)。备份该文件,把它的 `url:` 改成 `http://localhost:20000/mcp`,或者整块删掉、回落到 bundle 默认;profile 有 `patchReload: live` 则存盘即热重载,否则重启 DSH。只改这一处。
88
+ ### 2.3 DSH 侧不是 20000 → 改回 20000
80
89
 
81
- > ⚠️ 桌面端会把 profile 层的 `cordis.patch.yml` 当成自己设置的导出文件重写。把标准配置只写在那里不稳:能删覆盖行就删,靠 bundle 提供。
90
+ bundle 默认就是 `http://localhost:20000/mcp`。出现别的端口说明 profile 层有**覆盖行**:备份 `%DSH_PROFILE_DIR%\cordis.patch.yml`,把它的 `url:` 改成 `http://localhost:20000/mcp`,或整块删掉、回落到 bundle 默认;profile 有 `patchReload: live` 则存盘即热重载,否则重启 DSH。只改这一处。
82
91
 
83
- ## 5. 把 AI agent 配成 Kilo Code(`.kilocode\mcp.json`)
92
+ > ⚠️ 桌面端会把 profile 层的 `cordis.patch.yml` 当成自己设置的导出文件重写。能删覆盖行就删,靠 bundle 提供。
84
93
 
85
- **端口定死 20000 之后**再做这步 —— 写进去的 URL 是从 `--url` 推导的,先配后改端口只会留下连不上的客户端配置。
94
+ ## 3. DSH 侧:依赖与 bundle 自查
86
95
 
87
96
  ```powershell
88
- # 现状:UI 里选中的 agent、skills 目录、是否已有 mcp.json
89
- Get-Content (Join-Path $proj 'UserSettings\AI-Game-Developer-Config.json') -Raw |
90
- Select-String '"skillAutoGenerate"|"skillsPath"|"kilo-code"'
91
- Test-Path (Join-Path $proj '.kilocode\mcp.json')
92
-
93
- # 已存在就先备份,再写
94
- Copy-Item (Join-Path $proj '.kilocode\mcp.json') `
95
- (Join-Path $proj ('.kilocode\mcp.json.bak-' + (Get-Date -Format yyyyMMdd-HHmmss))) -ErrorAction SilentlyContinue
96
- unity-mcp-cli configure $proj --agent kilo-code --url 'http://localhost:20000'
97
- Get-Content (Join-Path $proj '.kilocode\mcp.json') -Raw
97
+ $prof = $env:DSH_PROFILE_DIR # 例如 C:\Users\<you>\.dsh\profiles\desktop
98
+ # 依赖 + bundle 列表:两者都在,bundle 才会被加载
99
+ Get-Content (Join-Path $prof 'package.json') -Raw | Select-String 'dsh-unity-mcp-bridge'
100
+ # 生效的 unity-mcp 行:默认由插件自带的 bundle patch 插入
101
+ Select-String -Path (Join-Path $prof 'node_modules\dsh-unity-mcp-bridge\cordis.patch.yml') `
102
+ -Pattern 'id: unity-mcp' -Context 0,12
103
+ # profile 层若有覆盖行,以它为准
104
+ Select-String -Path (Join-Path $prof 'cordis.patch.yml') -Pattern 'unity-mcp' -Context 0,12
98
105
  ```
99
106
 
100
- - 实测输出 `Configured Kilo Code (kilo-code).` + `config: <proj>\.kilocode\mcp.json`,写出来的是
101
- `{"mcpServers":{"ai-game-developer":{"disabled":false,"type":"streamable-http","url":"http://localhost:20000/p/<pin>"}}}`。
102
- 端口跟着 `--url` 走;路径是**项目 pin**(`/p/<pin>`)而不是 `/mcp`。实测 `http://localhost:20000/mcp` 与 `/p/<pin>` 都返回 200,DSH 侧仍固定用 `/mcp`,两边不冲突。
103
- - ⚠️ **别用 `setup-mcp`**:CLI 0.91.0、1.2.0 与 **1.5.0** 的 `setup-mcp --list` 都只有 14 个 agent(1.5.0 实测:`antigravity`…`vscode-copilot`,**仍不含 `kilo-code`**),直接 `ERROR: Unknown agent: "kilo-code"`。要用 `configure --agent` —— 它代理到托管 Server 的 configurator,那边实测有 16 个 agent(含 `kilo-code`、`zoo-code`、`other-custom`),用 `<server exe> configure --help` 列全。
104
- - `configure --agent` 依赖托管二进制 `~\.ai-game-dev\server\<rid>\`;缺了会报 `No managed GameDev-MCP-Server binary found … Run 'unity-mcp-cli install-plugin --with-server' first`。项目里已有 `Library\mcp-server\<rid>\gamedev-mcp-server.exe` 时可直接顶替(实测与 CLI 代理等价):
107
+ 确认四件事:依赖在不在、`dsh.profile.bundles` 里有没有 `dsh-unity-mcp-bridge`、生效的 `url:` 是不是 `http://localhost:20000/mcp`(读法见 2.1,改法见 2.3)、`serverName`(默认 `unity`)。同时确认**没有**第二份指向同一 `serverName` 的 stock `@deepseek-ai/dsh-mcp-client` 配置。
105
108
 
106
- ```powershell
107
- Push-Location $proj
108
- & (Join-Path $proj 'Library\mcp-server\win-x64\gamedev-mcp-server.exe') configure --agent kilo-code --url http://localhost:20000
109
- Pop-Location
110
- ```
109
+ > 依赖和 bundles 都在、插件页却显示「已安装,未生效」→ 看 bundle patch 是不是空的。0.4.0 及以前它故意是 `[]`,要求使用者把行手写进 profile 层;桌面端会把 profile 层的 `cordis.patch.yml` 当成自己设置的导出文件重写,手写行下次重启就没了。0.5.0 起这一行随 bundle 提供,不再依赖 profile 层。
111
110
 
112
- - **Skills 侧**:`.kilocode\skills\<tool>\SKILL.md` 只由 Unity 窗口的 **Auto-generate** 生成(对应配置里的 `skillAutoGenerate: {"kilo-code": true}` 与 `skillsPath: ".kilocode/skills"`);CLI 的 `setup-skills --list` 同样不含 `kilo-code`,用不了。
113
- - 换别的 agent:`configure --agent <id>` 同理(`cursor` / `claude-code` / `vscode-copilot` …)。改动的文件(`.kilocode\mcp.json` 及其备份)要报给用户。
111
+ ## 4. 初始化工具集(参考 `reference/tool.md`)与命令目录版本自检
114
112
 
115
- ## 6. 初始化工具集(参考 `reference/tool.md`)
113
+ Unity 侧**只留一个**可见工具 `tool-set-enabled-state`(1.6.0 起正式名 `tool-set-visibility`,旧名仍可用):它既是唯一的"开关",也是桥接 `unity_tools_restore` 的保留集,等于最小常驻状态。
116
114
 
117
- Unity 侧**只留一个**工具 `tool-set-enabled-state`:它是唯一的"开关",关掉就再也开不回来;这也正是插件的 `unity_tools_restore` 保留集,等于最小常驻状态。
115
+ > **1.6.0 起是「可见性」而不是禁用**:默认只有 7 个核心工具可见,且管理开关本身默认隐藏。隐藏的工具仍可按名调用,但**不会出现在 `tools/list`**(不进入模型上下文,桥接激活后也注册不到),所以这一步必须把开关显式设为 visible,否则模型拿不到任何开关。
118
116
 
119
117
  ```powershell
120
- unity-mcp-cli configure $proj --list | Select-String '\[enabled\]' # 先看当前状态
118
+ # 1.6.0 的 --list 打印 [visible]/[hidden],旧版 CLI 打印 [enabled]/[disabled]
119
+ unity-mcp-cli configure $proj --list | Select-String '\[(visible|enabled)\]' # 先看当前状态
121
120
 
122
121
  # 必须分成两条执行 —— 见下面的顺序陷阱
123
122
  unity-mcp-cli configure $proj --disable-all-tools
124
123
  unity-mcp-cli configure $proj --enable-tools tool-set-enabled-state
125
124
 
126
- unity-mcp-cli configure $proj --list | Select-String '\[enabled\]' # 复验:恰好 1 条
125
+ unity-mcp-cli configure $proj --list | Select-String '\[(visible|enabled)\]' # 复验:恰好 1 条
127
126
  ```
128
127
 
129
- - ⚠️ **顺序陷阱(实测)**:`--disable-all-tools` 与 `--enable-tools` **不能写在同一条命令里** —— disable-all 会覆盖 enable,结果连唯一的开关 `tool-set-enabled-state` 都被关掉(0 个启用),那就再也没有工具能把它开回来。必须分两条:先 disable-all,再 enable-tools。
130
- - 万一已经被全部关掉:单独跑一条 `unity-mcp-cli configure $proj --enable-tools tool-set-enabled-state` 即可救回,不用重装插件。
131
- - 复验结果应当**只有** `tool-set-enabled-state` 是 `[enabled]`,其余全是 `[disabled]`(注册总数随插件版本变:1.2.0 实测 **1 enabled / 17 disabled**,总数 18;0.9x 是 73。看到 18 不是「工具变少了」,是版本差异,见下面第 7 条)。
128
+ - ⚠️ **顺序陷阱(实测)**:`--disable-all-tools` 与 `--enable-tools` **不能写在同一条命令里** —— disable-all 会覆盖 enable,结果连唯一的开关 `tool-set-enabled-state` 都被隐藏(0 个可见),模型就再也看不到开关了。必须分两条:先 disable-all,再 enable-tools。
129
+ - 万一已经被全部隐藏:单独跑一条 `unity-mcp-cli configure $proj --enable-tools tool-set-enabled-state` 即可救回,不用重装插件。
130
+ - 复验结果应当**只有** `tool-set-enabled-state` 是 `[visible]`(旧版 CLI 显示 `[enabled]`),其余全是 `[hidden]` / `[disabled]`。注册总数随插件版本变:**1.6.0 = 19 个(默认 7 可见)**,1.2.0 = 18 个(默认 7),0.9x = 73。看到 19 不是「工具变多了」。
132
131
  - 这一步直接读写项目配置,**不需要 Unity 在运行**。
133
- - prompts / resources 默认全关,保持关闭即可;除非用户明确要求,不要打开。
134
- - 需要别的命令时,交给 `/unity-mcp-tools` 的按需流程(开启 → 用 → `unity_tools_restore` 收回),不要在这里预先全开:每个已启用命令的 schema 都会进入之后每一次模型请求。
132
+ - prompts / resources 默认全隐藏,保持关闭即可;除非用户明确要求,不要打开。
133
+ - 需要别的命令时,交给 `/unity-mcp-tools` 的按需流程(显示 → 用 → `unity_tools_restore` 收回),不要在这里预先全开:每个可见命令的 schema 都会进入之后每一次模型请求。
135
134
  - **命令目录版本自检(必做)**:`/unity-mcp-tools` 的索引和 `reference/*.md` 是按某个插件版本从源码生成的,**命令名随版本变**。比对两边,不一致就提示重生成,不要照着旧目录去开工具:
136
135
 
137
136
  ```powershell
138
137
  # 桥接自带的目录是按哪个版本生成的(SKILL.md 标题行)
139
- Select-String -Path (Join-Path $prof 'node_modules\dsh-unity-mcp-bridge\skills\SKILL.md') `
138
+ Select-String -Path (Join-Path $prof 'node_modules\dsh-unity-mcp-bridge\skills\unity-mcp-tools\SKILL.md') `
140
139
  -Pattern 'com\.ivanmurzak\.unity\.mcp@'
141
140
  # 项目里实际装的版本
142
141
  (Get-ChildItem (Join-Path $proj 'Library\PackageCache') -Directory -Filter 'com.ivanmurzak.unity.mcp@*').Name
@@ -146,41 +145,7 @@ unity-mcp-cli configure $proj --list | Select-String '\[enabled\]' # 复验:
146
145
 
147
146
  实测代价:目录停在 0.91.0 而项目已是 1.2.0 时,18 个分类文件里有 13 个写的是**已删除**的命令(`gameobject-*`、`assets-*`、`scene-*`、`profiler-*`、`console-*`、`editor-application-*`、`editor-selection-*`、`object-*`、`reflection-method-*`、`type-get-json-schema`),1.2.0 由 `rql-query` / `rql-mutate` / `rql-schema` 承担 —— 照旧目录调用必然 `tool not found`。
148
147
 
149
- ## 7. 版本与更新检查(必做;默认只报告,不擅自升级)
150
-
151
- 一次比三层:**上游最新 / 插件自带 `vendor/` 离线包 / 项目已装**,外加 `unity-mcp-cli`。
152
-
153
- ```powershell
154
- # <bridge> = 插件目录(已安装副本:%DSH_PROFILE_DIR%\node_modules\dsh-unity-mcp-bridge)
155
- # 代理优先:GitHub 的 release 资产直连常被掐断(实测 ECONNRESET on release-assets.githubusercontent.com)
156
- $px = (Get-ItemProperty 'HKCU:\Software\Microsoft\Windows\CurrentVersion\Internet Settings' |
157
- Where-Object ProxyEnable -eq 1).ProxyServer # 实测 127.0.0.1:7897,别猜端口
158
- if ($px) { $env:HTTPS_PROXY = "http://$px"; $env:NODE_USE_ENV_PROXY = '1' }
159
- node "<bridge>\tools\offline-package.mjs" check --project $proj --cli-version (unity-mcp-cli --version)
160
- ```
161
-
162
- - 脚本无第三方依赖(Node 24)。`--json` 给出机器可读结果;`--no-proxy` 强制直连。
163
- - **`NODE_USE_ENV_PROXY=1` 不能省**:Node 24 的全局 `fetch` 否则无视 `HTTPS_PROXY`(实测设了等于没设)。脚本自己会补,外层也设上更稳;也可以直接 `--proxy http://127.0.0.1:<port>`。
164
- - 网络策略是「代理 ↔ 直连互为兜底」:查询类(OpenUPM / npm / GitHub API)先直连,**下载类(Server zip、`SHA256SUMS`)先代理**,失败再直连。
165
- - **lockstep 判据不是「谁新用谁」**:插件 tarball 里 `Editor/Scripts/McpServerManager.cs` 的 `ServerVersion` 常量才是目标 —— 插件 `1.5.0` 钉 Server **`9.2.17`**;CLI 与插件同号(`1.5.0`)。脚本直接从 tarball 读这个常量,写进 `vendor/manifest.json` 的 `plugin.pinnedServerVersion`。
166
- - 项目侧读两处:`Packages\manifest.json` 的依赖(可能是 `file:…` 本地包依赖)与 `Library\PackageCache\com.ivanmurzak.unity.mcp@*`。
167
-
168
- ### 7.1 要更新时:优先用代理把新版本拉到 `vendor/`,再安装
169
-
170
- ```powershell
171
- node "<bridge>\tools\offline-package.mjs" fetch --plugin-version <latest> # 不给版本就取上游最新
172
- node "<bridge>\tools\offline-package.mjs" install --project $proj --dry-run # 先看会改什么
173
- node "<bridge>\tools\offline-package.mjs" install --project $proj
174
- unity-mcp-cli install-plugin $proj --with-server --server-version <pinned> `
175
- --server-source "<bridge>\vendor\gamedev-mcp-server-<rid>-<ver>.zip"
176
- ```
177
-
178
- - 下载有 4 次退避重试,失败保留 `.part`,重跑从断点续传(实测 GitHub 资产这一步会 `ECONNRESET`,第一次失败、第二次即通)。
179
- - zip 的 SHA256 对着**同一 release** 的 `SHA256SUMS` 校验,不匹配直接失败退出,不会留下「装上了但内容不对」的包。
180
- - 装完照第 6 步末尾**重生成命令目录**并重启 `dsh web`(命令名随插件版本变)。
181
- - 用户没点头就不升级:本技能的默认动作是**报告 + 给出可复制的命令**,升级动作交给 `/unity-mcp-install` 5.2。
182
-
183
- ## 8. 探测与实测
148
+ ## 5. 是否连接到 DSH(实测)
184
149
 
185
150
  ```powershell
186
151
  Test-NetConnection -ComputerName localhost -Port 20000 -InformationLevel Quiet
@@ -189,26 +154,22 @@ unity-mcp-cli status $proj # 需要时用 --url / --token / --ti
189
154
  unity-mcp-cli wait-for-ready $proj # 最长 120s
190
155
  ```
191
156
 
192
- DSH 侧只有一条真正的实测:**调用 `unity_mcp_activate`**。
157
+ 真正的实测只有一条:**调用 `unity_mcp_activate`**。
193
158
 
194
159
  - 成功 → 桥接连上并注册 `mcp__unity__*` 工具,检查完成;若本次任务不需要 Unity,立刻 `unity_tools_restore` 回到休眠(它同时把工具集还原成只留 `tool-set-enabled-state`)。
195
- - 失败 → 保留错误原文(`ECONNREFUSED` = 20000 没人听;404/405 = 端点路径不对;401/403 = token 不对),再回到第 4 步核对两端端口。
160
+ - 失败 → 保留错误原文,按下面判断,再回第 2 步核对端口:`ECONNREFUSED` = 20000 没人听;404/405 = 端点路径不对;401/403 = token 不对。
161
+ - 工具 `unity_mcp_activate` 本身不存在 → 桥接插件没加载,属于 DSH 侧安装问题(用 `dsh plugin` 检查是否安装、重启应用)。
196
162
 
197
- ## 9. 报告格式
163
+ ## 6. 报告格式
198
164
 
199
165
  | 检查项 | 结果 |
200
166
  |---|---|
201
- | `unity-mcp-cli` | 已装 v1.5.0(与插件 lockstep)/ 未装 / 已升级 1.2.0 → 1.5.0 |
202
- | Unity 包 `com.ivanmurzak.unity.mcp` | 已装 1.2.0 / 未装 |
203
- | 版本检查(第 7 步) | 上游 plugin 1.5.0 / server 9.2.17 / cli 1.5.0 | vendor 1.5.0 + 9.2.17(钉住 9.2.17)| 项目 1.5.0 → 一致 / 落后(已给 `fetch`+`install` 命令,未擅自升级) |
204
- | 命令目录(`/unity-mcp-tools`) | 按 1.2.0 生成,与项目一致 / 按 0.91.0 生成 → 已重生成(需重启 `dsh web`) |
205
- | MCP Server | 项目 `Library\mcp-server\win-x64\` 9.2.11 + CLI 托管目录 `~\.ai-game-dev\server\win-x64\`(含 `version` 标记)/ 缺 |
206
- | Unity 编辑器 | 运行中 / 未运行 |
207
- | Unity 侧端口 | 原 24009 → 已统一 20000(附备份路径)/ 本来就是 20000 |
208
- | DSH 侧 url | `http://localhost:20000/mcp`(一致 / 已改) |
209
- | 插件加载 | bundle 已插入 `unity-mcp` 行(0.5.0)/ bundle 为空 → 已升级或补了覆盖行 |
210
- | AI agent | Kilo Code:`.kilocode\mcp.json` → `http://localhost:20000/p/<pin>`;`skillsPath=.kilocode\skills` |
211
- | 工具集 | 只有 `tool-set-enabled-state` 为 `[enabled]` |
167
+ | Unity 插件 `com.ivanmurzak.unity.mcp` | 已装(manifest 依赖 = …,PackageCache = …)/ 未装 → 交由 `/unity-mcp-install` |
168
+ | Unity 侧端口 | 本来就是 20000 / 原 24009 → 已改 20000(附备份路径,需重载 Unity)/ 未改(用户要求保留) |
169
+ | DSH 侧 url | `http://localhost:20000/mcp`(一致 / 已改 / 无覆盖行) |
170
+ | 插件加载 | bundle 已插入 `unity-mcp` 行(0.5.0)/ bundle 为空 → 已补覆盖行 / `dsh.profile.bundles` 缺该包 |
171
+ | 命令目录(`/unity-mcp-tools`) | 按 1.6.0 生成,与项目一致 / 按 0.91.0 生成 → 已重生成(需重启 `dsh web`) |
172
+ | 工具集 | 只有 `tool-set-enabled-state` 为 `[visible]`(旧版 CLI 的 `[enabled]`) |
212
173
  | `unity_mcp_activate` | 成功 / 失败(原文错误) |
213
174
  | 改动的文件 | 列出(含备份路径);无则写"无" |
214
175
 
@@ -218,20 +179,11 @@ DSH 侧只有一条真正的实测:**调用 `unity_mcp_activate`**。
218
179
  |---|---|---|
219
180
  | 20000 没人听 | Unity 没开、改了配置但没重载、或服务器没启动 | 重载项目 / 在 Window → AI Game Developer 里启动服务器 |
220
181
  | 改了 host 但端口没变 | Unity 没重新加载项目 | 重启编辑器;`status` 再看 Config Server |
221
- | 别的客户端连不上 | 它们仍 pin 在旧端口(如 24009) | 一并改成 20000,或与用户确认是否回退 |
222
182
  | manifest 里有包但连不上 | Unity 还没解析包 | 用 Unity 打开项目一次 |
223
183
  | 404 / 405 | 端点路径不对(`/mcp` ↔ `/p/<token>`) | 以 `http://localhost:20000/mcp` 为准;需要 token 路径时再补 |
224
184
  | 401 / 403 | token 缺失或过期 | 用项目配置里的 token;或 `bootstrap-local --url ... --token ...` 重新固定 |
225
- | 工具全被关掉(含 `tool-set-enabled-state`) | 把 `--disable-all-tools` 与 `--enable-tools` 写进了同一条命令(上面那个顺序陷阱) | 单独跑一条 `unity-mcp-cli configure $proj --enable-tools tool-set-enabled-state` 救回 |
185
+ | 工具全被隐藏(含 `tool-set-enabled-state`) | 把 `--disable-all-tools` 与 `--enable-tools` 写进了同一条命令(上面的顺序陷阱) | 单独跑一条 `unity-mcp-cli configure $proj --enable-tools tool-set-enabled-state` 救回 |
186
+ | `mcp__unity__gameobject-find` 之类报 `tool not found` | 命令目录是按旧插件版本生成的(1.2.0 已移除 `gameobject-*` / `assets-*` / `scene-*` / `profiler-*` 等) | 按第 4 步做目录版本自检并重生成 + 重启 `dsh web`;读写 Unity 内容改走 `rql-query` / `rql-mutate` / `rql-schema` |
226
187
  | 工具名冲突 / 行为异常 | stock `dsh-mcp-client` 与桥接插件同时跑同一 `serverName` | 只留一个 |
227
- | `ERROR: Unknown agent: "kilo-code"` | 用了 `setup-mcp`(CLI 0.91.0 / 1.2.0 / 1.5.0 的列表只有 14 个 agent,不含 `kilo-code`) | 改用 `unity-mcp-cli configure $proj --agent kilo-code --url http://localhost:20000`(托管 Server 侧有 16 个) |
228
- | `No managed GameDev-MCP-Server binary found …` | 没装托管 Server(缺 `--with-server`) | 跑 `/unity-mcp-install` 的 `install-plugin --with-server`;或临时用项目 `Library\mcp-server\<rid>\gamedev-mcp-server.exe` 直接跑 `configure --agent` |
229
- | 凭空多出个监听 8080 的 `gamedev-mcp-server` | 对 server exe 跑了裸 `--help`(它不是帮助,是直接启动) | 按端口找 PID 杀掉(`Get-NetTCPConnection -LocalPort 8080`);只用 `configure --help` 这类子命令帮助 |
230
- | DSH 通、Kilo Code 连不上 | `.kilocode\mcp.json` 里 pin 的端口不是 20000(端口改过后没重配 agent) | 重跑 `configure --agent kilo-code --url http://localhost:20000`,再核对 `url` 里的端口 |
231
- | `mcp__unity__gameobject-find` 之类报 `tool not found` | 命令目录是按旧插件版本生成的(1.2.0 已移除 `gameobject-*` / `assets-*` / `scene-*` / `profiler-*` 等) | 按第 6 步做目录版本自检并重生成 + 重启 `dsh web`;读写 Unity 内容改走 `rql-query` / `rql-mutate` / `rql-schema` |
232
188
  | 插件页显示「已安装,未生效」 | bundle 没有插入插件行(0.4.0 及以前 bundle patch 是 `[]`),或 profile 的 `dsh.profile.bundles` 里没有这个包 | 升级到 ≥0.5.0(行随 bundle 提供);确认 `dsh.profile.bundles` 含 `dsh-unity-mcp-bridge`;重启 |
233
189
  | 重启后手写进 profile 层的配置不见了 | 桌面端把 profile 的 `cordis.patch.yml` 当自己的设置导出重写,不在它设置模型里的条目会被抹掉 | 插件行交给 bundle,别手写;其它设置走 UI |
234
- | 桌面端启动即崩,日志是 `webserver: host "0.0.0.0" is an unspecified (wildcard) address` | 从旧备份恢复的 `webserver` 块用了 `0.0.0.0`,当前版本拒绝通配监听 | 删掉该块或改成具体网卡 IPv4;局域网访问走 UI 的 remote-web-ui 开关,别手填 `0.0.0.0` |
235
- | `check` 某层显示 `?` 或报「…失败」 | 代理与直连都失败(GitHub API 被掐 / npm 超时) | 设 `HTTPS_PROXY` + `NODE_USE_ENV_PROXY=1`(或直接 `--proxy http://127.0.0.1:<port>`)重跑;插件版本可 `--plugin-version` 手工指定 |
236
- | `fetch` 报 `SHA256 不匹配` | 下载被中间盒改写,或复用了半截文件 | 删掉该 zip 与 `*.part`,重跑 `fetch --force`;仍不匹配就换代理节点 |
237
- | `fetch` 报 `下载不完整 …(保留 .part,可重跑续传)` | 连接被掐断(实测 GitHub release 资产会) | 直接重跑 `fetch`,从 `.part` 续传,别手删 |