Files
meta/references/wp01-baseline-decisions.md
jiantw83 b8b5737bc3 docs(wp01-baseline): 新增定案規格與待辦校正兩份參考文件
What:新增兩份文件。wp01-baseline-decisions.md 收錄十項技術定案(雜湊分隔符、計畫名稱正規化、跨存取庫工作包編號起算、PLAN_CONTENTS 存取庫欄格式、工作日誌週次雜湊、舊日誌拆頁、輸出原則 lint 化範圍、CPM 圖涵蓋範圍、不監看時的相依判定、PR 疊包上限),並補上五個未註冊存取庫(code、doc、persona、shared、code-review)去向決議:全部不納入 marketplace 正本,維持獨立系統。wp01-todo-corrections.md 收錄 TODO.md 十五項狀態過期校正與五項數字更新。

Why:分析階段裁定的規格內容原本只寫在分析頁全文裡,後續工作包每次要引用都得回頭翻找。整理成獨立文件,附出處與具體例子,工作包可以直接引用,不必重新確認脈絡。另外,TODO.md 本身不在任何 git 存取庫底下,沒有分支也沒有 PR 可走,校正意見沒有地方能落地,只能整理成清單交使用者手動核對。

How:定案文件逐項附出處(對應分析頁或測試計畫段落)與可驗證的具體例子,方便日後照抄核對。待辦校正文件依「狀態過期」與「數字更新」分兩節整理,開頭寫明無法走 PR 的原因,並註明資料來源是同一輪盤點、以各存取庫 origin/develop 為準逐一核對得出。

Who:WP-01 定案規格交付包。
2026-09-08 09:08:36 +08:00

17 KiB
Raw Permalink Blame History

十項定案規格

這份文件收錄分析頁裡十項技術裁定的定案內容,每項附出處與具體例子,供後續工作包直接引用,不必回頭翻找分析頁全文。

N-01:雜湊輸入分隔符

裁決:多個欄位(例如計畫名稱與存取庫路徑)要接成一個雜湊輸入字串時,固定用直線號 | 當分隔符。組法收在 hash-id 的 key 子命令這個單一入口,各技能不再自己接字串。

出處:「工作分解結構(WBS)」層1 共用腳本表格,工作包名稱「hash-id 加 key 子命令:分隔符 |、四道正規化、組法收單一入口」;測試計畫「雜湊組法收單一入口」小節第一個 TDD 循環,斷言 hash-id key "我的計畫" "plugins/sdlc" 與 hash-id "我的計畫|plugins/sdlc" 輸出同一個 40 碼雜湊。

例外:本份分析頁自己的雜湊輸入不吃 {owner}/{repo},只用計畫名稱,理由是這一輪盤點橫跨 11 個存取庫,綁任一個存取庫都是錯的。這是單一頁面的特例,不是分隔符定案本身跟著變。

例子:

hash-id key "我的計畫" "plugins/sdlc"
# 與下面這行輸出同一個 40 碼大寫 SHA-1
hash-id "我的計畫|plugins/sdlc"

N-02:計畫名稱正規化規則

裁決:計畫名稱進雜湊前,固定套四道正規化,依序是:

  1. Unicode NFC 正規化
  2. 去除頭尾空白
  3. 內部連續空白壓成一個半形空白
  4. 英數字元全形轉半形

大小寫不在正規化範圍內,維持原樣、視為不同名稱。

出處:測試計畫「雜湊組法收單一入口」小節第二個 TDD 循環,斷言「我的 計畫」「我的 計畫」「我的計畫 」三種輸入正規化後相同,而「ABC 計畫」與「abc 計畫」不同;最小實作寫明四道正規化內容。

例子:

  • 我的 計畫、我的 計畫(全形空白)、我的 計畫(兩個半形空白)→ 正規化後同一個結果,雜湊相同,第二次建立同名計畫會被擋下
  • ABC 計畫 與 abc 計畫 → 正規化後仍不同,雜湊不同,兩者當成不同計畫

