dsh-auto-model-routing 0.0.0-stage → 0.3.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.
Files changed (62) hide show
  1. package/CHANGELOG.md +8 -0
  2. package/LICENSE +21 -0
  3. package/README.md +67 -2
  4. package/README.zh.md +68 -0
  5. package/cordis.patch.yml +9 -0
  6. package/docs/SCREENSHOTS.md +6 -0
  7. package/docs/architecture.dual.svg +853 -0
  8. package/docs/architecture.json +486 -0
  9. package/docs/auto-routing.gif +0 -0
  10. package/docs/settings.gif +0 -0
  11. package/lib/client/control.d.ts +34 -0
  12. package/lib/client/control.js +28 -0
  13. package/lib/client/index.d.ts +34 -0
  14. package/lib/client/index.js +150 -0
  15. package/lib/client/label.d.ts +45 -0
  16. package/lib/client/label.js +46 -0
  17. package/lib/client/nav-icon.d.ts +2 -0
  18. package/lib/client/nav-icon.js +23 -0
  19. package/lib/client/route-picker.d.ts +21 -0
  20. package/lib/client/route-picker.js +75 -0
  21. package/lib/client/settings-section.d.ts +24 -0
  22. package/lib/client/settings-section.js +149 -0
  23. package/lib/client/settings-ui.d.ts +3 -0
  24. package/lib/client/settings-ui.js +1 -0
  25. package/lib/client.js +1016 -0
  26. package/lib/context.d.ts +25 -0
  27. package/lib/context.js +34 -0
  28. package/lib/effort.d.ts +11 -0
  29. package/lib/effort.js +31 -0
  30. package/lib/endpoints.d.ts +11 -0
  31. package/lib/endpoints.js +41 -0
  32. package/lib/hints.d.ts +3 -0
  33. package/lib/hints.js +12 -0
  34. package/lib/index.d.ts +10 -0
  35. package/lib/index.js +149 -0
  36. package/lib/input.d.ts +13 -0
  37. package/lib/input.js +8 -0
  38. package/lib/jev.d.ts +49 -0
  39. package/lib/jev.js +138 -0
  40. package/lib/judgements.d.ts +41 -0
  41. package/lib/judgements.js +55 -0
  42. package/lib/router.d.ts +68 -0
  43. package/lib/router.js +153 -0
  44. package/lib/rubric.json +12 -0
  45. package/lib/selection-projection.d.ts +8 -0
  46. package/lib/selection-projection.js +7 -0
  47. package/lib/settings-contract.d.ts +55 -0
  48. package/lib/settings-contract.js +3 -0
  49. package/lib/settings-host.d.ts +35 -0
  50. package/lib/settings-host.js +97 -0
  51. package/lib/settings-validation.d.ts +10 -0
  52. package/lib/settings-validation.js +56 -0
  53. package/lib/settings.d.ts +18 -0
  54. package/lib/settings.js +264 -0
  55. package/lib/state.d.ts +39 -0
  56. package/lib/state.js +69 -0
  57. package/lib/subagent-tool.d.ts +26 -0
  58. package/lib/subagent-tool.js +94 -0
  59. package/package.json +111 -4
  60. package/screenshots.json +4 -0
  61. package/scripts/label-report.mjs +50 -0
  62. package/skills/subagent-model-routing/SKILL.md +30 -0
package/CHANGELOG.md ADDED
@@ -0,0 +1,8 @@
1
+ # Changelog
2
+
3
+ ## 0.3.0
4
+
5
+ - Publish as a standalone DSH bundle with the companion `subagent-model-routing` skill included.
6
+ - Replace the separate ohmydsh skill customization with a package-owned filesystem skill provider. Skill and tools now enable/disable together.
7
+ - Add npm/Git installation instructions, demo GIFs, licensing and OIDC release automation.
8
+ - Keep the existing tier rubric, effort mappings, default MANUAL mode, credentials and stored state unchanged.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 prgrmrwy
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1,3 +1,68 @@
1
- # Temporary Holding Version
1
+ # dsh-auto-model-routing
2
2
 
