JAVASCRIPT V2 · BROWSER · 69
Browser DevTools:不要猜,直接看 Runtime Evidence
「畫面怪怪的」不是 diagnosis。Browser 同時包含 DOM、CSS、JavaScript runtime、storage、network 與 rendering。DevTools 的價值不是面板多,而是讓你回答:最後哪一步成功?第一個哪一步失敗?
Learning outcomes
- 依 symptom 選 Elements、Styles、Console、Sources、Network、Storage。
- 區分 source HTML 與 runtime DOM evidence。
- 讀懂 request URL、method、status、headers、body、timing。
- 用 breakpoint / call stack / scope 追 JavaScript state。
- 能建立 symptom → evidence → hypothesis → test → root cause 鏈。
1. Why now:前兩課建立了 pipeline,這一課學會把它拆開
User
↓ event
callback
↓ state
render()
↓ DOM
fetch()
↓ HTTP
API
任何一層失敗都可能最後只表現成「按鈕沒反應」或「資料沒出來」。Debug 的第一原則是不要從 symptom 直接跳到修正。
2. Elements:現在 live DOM 到底長什麼樣
Source:
<main id="app"></main>
Runtime JS:
app.innerHTML =
"<button>Save</button>";
View Source 可能只有空 main;Elements 則會看到 runtime 加上的 button。你要 debug 畫面,就應該看現在的 DOM,而不是只看原始檔。
3. Styles / Computed:Element 存在,不代表使用者看得到
.action {
display: block;
}
.hidden {
display: none;
}
Styles 告訴你哪些 selector 命中、哪些 declaration 被覆蓋;Computed 告訴你最終值。這比看到元素消失就補 !important 更可靠。
4. Console:Runtime value / type / exception 的第一站
const button =
document.querySelector("#save");
console.log({
button,
type: typeof button
});
Console 適合快速驗證 selector、state、function output 與 exception。但不要把 production secrets/token 印出來。
5. Sources:當問題不是一個 log 能看懂時,用 breakpoint
function handleSubmit(event) {
event.preventDefault();
const score =
Number(scoreInput.value);
saveStudent(score);
}
在 saveStudent(score) 前設 breakpoint,可以看 call stack、local variables、scope、目前 line。這對「值在哪一步變錯」尤其重要。
6. Network:Request / Response 的 protocol evidence
Request URL:
https://example.test/api/students
Method: GET
Status: 403
Response:
{"error":"forbidden"}
403 能證明 server 回了 forbidden response;不能單靠 status 就證明是哪個 RLS policy 或哪個 user identity 出錯。你還要繼續蒐集身份與 server/data evidence。
7. Worked Example A:Spinner 永遠轉
Console:
(no uncaught error)
Network:
GET /api/search?q=js
429 Too Many Requests
Retry-After: 30
第一個 failure evidence 在 HTTP response,不是 CSS。接著才問 UI 的 error state 為何沒有處理 429。
8. Worked Example B:Button 在 DOM,但看不到
Elements:
<button
id="save"
class="action hidden"
>
Save
</button>
Computed:
display: none
DOM evidence 證明 element 存在;CSS evidence 說明 presentation 把它隱藏。不要跳去查 API。
9. Worked Example C:資料成功回來但畫面仍舊
Network:
GET /api/students
200 OK
Response:
[{"name":"Amy","score":90}]
Console:
state.data.length === 1
Elements:
#students is empty
Network 與 state 都成功,第一個可疑 boundary 變成 render / DOM update。這就是「最後成功 / 第一失敗」方法。
10. Storage:確認 Browser-side persistence,而不是憑印象
localStorage:
gradeTrackerV1 = {...}
sessionStorage:
(empty)
Application/Storage panel 可以直接看 key/value。但 storage evidence 只證明 Browser storage 狀態,不代表 server database 有相同資料。
11. Timing:慢不等於 server 一定慢
Queueing 2 ms
DNS 18 ms
Connect 35 ms
TTFB 820 ms
Download 4 ms
如果 TTFB 很長,才比較像 server/upstream waiting;如果 DNS/connect 才長,方向不同。Performance/Network timing 的價值是把「很慢」分段。
12. Common mistakes
A. 一看到 API error 就改 frontend code
先看 request/status/body。
B. 一看到 element 不見就加 CSS
先確認 DOM 是否存在。
C. Console 沒 error就認為 JS 沒問題
Logic bug 可能完全不 throw。
D. 一次改五個地方再重新整理
你會失去哪個 hypothesis 被驗證的資訊。
13. Debug evidence workflow:固定六步
1. Reproduce
2. Classify layer
3. Collect evidence
4. Form hypothesis
5. Change one thing
6. Re-run same reproduction
修好後還要加 regression guard;否則你只是「目前看起來正常」。
14. Guided exercise:Selector Failure
const save =
document.querySelector(
"#save-course"
);
save.addEventListener(
"click",
handleSave
);
畫面其實只有 id="save"。請寫出你會開哪個 panel、要看到什麼 evidence、哪一行是 first failure、修正後如何驗證。
15. Independent exercise:三種 fault injection
在 Grade Tracker 故意製造:錯 selector、CSS display:none、API 404。每一個 incident 都記錄 symptom、第一個 panel、evidence、root cause、fix、retest。
16. Challenge:200 OK 但畫面資料錯
Network:
200 OK
{"score":90}
Console:
data.score === 90
Elements:
#score textContent = "0"
你不能再怪 network。設計最短的下一步 evidence chain 找出 render mapping 是否讀了錯 property、舊 state,或 render 根本沒跑。
Project checkpoint:Browser Incident Notebook
Incident #1
Symptom:
Evidence:
Last success:
First failure:
Hypothesis:
Fix:
Regression:
從這一課開始,Project checkpoint 不只保存「完成畫面」,還保存 debug evidence。後面的 Node、Linux、CI 都沿用同一 incident format。
17. Vocabulary / Summary
- live DOM:目前 runtime 的 document object tree。
- computed style:cascade/layout 後的最終 CSS value。
- breakpoint:暫停 execution 以檢視 runtime state。
- call stack:目前 function call chain。
- network waterfall:request 各階段 timing。
- evidence chain:支持 diagnosis 的可觀察事實序列。
18. Further reading
Knowledge check
- 說明 Elements 與 View Source 為何可能不同。
- CSS 覆蓋問題應蒐集哪些 evidence。
- HTTP 403 能證明與不能證明什麼。
- 解釋「最後成功 / 第一失敗」如何縮小 root cause。
- 完成頁面下方三個 Evidence Diagnostic incidents。