可直接貼進測試檔的指令:

hash-id key "我的 計畫" "plugins/sdlc"
hash-id key "我的 計畫" "plugins/sdlc"
hash-id key "我的  計畫" "plugins/sdlc"
# 三行輸出同一個 40 碼雜湊

hash-id key "ABC 計畫" "plugins/sdlc"
hash-id key "abc 計畫" "plugins/sdlc"
# 兩行輸出不同雜湊,這是反例,證明大小寫不會被正規化抹掉

N-05:跨存取庫工作包編號起算

裁決:每一份分析頁的工作包編號各自從 WP-01 起算,不跨頁連號。因此鎖定工作包不能只看編號,要在前面加上該分析頁自己的雜湊當複合鍵,兩份不同分析頁裡同編號的工作包才不會互搶同一把鎖。

出處:「工作分解結構(WBS)」層2 技能行為表格,處理 analyze 頁名與跨庫的工作包名稱寫明「各頁 WP-01 起算」;對應 TDD 小節斷言兩份不同分析頁各自的「雜湊組法收單一入口」下游工作包不互相搶鎖,最小實作是把鎖鍵改成「{分析頁雜湊}#WP-NN」複合鍵。

例子:分析頁 A 與分析頁 B 各有自己的第二個工作包。鎖鍵分別是 {分析頁A雜湊}#WP-02 與 {分析頁B雜湊}#WP-02,領取其中一個不影響另一個,兩邊各自從 1 起算。

N-07:PLAN_CONTENTS 存取庫欄格式

裁決:PLAN_CONTENTS 目錄頁的存取庫欄改成清單,同一行、多個值用頓號分隔,不拆成多行子條列。

出處:「工作分解結構(WBS)」層2 技能行為表格,工作包名稱「PLAN_CONTENTS 存取庫欄改清單,同行頓號分隔」;對應 TDD 小節斷言那一行 upsert 後讀得回多個值,最小實作是改範本並在寫入時以頓號串接。

例子:

- 存取庫:plugins/sdlc、plugins/log

L-03:年月週次進雜湊輸入

裁決:工作日誌頁名的雜湊輸入改吃「年-月-週次」字串(例如 2026-09-W1),取代原本的 {owner}/{repo}。週次字串進的是雜湊輸入本身,不是先照舊算出雜湊再在頁名後面加後綴。

出處:測試計畫「一週一頁工作日誌」小節第一個 TDD 循環,斷言三個不同存取庫、同一週的三筆日誌落在同一頁,且雜湊輸入不含 {owner}/{repo},最小實作是「頁名改吃週次字串」。

例子:plugins/sdlc、plugins/log、plugins/meta 三個存取庫在同一週(週五落在 2026-09-04)各寫一筆日誌。三筆都算出同一個雜湊、落在同一頁 LOG_{hash(2026-09-W1)},各自在頁面內容裡帶自己的存取庫欄位。

可直接貼進測試檔的指令:

worklog-target.sh week 2026-09-04
# 輸出:2026-09-W1

邊界情況(反例,跨月份):2026-08-28 是 8 月最後一個週五,算出 2026-08-W4;隔一週的 2026-09-04 只差 7 天,卻因為跨了月份算出 2026-09-W1。兩者雜湊不同、落在不同頁,不能因為「只差一週」就假設落在同一頁。

worklog-target.sh week 2026-08-28
# 輸出:2026-08-W4

L-05:舊日誌拆頁

裁決:舊制一庫一頁的工作日誌,依每筆條目自己的日期拆進對應的週頁,不整頁原樣搬過去。拆頁動作可重跑不重複(用條目內容雜湊去重),拆不出日期的條目列進待處理清單,不猜日期也不丟棄。

出處:「工作分解結構(WBS)」層3 搬遷與清理表格,工作包名稱「舊一庫一頁日誌依條目日期拆進各週頁,可重跑」,標明「不可逆」;對應 TDD 小節斷言含日期的條目落到正確週頁、沒日期的條目列進待處理清單且不丟掉,同一份輸入跑兩次不產生重複條目。

