Immutable Spec:讓需求、設計、執行和驗收收斂到同一份文檔

引言
在傳統的開發流程中,需求、設計、開發計劃、測試記錄、上線說明、回退方案往往分散在多個地方。PR 描述裡有一部分,文檔系統裡有一部分,聊天記錄裡還有一部分。項目推進一段時間後,一個很現實的問題就會出現:
當前到底該按什麼標準繼續做?
而這個問題,到了AI時代會更加突出。Immutable Spec 提供了一種更清晰的做法:每一個需求對應一份 spec,這份 spec 同時承載需求詳情、方案設計、執行計劃和測試驗收標準,並且只允許追加,不允許覆蓋歷史。
它既是一種文檔組織方式,也是一種交付機制。
為什麼需要 Immutable Spec
軟體開發中的許多混亂,並不來自技術本身,而是來自協作標準的不統一。常見情況包括:
- 需求改動後,舊文檔沒有同步,開發繼續按舊理解推進
- 設計和實現脫節,到了驗收階段才發現標準不一致
- 某個事項看起來已經完成,但沒人能準確說明是否真正通過驗收
- 出現問題需要回退時,只能臨時處理,缺少清晰記錄
- 迭代越來越多之後,歷史決策、變更原因和驗證證據難以追溯
這些問題最終都會指向同一個根源:缺少一個唯一、穩定、可追溯的執行標準。
Immutable Spec 的價值,就在於建立這樣一個標準。
Immutable Spec 的核心思路
一份 spec 對應一次需求交付
每一個明確的需求,都應該有一份對應的 spec。
這份 spec 至少覆蓋四個方面:
- 需求詳情
- 方案設計
- 執行計劃
- 測試與驗收標準
這樣,開發、測試、驗收和回退都圍繞同一份文檔展開,團隊對當前目標的理解也會更一致。
文檔只追加,不改寫歷史
這裡的 "immutable" 指的是歷史不可覆蓋。
允許追加:
- 執行日誌
- 驗證證據
- 變更說明
- 狀態記錄
不建議直接修改已經記錄的需求、設計和結論。歷史保留下來,後續追溯才有依據。
同一時間只允許一個 active spec
歷史 spec 應該保留,因為它們本身就是審計鏈路的一部分。
但為了保持流程線性、降低複雜度,同一時間只允許一個 active spec。
這意味著當前執行只能跟隨唯一的一份文檔。舊 spec 可以保留、可以完成、也可以停止使用,但不能與新的執行標準並行生效。
一份 Immutable Spec 應該包含什麼
推薦每份 spec 使用統一結構,例如:
# <Spec Title>
## 1. Requirement Details
- Background
- Scope
- Constraints
- Non-goals
## 2. Outline Design
- Architecture / modules impacted
- Data model and interfaces
- Risk and rollback strategy
## 3. Execution Plan
- [ ] pX-1 <deliverable>
- [ ] pX-2 <deliverable>
## 4. Test And Acceptance Criteria
- TC-1 ...
- TC-2 ...
## 5. Execution Log (append-only)
- <date> pX-1 started ...
- <date> pX-1 completed ...
## 6. Validation Evidence (append-only)
- TC-1 | stack: ... | command: ... | result: ... | note: ...
## 7. Change Log (append-only)
- <date> new requirement / scope change / rollback note
這樣的結構有一個很直接的好處:需求、設計、執行和驗收被放進了同一個上下文裡,團隊不需要在多個地方來回查找當前標準。
為什麼要堅持線性推進
Immutable Spec 特別適合希望降低協作複雜度的團隊。
如果多個 spec 同時處於活躍狀態,問題會迅速增加:優先級如何判斷、依賴如何處理、測試證據歸屬哪一份 spec、回退應該針對哪個狀態、commit 應該關聯哪條鏈路。這些問題會消耗大量協作成本。
更穩妥的方式,是在同一階段只推進一個 active spec。如果需求變化,就新建一份 spec,讓它成為新的執行標準;舊 spec 保留歷史記錄,並明確說明當前已停止使用。
這種做法會帶來少量重複內容,但會顯著提升執行邊界的清晰度。
事項管理:什麼叫「完成」
在 Immutable Spec 中,事項狀態可以保持得很簡單:
[ ]未開始[~]進行中[x]已完成
關鍵在於對「已完成」的定義要足夠嚴格。
一個事項只有在以下條件全部滿足後,才應當標記為完成:
- 實現已經完成
- 對應驗收標準已經驗證
- 驗證證據已經追加到 spec
這樣可以避免一種常見誤區:代碼寫完了,就默認事情完成了。
在工程交付中,完成通常意味著「實現 + 驗證 + 記錄」三者都已經閉合。
事項級提交:讓 commit 與 spec 對齊
如果 spec 是執行標準,那麼 commit 就應該成為這份標準的實現記錄。
推薦做法是:
- 一個事項對應一個 commit
- commit message 包含 spec 文件名和事項 ID
- 沒有驗收證據的事項,不作為完成項提交
例如:
spec(2026-03-06-phase3-runtime-probe.md): p3-1 add runtime probe command
正文可以進一步統一為:
Spec: docs/specs/2026-03-06-phase3-runtime-probe.md
Item: p3-1
Acceptance: TC-1, TC-2
這樣做的好處非常明顯:代碼歷史和文檔歷史自然對齊。後續復盤時,可以快速定位某個 commit 對應的事項、需求背景和驗收標準。
驗收證據需要統一格式,但不應綁定技術棧
不同項目的技術棧不同,驗收命令也會不同。
Rust 項目可能是 cargo test,Node 項目可能是 pnpm build,Python 項目可能是 pytest,部署鏈路可能還涉及 Ansible、Shell 或手工驗證。
因此,更合理的約束方式是統一證據格式,而不是固定命令本身。
推薦格式如下:
TC-<n> | stack: <rust|node|python|ansible|ui|other> | command: <cmd or manual step> | result: <pass|fail> | note: <short observation>
例如:
TC-1 | stack: rust | command: cargo test -q | result: pass | note: deploy payload defaults coveredTC-2 | stack: node | command: pnpm build | result: pass | note: UI renders correctlyTC-3 | stack: ansible | command: ansible-playbook --syntax-check ... | result: pass | note: syntax validTC-4 | stack: ui | command: manual validation | result: pass | note: warning banner displayed
這樣既保留了統一的記錄方式,也保留了對不同項目形態的適配能力。
需求變更時應該如何處理
當需求發生變化時,不建議直接改寫當前 spec 的核心內容。
更穩妥的方式,是新建一份 spec,把新的範圍、設計、執行計劃和驗收標準完整寫清楚。
舊 spec 保留原樣,只追加一條變更記錄,說明它已經停止作為當前執行標準,並指向新的 spec。後續執行全部切換到新 spec。
這種處理方式有兩個優點:
- 歷史決策會被完整保留
- 當前執行標準始終清晰,不會出現多份文檔交叉生效的情況
回退時應該如何處理
如果某項改動需要回退,也應該納入同一套流程。
對於已經提交、已經聯調、已經上線,或者已經被外部驗證過的改動,回退應當被視為一次新的變更,並單獨創建一份 rollback spec。回退原因、影響範圍、執行步驟和回退後的驗收標準,都應寫在這份新文檔中。
代碼層優先使用 git revert。回退完成後,同樣要補充驗收證據,並在原 spec 中追加一條回退記錄,指向新的 rollback spec。
這樣做之後,團隊可以清楚回答這些問題:
- 為什麼回退
- 回退了哪些內容
- 回退後如何驗證
- 回退影響了哪些後續事項
Immutable Spec 能帶來什麼
採用 Immutable Spec 之後,團隊通常會獲得幾項明顯收益:
- 需求標準更加統一
- 設計、實現、驗收之間更容易對齊
- 每個事項都有清晰的完成條件
- 驗收證據和代碼歷史可以互相對應
- 歷史決策能夠被持續追溯
- 回退流程更容易制度化
更重要的是,團隊的溝通方式會發生變化。
討論不再依賴零散的口頭上下文,而是回到當前 active spec。完成結論也不再依賴主觀判斷,而是看驗收標準和證據是否已經補齊。
適合哪些場景
Immutable Spec 特別適合這些情況:
- 需求變化頻繁,但要求強追溯
- 工程任務跨越前端、後端、部署、聯調多個環節
- 事項完成後需要支持復盤和審計
- 希望把開發、驗收、上線、回退納入同一套規則
- 團隊希望減少對口頭同步的依賴
對於非常輕量、完全臨時性的探索任務,這套方法可能會顯得偏重。
但對於需要長期維護、多人協作、強調驗收質量的項目,它通常會帶來更高的穩定性和更低的協作成本。
結語
Immutable Spec 的核心價值,在於用一份清晰、可追溯、可執行的文檔,把需求、設計、執行、驗證和回退收斂到同一個坐標系中。
它要求團隊堅持幾條簡單規則:
- 一個需求對應一份 spec
- 一個時間點只保留一個
active spec - 一個事項對應一個 commit
- 一個完成結論對應一份證據
- 一次回退進入新的 spec 流程
這些約束會增加一定的前期紀律,但通常能顯著減少返工、誤解和歷史混亂。對於長期項目來說,這種收斂通常是值得的。