3
- This version is a temporary placeholder for this package. An operational version to replace this has been submitted for review and is awaiting a staged release.
3
+ English · [简体中文](README.zh.md)
4
+
5
+ ![AUTO in action: a refactor-and-debug turn is judged complex and runs at high, a follow-up rename is judged simple and drops to low; hovering the AUTO chip shows the decision, clicking it switches to MANUAL](docs/auto-routing.gif)
6
+
7
+ <!-- problem -->
8
+ You should not have to raise or lower reasoning effort by hand for every message. In AUTO, each user turn is judged by the Jev decision model (via OpenRouter) as `simple` / `standard` / `complex` / `escalated`, and the plugin changes **only the reasoning effort** of the model you already picked. Provider and model are never changed. If Jev fails for any reason, AUTO switches itself off and the chip shows why.
9
+
10
+ **Install.** DSH `0.2.0-rc.2`, Node.js `>=22.19`.
11
+
12
+ ```sh
13
+ dsh plugin --profile web add dsh-auto-model-routing
14
+ # Or install source (approve the local build when prompted):
15
+ dsh plugin --profile web add prgrmrwy/dsh-auto-model-routing
16
+ ```
17
+
18
+ Restart DSH, refresh the Web page, then configure your OpenRouter key in **Settings → 自动模型路由**. The companion skill is included; it guides delegation but does not enforce every dispatch. Unlike model-pool routers or local classifiers, this plugin uses external Jev judgments and never switches the main model. The demos use an isolated Host with local mock Jev/model responses.
19
+
20
+ In [ohmydsh](https://github.com/prgrmrwy/ohmydsh), enable only the local `auto-model-routing` entry and run `dsh build`; no separate skill customization is needed.
21
+
22
+ ## Use
23
+
24
+ | Where | What you do |
25
+ |---|---|
26
+ | **AUTO / MANUAL chip** (left of the model picker) | Click to switch. Hover to see this turn's effort, the latest Jev decision and its distribution. |
27
+ | **Decision hint** | Appears above the chip for 3 s after each judgment, e.g. `complex → high · 0.70s`. |
28
+ | **Gauge button** on a reply | Hover for the judgment; click to record which tier the turn should have used. |
29
+ | **Settings → 自动模型路由** | OpenRouter key, default mode, effort cap, Jev deadline, hint switch and the routing maps (below). |
30
+
31
+ ![Settings → Auto model routing: judging service, session defaults, and the Claude / GPT routing maps with main-chat effort and sub-agent recommendation per tier](docs/settings.gif)
32
+
33
+ **Default effort.** Each model starts at its officially recommended effort: `standard` keeps it, `simple` goes one step down, `complex` one up, `escalated` two up. The result is capped (default `xhigh`), and AUTO never picks `max`. Each cell of the routing map can override this: main efforts apply to every model of a provider family, and sub-agent cells are full model + effort pairs.
34
+
35
+ **Sub-agents.** The `route_subagent` tool uses the same judgment and returns provider/model/effort (Claude: Haiku → Sonnet → Opus → Opus; GPT: Luna → Sol → Sol → Sol). It only judges when the root chat is AUTO, and otherwise returns `routed: false`. These routes must be in the official sub-agent allowlist, which is fixed when a chat is created.
36
+
37
+ ## Good to know
38
+
39
+ - **New chats default to MANUAL.** You can change this in Settings.
40
+ - **Fail closed.** No key, out of credits, rate limit, region block, timeout or a bad reply: the chat goes to `MANUAL · Jev 停用` with the reason. Click AUTO to retry. There is no local fallback and no retry.
41
+ - **MANUAL only stops changes.** The chat keeps the last effort AUTO set. AUTO also writes it into the official selection, so new chats start from it.
42
+ - **Data sent out.** In AUTO, every user turn sends up to 8000 characters of your message and short parts of the previous turn to OpenRouter / TypeSafe (`typesafe/jev-1.13`). The text is redacted by shape first (keys, tokens, URL credentials, IPs). This is best effort and does not guarantee that every secret is removed.
43
+ - **The key** is stored through the official DSH credentials service, never in the plugin config. A key in the launch environment (`OPENROUTER_API_KEY`) takes precedence and is read-only. To move it to the GUI, remove it from the launch environment, restart once, then save it in Settings.
44
+ - **Files.** Settings live in `$DSH_HOME/plugins/dsh-auto-model-routing/config.json`; per-chat mode and judgments live in `$DSH_HOME/state/auto-model-routing/`. Changes take effect on the next request; no restart is needed.
45
+
46
+ ## Architecture
47
+ <!-- section: architecture -->
48
+
49
+ ![auto-model-routing architecture: the chip and RPC endpoints, the agent/pre-step hook asking Jev through OpenRouter, the agent/request hook rewriting only reasoning effort, and the route_subagent tool sharing the same judgment](docs/architecture.dual.svg)
50
+
51
+ An `agent/pre-step` hook judges step 1 of each user turn. An `agent/request` hook (prepended) then rewrites only `reasoningEffort`, and syncs it to the official model selection. Entry point: [`src/index.ts`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/index.ts). Rubric: [`src/rubric.json`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/rubric.json). Effort table: [`src/effort.ts`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/effort.ts). UI: [`src/client/`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/client/index.ts). Regression cases: [`eval/`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/eval/README.md). Diagram source: [`docs/architecture.json`](docs/architecture.json) (archify).
52
+
53
+ ## Development
54
+
55
+ ```sh
56
+ npm test
57
+ npm run typecheck
58
+ npm run build
59
+ ```
60
+
61
+ Tests use the real AgentLoop with a fake LLM stream and a loopback fake Jev; they never call OpenRouter. `node scripts/label-report.mjs` summarizes your tier labels per rubric version.
62
+
63
+ Specs and design: the current spec is [`openspec/specs/auto-model-routing`](https://github.com/prgrmrwy/ohmydsh/blob/main/openspec/specs/auto-model-routing/spec.md). The archived changes record the design history: [routing](https://github.com/prgrmrwy/ohmydsh/blob/main/openspec/changes/archive/2026-10-22-auto-model-routing/design.md) (decisions D1–D14) and [settings](https://github.com/prgrmrwy/ohmydsh/blob/main/openspec/changes/archive/2026-10-23-auto-model-routing-settings/design.md). The companion skill is [`skills/subagent-model-routing`](skills/subagent-model-routing/SKILL.md). Before you change the hooks, read [DSH plugin integration pitfalls](https://github.com/prgrmrwy/ohmydsh/blob/main/docs/architecture/dsh-plugin-integration-pitfalls.md).
64
+
65
+ ## Removal
66
+ <!-- section: removal -->
67
+
68
+ Run `dsh plugin --profile web remove dsh-auto-model-routing`, then restart DSH and refresh the page. In ohmydsh, set `enabled: false` and rebuild instead. The plugin-owned skill and tools disappear; settings and logs remain. Chats keep the last effort AUTO set until you pick another one.
package/README.zh.md ADDED
@@ -0,0 +1,68 @@
1
+ # dsh-auto-model-routing
2
+
3
+ [English](README.md) · 简体中文
4
+
5
+ ![AUTO 实际效果:「重构并调试」被判为 complex,用 high;随后的「改个名」被判为 simple,降到 low;悬停 AUTO 芯片查看判档,点击切到 MANUAL](docs/auto-routing.gif)
6
+
7
+ <!-- problem -->
8
+ 不必每条消息都手动调高或调低推理强度。AUTO 下,每个用户回合由 Jev 决策模型(经 OpenRouter)判为 `simple` / `standard` / `complex` / `escalated`,插件**只调整你已选模型的推理强度**,不换 provider 和模型。Jev 任何失败都会让 AUTO 自动停用,芯片上显示原因。
9
+
10
+ **安装**:DSH `0.2.0-rc.2`,Node.js `>=22.19`。
11
+
12
+ ```sh
13
+ dsh plugin --profile web add dsh-auto-model-routing
14
+ # 或从源码安装(出现提示时批准本地构建):
15
+ dsh plugin --profile web add prgrmrwy/dsh-auto-model-routing
16
+ ```
17
+
18
+ 重启 DSH、刷新页面,再到**设置 → 自动模型路由**配置 OpenRouter key。配套 skill 已包含,提供委派指引,但不强制拦截每次派发。与模型池路由或本地分类器不同,本插件用外部 Jev 判档,始终不换主模型。演示来自隔离 Host,使用本地模拟的 Jev 和模型响应。
19
+
20
+ 在 [ohmydsh](https://github.com/prgrmrwy/ohmydsh) 中只需启用 local `auto-model-routing` 条目并运行 `dsh build`,不再单独启用 skill 条目。
21
+
22
+ ## 使用
23
+
24
+ | 位置 | 操作 |
25
+ |---|---|
26
+ | **AUTO / MANUAL 芯片**(模型选择器左侧) | 点击切换;悬停查看本回合 effort、最近一次 Jev 决策及其分布 |
27
+ | **判档提示** | 每次判档后在芯片上方显示 3 秒,例如 `complex → high · 0.70s` |
28
+ | 回复下方的**仪表按钮** | 悬停看判档,点击标注「这轮应该用哪档」 |
29
+ | **设置 → 自动模型路由** | OpenRouter key、默认模式、强度上限、判档等待上限、提示开关、路由映射(见下图) |
30
+
31
+ ![设置 → 自动模型路由:判档服务、会话默认值,以及 Claude / GPT 分页下每档的主会话推理等级与子会话推荐](docs/settings.gif)
32
+
33
+ **缺省强度**:从各模型的官方推荐起点出发。standard 取起点,simple 降一级,complex 升一级,escalated 升两级;受上限约束(缺省 `xhigh`),AUTO 永不选 `max`。路由映射可逐格覆盖:主会话等级作用于同体系所有模型,子会话格为完整的 model + effort。
34
+
35
+ **子会话**:`route_subagent` 工具用同一套判档,返回 provider/model/effort(Claude:Haiku → Sonnet → Opus → Opus;GPT:Luna → Sol → Sol → Sol)。只有根会话为 AUTO 时才判档,否则返回 `routed: false`。这些路由须在官方子智能体允许列表中,该列表在会话创建时固定。
36
+
37
+ ## 须知
38
+
39
+ - **新会话缺省 MANUAL**,可在设置中改。
40
+ - **失败即关闭**:无 key、余额不足、限流、地区受限、超时或响应无效时,会话切到 `MANUAL · Jev 停用` 并显示原因,点 AUTO 重试。没有本地降级,也不重试。
41
+ - **MANUAL 只停止调整**:会话保持 AUTO 最后设定的 effort。AUTO 也会把它写入官方模型选择,所以新会话会从这个值开始。
42
+ - **外发数据**:AUTO 下每个用户回合会把你的消息(最多 8000 字符)和上一轮的少量片段发给 OpenRouter / TypeSafe(`typesafe/jev-1.13`)。外发前先按形态脱敏(密钥、token、URL 凭据、IP),这是尽力而为,不保证去掉所有敏感信息。
43
+ - **key** 经官方 DSH 凭据服务保存,不写进插件配置。启动环境里的 `OPENROUTER_API_KEY` 优先且只读;要迁到 GUI,先从启动环境删掉它,重启一次,再在设置页保存。
44
+ - **文件**:设置在 `$DSH_HOME/plugins/dsh-auto-model-routing/config.json`;每个会话的模式与判档记录在 `$DSH_HOME/state/auto-model-routing/`。改动在下一次请求生效,无需重启。
45
+
46
+ ## 架构
47
+ <!-- section: architecture -->
48
+
49
+ ![auto-model-routing 架构图:芯片与 RPC 端点、agent/pre-step 钩子经 OpenRouter 请求 Jev、agent/request 钩子只改推理强度、route_subagent 工具共用同一判断](docs/architecture.dual.svg)
50
+
51
+ `agent/pre-step` 钩子在每个用户回合的第 1 步判档;随后以 prepend 注册的 `agent/request` 钩子只改写 `reasoningEffort`,并同步到官方模型选择。入口 [`src/index.ts`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/index.ts),判档规则 [`src/rubric.json`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/rubric.json),强度表 [`src/effort.ts`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/effort.ts),界面 [`src/client/`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/src/client/index.ts),回归用例 [`eval/`](https://github.com/prgrmrwy/dsh-auto-model-routing/blob/main/eval/README.zh.md),图源 [`docs/architecture.json`](docs/architecture.json)(archify)。
52
+
53
+ ## 开发验证
54
+
55
+ ```sh
56
+ npm test
57
+ npm run typecheck
58
+ npm run build
59
+ ```
60
+
61
+ 测试使用真实 AgentLoop、假 LLM 流和本地回环假 Jev,不访问 OpenRouter。`node scripts/label-report.mjs` 按规则版本汇总你的档位标注。
62
+
63
+ 规范与设计:当前规范见 [`openspec/specs/auto-model-routing`](https://github.com/prgrmrwy/ohmydsh/blob/main/openspec/specs/auto-model-routing/spec.md)。归档 change 记录了设计演进:[路由](https://github.com/prgrmrwy/ohmydsh/blob/main/openspec/changes/archive/2026-10-22-auto-model-routing/design.md)(决策 D1–D14)与[设置](https://github.com/prgrmrwy/ohmydsh/blob/main/openspec/changes/archive/2026-10-23-auto-model-routing-settings/design.md)。配套 skill 见 [`skills/subagent-model-routing`](skills/subagent-model-routing/SKILL.md)。修改钩子前先读 [DSH 插件集成陷阱](https://github.com/prgrmrwy/ohmydsh/blob/main/docs/architecture/dsh-plugin-integration-pitfalls.md)。
64
+
65
+ ## 移除
66
+ <!-- section: removal -->
67
+
68
+ 运行 `dsh plugin --profile web remove dsh-auto-model-routing`,重启 DSH 并刷新页面;ohmydsh 则设为 `enabled: false` 并构建。插件提供的 skill 与工具一并撤销,设置和日志保留。会话保持 AUTO 最后设定的 effort,直到在模型选择器里另选。
@@ -0,0 +1,9 @@
1
+ - insert:
2
+ - id: dsh-auto-model-routing
3
+ name: dsh-auto-model-routing
4
+ - id: auto-model-routing-skills
5
+ name: '@deepseek-ai/dsh-skill-filesystem'
6
+ config:
7
+ providerName: auto-model-routing-plugin
8
+ includeDefaultRoots: false
9
+ bundledSkillDir: !!js process.getBuiltinModule('node:path').join(process.getBuiltinModule('node:path').dirname(process.getBuiltinModule('node:module').createRequire(baseUrl).resolve('dsh-auto-model-routing/package.json')), 'skills')
@@ -0,0 +1,6 @@
1
+ # Screenshots
2
+
3
+ | file | kind | source | date | reviewer | verdict | note |
4
+ | --- | --- | --- | --- | --- | --- | --- |
5
+ | auto-routing.gif | screenshot | isolated DSH_HOME instance (temp HOME/XDG/DSH_HOME under /tmp, port 3199), synthetic data: local mock model and mock Jev on loopback, demo prompts; recorded with agent-browser, converted with ffmpeg | 2026-10-23 | lead | pass (viewed frames: demo prompts and mock replies only; no hostname, user, path, token or real session) | AUTO chip, decision hint, hover panel, switch to MANUAL |
6
+ | settings.gif | screenshot | same isolated instance and recording run as auto-routing.gif | 2026-10-23 | lead | pass (viewed frames: settings section only; key field empty, source shown as launch environment of the isolated process) | Settings → 自动模型路由, Claude/GPT routing maps |