例子:舊頁裡四筆條目:

條目 日期 落頁
條目一 2026-08-14 LOG_{hash(2026-08-W2)}
條目二 2026-08-28 LOG_{hash(2026-08-W4)}
條目三 2026-09-04 LOG_{hash(2026-09-W1)}
條目四 無日期欄位 列進待處理清單,不猜週次

三筆有日期的條目各自落進對應週頁;第四筆沒有日期,列進一份待處理清單交人工確認,不強行歸入任何一週。同一份舊頁重跑一次拆頁,用條目內容雜湊去重,不會讓已經拆過的四筆再多出一份——重跑後 LOG_{hash(2026-08-W2)} 頁裡條目一依然只有一份,不是兩份。

O-09:六條輸出原則裡哪幾條進得了 lint

裁決:六條輸出原則裡,只有「避免書面語」與「問句要放句尾」這兩條寫成 ste100-lint.sh 裡的程式化判定;其餘四條要靠語意判斷,不硬塞進 lint。

出處:「工作分解結構(WBS)」層2 技能行為表格,工作包名稱「ste100-lint.sh 補書面語詞彙與問句位置,加名詞展開寫法檢查」,註記「O-09 定案」;對應 TDD 小節有兩個判定,一個餵「請您進行身分驗證確認之動作」斷言抓得到書面語並建議改寫,另一個餵「請告訴我目的地,以便為您查詢班機」斷言抓得到問句不在句尾。

例子:

  • 輸入「請您進行身分驗證確認之動作」→ 判定為書面語,建議改寫成「請幫我確認您的身分」
  • 輸入「請告訴我目的地,以便為您查詢班機」→ 判定為問句不在句尾,應改成先問句、後補充理由

A-12:關鍵路徑圖涵蓋所有工作包

裁決:「涵蓋所有工作包」是指關鍵路徑圖上要畫出全部工作包,不是把 WBS 拆成每一包都串在同一條鏈上。圖裡只有真正的最長鏈標成關鍵路徑,其餘工作包照自己實際的相依邊掛上去,不為了「全部在一條鏈上」而編造假的先後順序。

出處:分析頁「關鍵路徑(CPM)」節開頭:「本圖收進全部 55 個工作包(2026-09-07 裁示:關鍵路徑圖必須涵蓋所有工作包)」,並註明「crit 只標最長那一條鏈,其餘照自己的相依邊掛,不串成假的先後順序」。

例子:55 個工作包全部畫進甘特圖;只有一條鏈(定案交付包 → 雜湊組法收單一入口 → 一週一頁工作日誌 → 舊日誌拆頁)標成關鍵路徑,其餘工作包各自照自己的相依關係接線,沒有相依的直接從錨點日期起排,不硬接到關鍵路徑上。

可直接比對的斷言:

  • 甘特圖節點總數:55(等於分析頁工作包總數,一個都不能少)
  • 標 crit 的節點數:4(就是上面那條鏈),其餘 51 個工作包不掛 crit
  • 反例:沒有相依的工作包(例如一個獨立的小型修正包)不會被接在關鍵路徑任何一個節點後面,而是直接從錨點日期起排;如果檢查發現它被接進了那條 4 節點的鏈,就是誤把「涵蓋」做成了「全部串成一條鏈」

I-07:不監看時的相依判定

裁決:implement 階段選擇不監看 PR 時,判斷某個工作包是否「已完成」要同時滿足兩個條件:狀態欄本身寫著「已完成」,而且那個工作包對應的 commit 真的在目前分支的歷史裡(用 git merge-base --is-ancestor 判定,狀態欄要多存一個 commit 欄位)。兩個條件都成立才放行,只滿足其中一條不算。

