AI 改 Code 一直改 A 壞 B?Brownfield 專案的五步工作流¶
影片核心論點:「問題從來不是 AI 不夠強,而是你用它的方法錯了。」 在 Brownfield(既有)專案中,AI 必須先當「幫你讀專案的資深同事」,再當「照規矩施工的師傅」。順序不能反——先看懂,再動手。
目錄¶
- 1. 根因:Greenfield vs Brownfield
- 2. 兩種開發模式
- 3. 五步工作流總覽
- 4. 第一階段:看懂它(探索)
- 5. 第二階段:安全的動它(決策)
- 6. 完整走一次
- 7. 核心觀念與進階路線
- 8. Prompt 模板
- 參考資料
- 相關筆記
1. 根因:Greenfield vs Brownfield¶
兩種專案類型對比¶
| 維度 | Greenfield(綠地) | Brownfield(棕地) |
|---|---|---|
| 比喻 | 一塊什麼都沒有的空地 | 別人蓋好、已經有人住的房子 |
| 歷史包袱 | 無 | 既有 code、pattern、未解 bug、隱性相依性 |
| 架構決策權 | 完全自主 | 必須遵守既有規範 |
| AI 發揮空間 | 極高(「你叫它怎麼蓋,它就怎麼蓋」) | 受限(須遵守既有 pattern) |
| 典型場景 | 「用 AI 30 分鐘做一個 App」 | 進公司接手別人的 codebase |
為什麼教學派 vs 實戰派差這麼多¶
「用 AI 30 分鐘做一個 App」的教學影片全部都是 Greenfield 場景——沒有歷史包袱,AI 自由發揮。但日常工作中面對的是 Brownfield:在別人住的房子裡拆牆改管,還不能停水停電。
關鍵轉變:Greenfield 不會永遠是 Greenfield。Vibe Coding 狂寫一個月後,如果過程中沒有意識地維持架構乾淨,專案就已經變成 Brownfield 了——因為裡面大部分的 code 你根本沒讀過。
「改 A 壞 B」的標準翻車現場¶
場景:商品頁要加「庫存狀態篩選」功能
│
├─ 需求:"幫我加庫存狀態的篩選跟編輯功能"
│
├─ AI 不知道專案有 React Query pattern → 自己發明新寫法
├─ AI 不知道有共用 Table 元件 → 自己重刻一個
├─ AI 改了 useProducts hook 取資料 → 訂單頁也在用這個 hook
│
└─ 結果:商品頁修好了,訂單頁卻爆了
根因:把一個從沒進過你家的裝潢師傅一個人丟進廚房,叫他直接搞個流理台出來,完全沒先說設計風格與裝潢理念。AI 手藝再好,不認識這棟房子的管線,一鎚子下去就可能出事。
2. 兩種開發模式¶
在進入五步驟前,根據「對 AI 的信任度」與「使用的工具」選擇走法:
| 模式 | 主導權 | 適合人群 | 工具 | 特點 |
|---|---|---|---|---|
| 模式 A:AI 輔助開發 | 在人手上 | 網頁版 AI 使用者、對 AI 仍觀望者 | ChatGPT / Claude 網頁版 | 人親自走進每個房間,AI 是放大鏡 |
| 模式 B:純指揮 Agent | 在 AI 手上 | Claude Code / Cursor 用戶 | Coding Agent | 只出一張嘴,Agent 自己探勘、回報 |
對 AI 的信任度 / 工具能力
低 ◄──────────────────────────► 高
│ │
模式 A 模式 B
AI 輔助開發 純指揮 Agent
(人主動搜尋、貼 code) (Agent 全域讀取)
│ │
└──────── 第一、二步分岔 ────────┘
│
第三步起合流
(決策活沒有外包版)
│
第五步再分岔
(勞力活可以外包)
選擇原則:沒有標準答案,取決於你對 AI 的熟練度跟信任度、以及你使用的工具能力。隨著 AI 越強,所有步驟會越來越往「純指揮」收斂。
3. 五步工作流總覽¶
整套流程拆成兩大階段,核心區別是「勞力活 vs 決策活」:
┌─────────────────────────────────────────────────┐
│ Brownfield AI 開發五步工作流 │
├─────────────────────────────────────────────────┤
│ │
│ 第一階段:看懂它(探索 / 勞力活 / 可外包) │
│ ┌──────────────────────┐ ┌──────────────────┐ │
│ │ 步驟 1 │ │ 步驟 2 │ │
│ │ 定位 UI → 元件檔案 │ │ 梳理 Dataflow │ │
│ │ DevTools + 全域搜尋 │ │ 狀態管理 + 邊界 │ │
│ └──────────────────────┘ └──────────────────┘ │
│ ▼ │
│ 第二階段:安全的動它(決策 / 必須人為把關) │
│ ┌──────────────────────┐ ┌──────────────────┐ │
│ │ 步驟 3 │ │ 步驟 4 │ │
│ │ Guardrails 規範需求 │ │ 拆解任務 + Review │ │
│ │ 帶邊界的指令 │ │ 小步迭代 │ │
│ └──────────────────────┘ └──────────────────┘ │
│ ▼ │
│ ┌──────────────────────────────────────────┐ │
│ │ 步驟 5:測試驗證 + 回歸檢查 │ │
│ │ 跑既有測試 / 看懂 Error Log / Regression │ │
│ └──────────────────────────────────────────┘ │
└─────────────────────────────────────────────────┘
勞力活 vs 決策活:外包界線¶
| 活的類型 | 本質 | 可否外包 | 對應步驟 |
|---|---|---|---|
| 勞力活 | 讀 code、找檔案、追資料流 | 可外包(信任度決定外包程度) | 步驟 1、2、5 |
| 決策活 | 決定什麼不能動、判定 code 夠不夠格 | 不可外包,AI 只能起草 | 步驟 3、4 |
「改壞了之後,被 QA 找麻煩的是你,隔天踩到地雷的也是你,不是它。」
4. 第一階段:看懂它(探索)¶
步驟 1:定位 UI 畫面對應的元件檔案 [05:19]¶
目標:搞清楚畫面上這一塊到底長在哪個檔案裡,建立「地圖」,辨識哪些是全站共用資產。
做法:AI 輔助模式¶
1. 瀏覽器 DevTools → 對目標區塊右鍵「檢查」
2. 找出一個獨特特徵:
- 特殊 class name
- 按鈕文字
- 測試標籤(data-testid)
3. 回編輯器「全域搜尋」這個特徵
4. 定位渲染該畫面的檔案
5. 把檔案丟給 AI 分析
Prompt(AI 輔助):
這是負責商品頁的檔案。幫我分析這個畫面的結構:
- 它引入了哪些子元件,各自負責渲染什麼?
- 有沒有哪些看起來是全站共用,而不是這頁專屬的元件?
⚠️ 只分析,不要修改任何 code
做法:純指揮 Agent 模式¶
畫面上商品列表這一塊,是哪個檔案在渲染的?幫我找出來。
分析它的元件結構,標出哪些子元件是全站共用的。
⚠️ 這個階段只做分析就好,不要改任何 code
共通原則:嚴禁此階段修改 code¶
兩條路的 Prompt 結尾都是「只分析,不要改」。這一步的價值是把「我怕改壞」的恐懼,變成一張看得見的地圖——你會清楚知道: - 自己現在站在這棟房子的哪個房間 - 哪些元件是全站共用資產(可以重用,絕對不能亂改) - 同步讓你和 AI 都認識這個專案
步驟 2:梳理資料流(Dataflow)與相依性 [06:42]¶
目標:搞清楚資料從哪裡來、存在哪裡、怎麼被改動。前端最容易出事的地方從來不是畫面,而是資料。
做法:AI 輔助模式¶
1. 打開 package.json → 確認狀態管理工具(Redux / Zustand / React Query)
2. 找對應的 store 或 hooks 資料夾
3. 回到畫面元件,找出觸發資料變動的動作(dispatch / mutate / setState)
4. 把畫面元件 + 狀態檔案一起丟給 AI
Prompt(AI 輔助):
我會給你商品頁的檔案,還有這個 hook 檔案。
請用白話文解釋這條 data flow:
- 商品列表的資料是從哪個 API 來的?用哪套工具在管?
- 當管理員編輯庫存時,資料是怎麼從畫面流回 server 的?
把中間經過的 function 依序列出來。
📌 請特別標出:這個 hook 有沒有被商品頁以外的地方用到?
網頁版 AI 的限制:看不到整個專案,所以要先在編輯器「全域搜尋」這個 hook,把搜到的檔案一起貼給它,它才答得出「誰還在用」。
做法:純指揮 Agent 模式¶
幫我梳理商品頁的 data flow:
- 商品列表的資料是從哪個 API 來的?用哪一套工具在管理?
- 當管理員編輯庫存時,資料是怎麼從畫面流回 server 的?
把中間經過的 function 依序列出來。
- 另外,商品資料那個 hook,有沒有被商品頁以外的地方用到?
Agent 讀得到整個 codebase,「還有誰在用」這一題直接就能答。
進階技巧:架構導覽圖 [08:18]¶
探勘做完後,補一句 Prompt:
把你剛剛探勘到的結果做成一頁 HTML:
- 這個專案的頁面結構
- 共用元件
- data flow
畫成一張架構導覽圖,我要直接用瀏覽器打開來看。
幾分鐘後就會拿到一張「建築藍圖」——哪些元件是共用的、資料從哪裡流到哪裡、哪一根水管後面接著別的頁面,一目了然。
5. 第二階段:安全的動它(決策)¶
從第三步開始,AI 輔助跟純指揮 Agent 兩條路合流。因為前面兩步是勞力活(可以外包),但接下來是決策活——決定什麼東西絕對不准動、判定一段改動夠不夠格進這個 codebase。決策活沒有外包版。
步驟 3:帶有邊界與規範的需求指令(Guardrails) [09:18]¶
這是 Brownfield 跟 Greenfield 差最多的地方。 你給 AI 的不能是一個空需求,必須是一個帶著既有規則的需求。
❌ 錯誤做法(空需求)¶
幫我加一個庫存篩選
✅ 正確做法(帶 Guardrails)¶
請在既有的商品頁新增庫存狀態篩選,並讓管理員可以編輯庫存。
動手前,先讀:
- 負責商品資料的 hook
- 共用元件資料夾
- 型別定義檔
要求:
- 沿用專案既有的 React Query pattern
- 重用現成的 Table、Modal、Select 元件
- 只准用 Tailwind
🚫 絕對不要動到:
- 全域的 routing
- 權限控管
- 任何被商品頁以外用到的共用 hook
「絕對不要動」那句話,就是把前半場看懂的東西變成 AI 的 guardrail。
Brownfield 的 Clean Code 觀念 [10:08]¶
很多人搞錯 Clean Code 的定義:
| 觀念 | Greenfield | Brownfield |
|---|---|---|
| Clean Code | 自己覺得漂亮的寫法 | 跟前人一致的寫法 |
在 Brownfield 裡,所謂的 Clean Code 不是你自己覺得很漂亮的寫法,而是跟前人一致的寫法。所以 Guardrails 第一條永遠是:照著這個專案原本的樣子寫。沿用前人的 coding style,本身就是最高優先的 Clean Code。
步驟 4:拆解任務、小步迭代與 Code Review [10:28]¶
不要讓 AI 一次生出整個功能,拆成小步,每一步都親自 Review。
拆解順序¶
1. 先叫它只提出「元件結構跟資料流的規劃」
└─ 先不要寫 code,等你確認方向對了
2. 再讓它只去改那個商品資料的 hook
└─ 加上庫存篩選的參數,改完你 Review
3. 再讓它做篩選的畫面
└─ Review
4. 最後才做編輯庫存的彈出視窗
└─ Review
Brownfield Review 的專屬重點¶
跟 Greenfield 不一樣,你不是只看有沒有 bug:
| Review 項目 | 問題 |
|---|---|
| 一致性 | 命名習慣、資料夾結構、抓資料放的位置跟前人一不一致? |
| 共用檔案 | 有沒有偷偷改到共用的檔案? |
| 重複造輪子 | 有沒有自己又刻了一個其實早就存在的元件? |
讓 AI 當第一道防線:
用資深前端工程師的角度,幫我 Review 這段改動:
- 它有沒有偏離專案既有的 React Query 寫法?
- 有沒有動到共用元件?
- 有沒有漏掉 loading 跟 error 的狀態處理?
但記住:AI 的 Review 是初審,終審永遠是你。 在 production 環境下,除非你已經很熟悉這套 codebase,或者這套 codebase 已經有很好的 harness 跟 context 管理,否則重要決策建議都先不要外包給 agent。
步驟 5:測試驗證與回歸檢查(Regression Check) [11:41]¶
回答影片一開始纏著你的恐懼:我改的東西,到底有沒有弄壞別人的功能? 到了這一步,勞力活回來了,所以兩條路又分岔。拆成三個部分:
5-1. 跑專案本來就有的測試 [11:52]¶
很多人完全忘記專案裡其實早就有一整套的測試——這是最快、最省力確認有沒有壞到既有功能的方法。
| 模式 | 做法 |
|---|---|
| AI 輔助 | 動手前自己跑一次(確認綠燈)→ 動完手再跑一次 |
| 純指揮 | 動手前先跑一次專案既有的測試,跟我回報結果,之後每完成一小塊改動就再跑一次 |
如果你的專案根本沒有測試,那現在就是叫 AI 幫你補幾條關鍵測試的最好時機。
5-2. 看懂別人的 Error Log(部落知識)[12:28]¶
Brownfield 有一個經典的坑:很多專案有自己一套包裝過的錯誤紀錄機制(custom error logging)——可能是包裝過的 logger、一組統一的 error code、或固定要送去某個後台的格式。在公司裡這叫做部落知識(老鳥都懂,但沒有寫在任何文件裡)。
錯誤機制可能是:
├─ 包裝過的 Logger
├─ 統一的 error code
└─ 固定要送去某個後台的格式
Prompt:
這個專案有自己的錯誤紀錄機制。讀一下負責這件事的 logger 檔案,
然後告訴我三件事:
1. 錯誤最後被送到哪裡?
2. 一筆 log 長什麼樣子?
3. 有沒有規定一定要帶哪些欄位?
然後示範一次:如果我這次的庫存編輯功能要沿用同一套 logging,
我該怎麼寫?
後果對比:
❌ 隨手 console.error
→ 上線後根本不會被任何人看到
→ Debug 時找不到線索
✅ 照專案既有格式 + errorCode + metadata
→ 乖乖出現在該出現的地方
→ Debug 才找得到線索
注意:AI 幫你生 side project 時也常順手建了一套 error handling,你根本不知道它存在。結果你後來隨手寫的 console.error,根本沒有進到那個系統裡。
5-3. 回歸檢查(Regression Check)[13:36]¶
直接對付「訂單頁掛掉」事件的一招。
| 模式 | 做法 |
|---|---|
| AI 輔助 | 拿著前半場 AI 標出的「hook 還被誰用到」清單,一個一個回頭驗 |
| 純指揮 | 見下方 Prompt |
Prompt(純指揮):
我動了商品資料的 hook。
列出專案裡所有用到它的地方,逐一確認我的改動有沒有改變它原本的行為:
- 回傳的型別
- 參數
- 預設值
有沒有變?
如果既有的測試有覆蓋到這些地方,告訴我該跑哪幾個。
這一句話,就是你跟「改 A 壞 B」這件事的正式和解。
6. 完整走一次 [14:15]¶
把整條線套回開頭那個商品頁的任務:
❌ 之前的做法
└─ "幫我加個庫存篩選跟編輯"(空需求)
→ 改 A 壞 B
✅ 五步工作流
1. 分清楚這是 Brownfield
└─ 知道自己是在別人的房子裡改廚房
2. 選好你的路
├─ 自己拿著放大鏡逐間看房(AI 輔助)
└─ 指揮 agent 幫你畫出建築藍圖(純指揮)
→ 都拿到了那張地圖,標出那根危險的共用水管
3. 把既有的規矩(包含 coding style)
寫成規格跟 guardrail
4. 讓 AI 一小塊一小塊的寫
→ 每一塊都用資深的眼光親自 Review
5. 用既有的測試、看懂的 log、回歸檢查
客觀證明你這次沒有弄壞任何人的東西
同一個需求,同一個 AI,差別只在於你這次是先看懂,再動手,而不是閉著眼睛把整包 code 直接丟給它。
7. 核心觀念與進階路線¶
三條核心行動建議¶
| 原則 | 說明 |
|---|---|
| 嚴格執行 Prompt 限制 | 修改前務必加上「只分析不修改」或「絕對不可以修改 shared components」等 Guardrail 邊界指令 |
| 注重專案 Consistency | 在舊專案中,最好的 Clean Code 就是「與前人寫法保持一致的程式碼」 |
| 逐步建立 Harness 與 Context 管理 | 從初階 Vibe Coder 晉升為具備系統化掌控力的 Agentic Engineer 的關鍵里程碑 |
AI 越強,流程越往純指揮收斂¶
現在
├─ 步驟 1-2:AI 輔助 ◄──┐
│ vs 純指揮 │ 兩條路
└─ 步驟 5:AI 輔助 ◄──┘
未來(AI 更強)
└─ 全部往純指揮收斂
└─ 總有一天不會再有人手動貼檔案給 AI
身為 AI 原生工作者,很重要的能力之一就是:在被丟進一棟完全陌生的專案裡時,你要知道自己現在需要 agent 幫你探索,並帶著你理解,而不是直接擼起袖子幹活。
進階路線:Harness 與 Context 管理¶
如果你在開啟一個新專案時就已經有很好的 harness 跟 context 管理,那這些問題都不存在——真的只需要出一張嘴就好了。有能力搭建專案的架構、做好 context 管理,是 Vibe Coder 晉升 Agentic Engineer 的關鍵里程碑之一。
8. Prompt 模板¶
以下模板可直接複用,以「商品頁加庫存篩選」為例。
步驟 1:定位元件¶
[AI 輔助]
這是負責 {頁面} 的檔案。幫我分析這個畫面的結構:
- 它引入了哪些子元件,各自負責渲染什麼?
- 有沒有哪些看起來是全站共用,而不是這頁專屬的元件?
只分析,不要修改任何 code。
[純指揮]
畫面上 {區塊描述} 是哪個檔案在渲染的?幫我找出來。
分析它的元件結構,標出哪些子元件是全站共用的。
這個階段只做分析就好,不要改任何 code。
步驟 2:梳理 Dataflow¶
[純指揮]
幫我梳理 {頁面} 的 data flow:
- {資料} 是從哪個 API 來的?用哪一套工具在管理?
- 當 {角色} {動作} 時,資料是怎麼從畫面流回 server 的?
把中間經過的 function 依序列出來。
- {資料 hook} 有沒有被 {頁面} 以外的地方用到?
步驟 3:Guardrails 需求¶
請在既有的 {頁面} 新增 {功能描述}。
動手前,先讀:
- {負責資料的 hook}
- 共用元件資料夾
- 型別定義檔
要求:
- 沿用專案既有的 {pattern}
- 重用現成的 {元件清單}
- {其他規範,如 styling 工具}
🚫 絕對不要動到:
- 全域的 routing
- 權限控管
- 任何被 {頁面} 以外用到的共用 hook
步驟 4:Review¶
用資深前端工程師的角度,幫我 Review 這段改動:
- 它有沒有偏離專案既有的 {pattern} 寫法?
- 有沒有動到共用元件?
- 有沒有漏掉 loading 跟 error 的狀態處理?
步驟 5-3:回歸檢查¶
我動了 {hook 名稱}。
列出專案裡所有用到它的地方,逐一確認我的改動有沒有改變它原本的行為:
- 回傳的型別
- 參數
- 預設值
有沒有變?
如果既有的測試有覆蓋到這些地方,告訴我該跑哪幾個。
參考資料¶
- 影片:AI 改 code 一直改 A 壞 B?你缺的是這五個步驟 — Gary Chen
- 完整文章與 Prompt 模板:Patreon(付費)
- 相關工具:Claude Code、Cursor
相關筆記¶
- [[AI Coding 工作流]]
- [[Vibe Coding 實踐筆記]]
- [[Guardrails 設計原則]]
- [[Code Review Checklist]]