diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json index 75fa4ed..e87112b 100644 --- a/.claude-plugin/plugin.json +++ b/.claude-plugin/plugin.json @@ -1,6 +1,6 @@ { "name": "jsc-cli", - "version": "0.0.1", + "version": "0.0.2", "description": "CLI 偵測、模型能力標籤與技能庫批次部署", "skills": "./skills", "author": { diff --git a/.codex-plugin/plugin.json b/.codex-plugin/plugin.json index e5039e6..f96f73d 100644 --- a/.codex-plugin/plugin.json +++ b/.codex-plugin/plugin.json @@ -1,6 +1,6 @@ { "name": "jsc-cli", - "version": "0.0.1", + "version": "0.0.2", "description": "CLI 偵測、模型能力標籤與技能庫批次部署", "skills": "./skills" } diff --git a/README.md b/README.md index ac30862..317b7ca 100644 --- a/README.md +++ b/README.md @@ -21,6 +21,7 @@ Marketplace 統一為 `jsc`(https://gitea.jsc.idv.tw/plugins/jsc.git),安 | 工具 | 用途 | | --- | --- | | `tools/detect-clis.sh` | 列出已安裝的 AI CLI 與執行檔路徑(TSV:name / path / version;kiro 的執行檔為 `kiro-cli`) | +| `tools/model-config.sh` | 解析 SDLC 各階段的指定模型鏈(`get {stage}`、`list`);專案 `.jsc/models` 優先於 `$JSC_HOME/models.conf`,格式見 `references/model-tags.md` | ## Skills 目錄 @@ -30,7 +31,7 @@ Marketplace 統一為 `jsc`(https://gitea.jsc.idv.tw/plugins/jsc.git),安 ### `models` -讀取各已安裝 CLI 可使用的模型並加上能力標籤(`references/model-tags.md`),並列出 SDLC 各階段的必要標籤,供 `jsc-sdlc` 的模型能力閘門使用。 +讀取各已安裝 CLI 可使用的模型並加上能力標籤(`references/model-tags.md`),列出 SDLC 各階段的必要標籤,並用 `tools/model-config.sh` 解析各階段的指定模型鏈(專案 `.jsc/models` 優先於 `$JSC_HOME/models.conf`)。`jsc-sdlc` 閘門先看指定模型,沒有指定才退回標籤比對。 ### `deploy` diff --git a/plugin.json b/plugin.json index ed9ebb1..009a189 100644 --- a/plugin.json +++ b/plugin.json @@ -1,6 +1,6 @@ { "name": "jsc-cli", - "version": "0.0.1", + "version": "0.0.2", "description": "CLI 偵測、模型能力標籤與技能庫批次部署", "skills": "./skills/" } diff --git a/references/model-tags.md b/references/model-tags.md index 954280d..e1ecfde 100644 --- a/references/model-tags.md +++ b/references/model-tags.md @@ -34,4 +34,27 @@ | 實作(implement) | coding | | 維護(maintain) | 任意 | +## 階段指定模型(角色式路由) + +每個 SDLC 階段可以指定一個模型,並附上遞補模型。設定格式一行一階段: + +``` +stage=model[,fallback1[,fallback2...]] +``` + +「#」開頭為註解,空白行忽略。階段限定 plan、analyze、implement、maintain。 + +設定檔位置與優先序: + +| 順位 | 檔案 | 範圍 | +| --- | --- | --- | +| 1 | 專案目錄的 `.jsc/models` | 專案覆寫 | +| 2 | `$JSC_HOME/models.conf`(`JSC_HOME` 預設 `~/.jsc`) | 全域 | + +專案檔有設定的階段完全覆寫全域設定;其餘階段仍讀全域檔。解析一律用 `jsc-cli/tools/model-config.sh`,不自行讀檔。 + +遞補鏈語意:鏈上第一個模型優先;前面的模型不可用時依序後退到下一個。 + +指定模型優先於標籤比對:階段有指定模型時直接用指定鏈;只有階段沒有指定模型時,才用上表的必要標籤判定。 + 表列以外的模型:依 `jsc-ask:ask` 規則詢問使用者或依供應商文件補表後再判定。 diff --git a/skills/models/SKILL.md b/skills/models/SKILL.md index 2ff0795..9c68060 100644 --- a/skills/models/SKILL.md +++ b/skills/models/SKILL.md @@ -1,6 +1,6 @@ --- name: models -description: List every model usable by each installed AI CLI (claude, codex, copilot, antigravity, kiro) and attach capability tags from references/model-tags.md. Also states which tags each SDLC phase requires, so jsc-sdlc skills can gate execution. Use when checking model fitness or inventorying models; not for switching models. +description: List every model usable by each installed AI CLI (claude, codex, copilot, antigravity, kiro) and attach capability tags from references/model-tags.md. Also resolves each SDLC stage's designated model chain via tools/model-config.sh (project .jsc/models overrides $JSC_HOME/models.conf) and states which tags each phase requires, so jsc-sdlc skills gate on the designated model first and fall back to capability tags. Use when checking model fitness, inventorying models, or reviewing designated-model routing; not for switching models or editing the config files. --- # models — list CLI models with capability tags @@ -22,3 +22,4 @@ description: List every model usable by each installed AI CLI (claude, codex, co 3. Attach capability tags to every model per `references/model-tags.md`. Handle unlisted models per the closing rule of that file. 4. Output a table with four columns: CLI, model, tags, currently in use. 5. Append the SDLC phase requirement table (plan and analyze need `reasoning-high`; implement needs `coding`; maintain accepts any), so `jsc-sdlc` skills can gate on model capability. +6. Run `jsc-cli/tools/model-config.sh list` and append a 「階段指定模型」 table right after the phase requirement table, with three columns: stage, designated chain, source (`project` / `global`). State below the table that `jsc-sdlc` gates resolve the designated model first and fall back to capability tags only when a stage has no designated model. Done when the table shows all four stages, with `-` for unconfigured ones. diff --git a/tools/model-config.sh b/tools/model-config.sh new file mode 100755 index 0000000..e9108d7 --- /dev/null +++ b/tools/model-config.sh @@ -0,0 +1,84 @@ +#!/usr/bin/env sh +# model-config.sh — 解析 SDLC 各階段的指定模型鏈(角色式路由)。 +# 設定格式(一行一階段):stage=model[,fallback1[,fallback2...]] +# 「#」開頭為註解,空白行忽略。階段限定:plan、analyze、implement、maintain。 +# 解析順序: +# 1. 目前工作目錄的 ./.jsc/models(專案覆寫) +# 2. $JSC_HOME/models.conf(JSC_HOME 預設 ~/.jsc) +# 專案檔有設定的階段完全覆寫全域設定;其餘階段仍讀全域檔。 +# 用法: +# model-config.sh get {stage} 印出該階段解析後的模型鏈(逗號分隔);未設定不印。兩種情況都 exit 0。 +# model-config.sh list 每階段一行:stagechainsource(project 或 global);未設定的 chain 與 source 印「-」。 +set -u + +JSC_HOME="${JSC_HOME:-$HOME/.jsc}" +PROJECT_FILE=./.jsc/models +GLOBAL_FILE="$JSC_HOME/models.conf" +STAGES="plan analyze implement maintain" + +# 取出單一設定檔裡某階段的模型鏈。 +# 同階段出現多行時取最後一行,結果才有確定性。 +read_chain() { # $1=設定檔 $2=階段 + [ -f "$1" ] || return 0 + awk -F= -v stage="$2" ' + { sub(/\r$/, "") } # 去掉 CR + /^[ \t]*#/ { next } # 註解行 + /^[ \t]*$/ { next } # 空白行 + index($0, "=") == 0 { next } + { + key = $1 + gsub(/[ \t]/, "", key) + if (key != stage) next + val = substr($0, index($0, "=") + 1) + gsub(/[ \t]/, "", val) + if (val != "") chain = val + } + END { if (chain != "") print chain } + ' "$1" +} + +# 解析單一階段:專案檔優先,該階段沒設定才退回全域檔。 +# 輸出:chainsource;兩檔都沒設定時不輸出。 +resolve() { # $1=階段 + chain=$(read_chain "$PROJECT_FILE" "$1") + if [ -n "$chain" ]; then + printf '%s\tproject\n' "$chain" + return 0 + fi + chain=$(read_chain "$GLOBAL_FILE" "$1") + if [ -n "$chain" ]; then + printf '%s\tglobal\n' "$chain" + fi + return 0 +} + +usage() { + echo "用法:model-config.sh get {plan|analyze|implement|maintain} | list" >&2 + exit 1 +} + +case "${1:-}" in + get) + stage="${2:-}" + case " $STAGES " in + *" $stage "*) ;; + *) usage ;; + esac + resolve "$stage" | cut -f1 + exit 0 + ;; + list) + for stage in $STAGES; do + line=$(resolve "$stage") + if [ -n "$line" ]; then + printf '%s\t%s\n' "$stage" "$line" + else + printf '%s\t-\t-\n' "$stage" + fi + done + exit 0 + ;; + *) + usage + ;; +esac