這個判法跟「PR 已合併」不衝突:監看模式下 PR 合併之後,commit 自然會進到分支歷史裡,兩個條件同時成立;不監看模式下沒有實際等 PR 合併,改靠這兩個條件直接對真實的 git 歷史查驗,效果等同,但不必守著輪詢。

出處:測試計畫「implement PR 監看二選一」小節第二個 TDD 循環,斷言相依包狀態欄寫「已完成」但其 commit 不在目前分支歷史裡時不放行,兩條都成立才放行;使用者故事驗收計畫「PR 沒人審把階段掛住」失敗流程一列寫明「相依判定改吃『狀態欄加 git 祖先』」。

例子:某個工作包的狀態欄寫「已完成」、commit 欄記著一個 40 碼 SHA-1。查驗時執行 git merge-base --is-ancestor {該commit} HEAD;結束碼 0 才判定它真的完成,可以讓依賴它的下一包開工;結束碼非 0(commit 不在目前分支歷史)即使狀態欄寫完成也不放行。

反例(另一半條件不成立):狀態欄寫「進行中」,commit 欄記的 commit 其實已經是 HEAD 的祖先(git merge-base --is-ancestor 結束碼 0)。這種情況一樣不放行——兩個條件要同時成立,狀態欄沒寫「已完成」,光是 commit 在歷史裡也不夠。

I-09:同一張 PR 疊多個工作包要不要收斂

裁決:不設上限,也不強制收斂。一張 PR 可以疊上任意數量的工作包;每次收尾時要印出目前這張 PR 疊了幾個工作包、累計改了幾行(用 git diff --shortstat 取得),讓疊加狀況看得見,但不會因為疊太多就被擋下。

出處:「定案規格交付包」工作包的測試計畫小節,列出十項定案的簡表,其中一項寫明「I-09 不設上限」;「implement PR 監看二選一」小節第四個 TDD 循環,斷言每次收尾都印出目前這張 PR 疊了幾包、累計幾行,最小實作是取 git diff --shortstat 與領取紀錄。

例子:同一張 PR 已經疊了 3 個工作包、累計改了 214 行。收尾時印出「本 PR 目前疊 3 包,累計 +180/-34 行」,然後照常繼續,不會因為已經疊了 3 包就強制先關閉這張 PR。

無繼承例子的工作包:analyze-check.sh 三合一靜態檢核

說明:這份文件收錄的十項技術定案加 F-01 決議,沒有一項對應到「三合一靜態檢核」這個工作包。逐一核對過 N-01、N-02、N-05、N-07、L-03、L-05、O-09、A-12、I-07、I-09、F-01,都不是這個工作包的裁決依據,硬套任何一項的例子都是誤導。

如實記錄:這個工作包沒有從十項技術定案加 F-01 決議裡繼承到的例子,動工時要自己另外準備測試資料——具體要涵蓋哪三種靜態檢核、各自的正常輸入與異常輸入長什麼樣子,留給工作包自己在分析頁或動工當下決定,不在這份文件裡代寫。

F-01:五個未註冊存取庫的去向

盤點 jsc 技能組時,發現五個存取庫檔案完整、能動,但沒登錄進 plugins/meta marketplace 正本的 .claude-plugin/marketplace.json。這一節記下五個存取庫各自的決議,供 E 表重寫直接引用。

裁決:五個存取庫全部不納入正本,各自維持獨立系統。逐一列用途與決議:

存取庫 一句話用途 決議
plugins/code(jsc-code) .NET/NuGet 升版、Gitea AI review findings 修復、存取庫批次同步、TARGET.md 每日待辦 不納入正本,維持獨立系統
plugins/doc(jsc-doc) Gitea 通知分組處理、docker 註解整理、議題分析與同步、工時日誌 不納入正本,維持獨立系統
plugins/persona(jsc-persona) AI 人格化記憶聊天,跟 SDLC 技能組完全不相干的獨立系統 不納入正本,維持獨立系統
plugins/shared(jsc-shared) 三十多支跨助理共用規格類技能(spec-*) 不納入正本,維持獨立系統
plugins/code-review(呼叫前綴 jsc:,不是 jsc-code-review:) 以 GitHub Actions 為基礎的 RPG 攻防式 git diff review,跟正本裡互動式的 jsc-review 是兩套不同東西 不納入正本,維持獨立系統

