
Day 12 把需求寫成可判定 PASS / FAIL 的驗收條件(Acceptance Criteria,AC),Day 13 再把一條使用者旅程(User Journey)拆成責任與觀察點。
接著還有一個問題:
今天人工驗過的規則,下次 AI 再改別的功能時,誰還記得?
如果答案是「到時候再重測一次」,那這些規則仍然主要存在人的腦袋裡。
值得留下來的測試,是把已確認的業務規則(Business Rule)保存成未來仍可重跑的回歸契約(Regression Contract)。
這對 Vibe Coding 特別重要。AI 讓修改變快,也讓一次碰很多檔案、很多流程變得容易;系統若沒有同樣可重跑的記憶,舊規則就更容易在下一次修改時被忘掉。
代點餐(delegated ordering)很適合拿來看這件事。
前兩天已經確認幾條規則:
targetUserId 替別人下單;Day 14 不再重講身份邊界,而是問:
這些規則下一次被碰到時,會不會自己跳出來提醒我們?
真實 repo 的 orders-delegated.test.js 留下了幾個直接對應業務規則的 case:
targetUserId 時回傳 403,而且 target 名下不會新增訂單;這些 case 不是為了把測試數量堆高。
它們記住的是:
可以替別人操作
≠
取得對方資料的 ownership
只測成功路徑(happy path)很容易得到:
Admin 選一個人
→ 建立訂單成功
→ API 回 200
這只能證明功能能跑。
repo 裡另有一條 regression 專門驗:
Given 一般 User
When request 偷帶 targetUserId
Then 403 DELEGATED_ORDER_FORBIDDEN
And target 名下訂單數仍是 0
這裡同時驗了「被拒絕」和「拒絕後沒有副作用」。
如果只看 status code,未來某次 refactor 仍可能發生:
資料先寫入
→ 後面才判定失敗
→ 畫面顯示錯誤
→ DB 卻已被改動
所以重要規則不能只驗回應訊息,還要驗不該留下的狀態真的沒有留下。
Day 12 的 AC 描述「什麼叫做做對」。
Day 14 再問下一題:
這個 Test 到底替哪條 Business Rule 看門?
例如:
AC
一般 User 不得替其他人建立 delegated order
Regression Contract
- forged targetUserId → 403
- target order count 不增加
餘額規則也是同樣邏輯:create / cancel 都作用在 target,actor balance 必須保持不變。
如果一個 Test 說不出自己保護哪條 Business Rule,它很可能只是在固定當下的實作細節。

AI 很會生成測試。
輸入 Component、function 或 endpoint,很快就能補出一批 case;但生成成本降低,也代表無意義測試同樣變便宜。
便當系統有一個很具體的 UI regression。
delegated order 成功後,Worker 已回傳最新的 newBalance。畫面可以立刻更新被代點成員的餘額,但管理頁另外還有一份 member balance cache。
如果只更新眼前畫面,餘額管理列表仍可能保留舊值。
delegated-order-ui.test.cjs 把這次踩坑留下來:
member balance cache = 0
delegated response.newBalance = -100
↓
delegated banner 立即顯示 -100
↓
member balance cache 標記失效
↓
再次進入餘額管理
↓
重新向 API 讀取
↓
列表顯示 -100
這個 Test 保護的不是某一行 React state code。
它保護的是一條資料規則:
當前畫面可以使用 mutation 回傳的新值立即更新;其他舊快取不能假裝自己仍是最新資料,必須失效後重新讀取。
這就比「某個 setter 有沒有被呼叫」更值得成為長期 regression。
面對 AI 一次生成很多測試,我會再問第二題:
如果實作換掉,這個 Test 還有沒有意義?
未來即使:
只要 Business Rule 沒變,重要的 regression 應該還能表達同一個契約。
實務上不可能全部都是黑箱測試。某些前端 wiring 仍會需要 source-level regression。
但就算是 source-level test,也應該先知道它保護的行為是什麼,而不是把目前程式碼長相本身當成需求。
還有一種記憶不是業務規則,而是「修改前的系統狀態」。
如果 Repository 原本就有已知 failure,AI 改完看到紅字時,不能直接判定是這次改壞;反過來,也不能把所有新紅字都丟進「本來就壞」這個桶子。
最少要能比較:
Before
- 哪些檢查原本 PASS
- 哪些 failure 原本就存在
After
- 是否多出新的 failure
- 原本 failure 是否維持同一型態
這讓 Regression 不只保存規則,也保留「這次修改前的基準線」。
Regression 會有成本:
所以判斷標準不是「發生過就全部寫進測試」。
比較值得留下來的,通常是:
偶發、無法重現,或只屬於一次性資料修復的事件,不一定值得永久加入 suite。
Vibe Coding 大幅降低修改成本,但這也讓「每次改完要留下什麼」更重要。
這篇可以帶走的流程很短:
Incident / Requirement
↓
Acceptance Criteria
↓
找出容易再次被破壞的 Business Rule
↓
寫成 Regression Contract
↓
驗結果 + side effect + data ownership
↓
未來修改時重跑
Patch 解決這一次。
Regression 讓下一次不用再付同一筆學費。
下一篇會處理另一個問題:當 Test、UI 或 Production 現象真的告訴你「有問題」,要怎麼用 Evidence 縮小 fault domain,而不是從整個 Repository 開始猜。
這是一套持續開發中的便當訂購系統。文章著重「為什麼」,GitHub 保留實際程式碼、測試與演進紀錄。
這篇主要核對:
worker-poc/tests/orders-delegated.test.js:delegated authority、target eligibility、target-owned order / balance 與 forbidden side effect;tests/delegated-order-ui.test.cjs:authoritative newBalance、member-balance cache invalidation 與再次讀取;CHANGELOG.md:v0.14.0 delegated ordering 與 v0.14.1 balance refresh follow-up。GitHub:https://github.com/henryfir456/bento-order-app