出處:這一輪盤點(2026-09-07)裡使用者針對「五個未註冊存取庫逐一定去向」這一項待辦的明確答覆——五個全部不納入,不再逐一討論註冊、歸檔或刪除三選一。

對 E 表的具體影響:meta/tools/delegate-spec.tsv 本身已經是對的——現有 35 列,不含這五個存取庫的任何技能,不必再修。真正還記著這幾支技能、需要訂正的是 /root/plugins/TODO.md 第 652~655 行那份 E 表(設計討論用的表格,跟 delegate-spec.tsv 是兩份不同的東西)。決議之後,TODO.md 那份 E 表要照下面的方式修正,實際改檔案交給 WP-36(或 TODO.md 自己校正清單裡已經開著的 F-02 項):

  • E-13(TODO.md 第 652 行,jsc-doc:notifications,定期讀 Gitea 通知分組提醒):整條移除。這支技能不會進正本,助理的技能清單裡永遠找不到它。
  • E-14(TODO.md 第 653 行,jsc-code:review-resolve,巡檢 findings 有沒有新的未處理項目):整條移除,理由同上。
  • E-15(TODO.md 第 654 行,原列 jsc-pkg:pkg-update、jsc-code:nuget):只留 jsc-pkg:pkg-update 那一半,jsc-code:nuget 那一半移除。
  • E-16(TODO.md 第 655 行,原列 jsc-code:sync、jsc-gitea:repo-sync):只留 jsc-gitea:repo-sync 那一半,jsc-code:sync 那一半移除。
  • M-20(TODO.md 第 934 行,jsc-code:target 跟助理待辦簿的關係要收攏成一套,還是只巡檢它的系統排程):這個問題本身不成立了。jsc-code:target 不在正本裡,助理的技能清單與委派判定清單都碰不到它,不會被觸發,也就沒有「兩份待辦互不知道」的風險。這一項直接關閉,不必再往下決議要收攏還是只巡檢。

plugins/persona、plugins/shared 沒有被 TODO.md 那份 E 表任何一列引用,純粹是盤點時發現的閒置存取庫,記下「維持獨立、不納入」即可,不需要再對 E 表或委派判定清單做任何修正。

例子:meta/tools/delegate-spec.tsv 現有 35 列,範圍剛好卡在 ask 到 sdlc,不含 code、code-review、doc、persona、shared 五個 domain 的任何一支技能——這份檔案本來就是決議之後該有的樣子,不必動它。要改的是 TODO.md 裡那份 E 表:核對 E-13 到 E-16、M-20 這五列,照上面的方式移除或裁半,不必再往回加東西,也不必幫已刪的那一半補回來。

不是價值判斷:五個存取庫都是完整、能動的系統,不納入正本不代表它們沒用或做得不好。persona 是另一條產品線,人格化聊天跟 SDLC 開發流程沒有交集;shared 是跨助理共用規格技能,服務對象是所有助理而不是單一 SDLC 流程;code、doc、code-review 三個雖然功能上跟 jsc 技能組相近(都碰 Gitea、都碰程式碼),但各自的呼叫方式、維運節奏、目標使用情境都不同,例如 code-review 連呼叫前綴都還是舊的 jsc:,跟正本裡 jsc-review 的互動式流程本來就是兩套設計。維持獨立系統,讓 jsc 技能組正本只收它管得到、巡檢得到的技能,才是對的做法。

跟 wp01-todo-corrections.md 的分工

這份文件收十項技術定案跟 F-01 決議,都是這一輪盤點裡定下來、可以直接引用的規格內容。

TODO.md 的狀態校正另外放在 wp01-todo-corrections.md,不併進這份文件;不能開 PR 的完整理由見該文件開頭。