簡介
目前,作者可以使用許多抽象概念來建構網路應用程式。許多作者並未直接與 Web 平台提供的低階 API 介接,而是利用架構、建構工具和編譯器,從更高層級的角度編寫應用程式。
舉例來說,以 Angular 架構為基礎建構的元件會使用 TypeScript 和 HTML 範本編寫。在幕後,Angular CLI 和 webpack 會將所有內容編譯為 JavaScript,並轉換為所謂的套件,然後運送至瀏覽器。
在 DevTools 中偵錯或分析網頁應用程式時,您目前會看到並偵錯這個已編譯的程式碼版本,而不是實際編寫的程式碼。不過,這並不是作者想要的結果:
- 您不想對壓縮過的 JavaScript 程式碼進行偵錯,而是想對原始 JavaScript 程式碼進行偵錯。
- 使用 TypeScript 時,您不想對 JavaScript 進行偵錯,而是要對原始的 TypeScript 程式碼進行偵錯。
- 使用 Angular、Lit 或 JSX 等範本時,您不一定需要對產生的 DOM 進行偵錯。您可能需要對元件本身進行偵錯。
總體而言,您可能會在編寫程式碼時對其進行偵錯。
雖然原始碼對照圖已在某種程度上縮小了這項差距,但 Chrome 開發人員工具和生態系統仍可在這方面做得更多。
現在就來看看兩者的不同之處!
編寫程式碼與部署程式碼
目前,在「Sources」面板中瀏覽檔案樹狀結構時,您會看到已編譯 (通常是經過精簡) 的bundle內容。這些是瀏覽器下載及執行的實際檔案。開發人員工具稱之為「已部署的程式碼」。
這麼做不太方便,而且通常很難掌握。作者想要查看及偵錯自己編寫的程式碼,而不是已部署的程式碼。
為彌補這項缺失,您現在可以讓樹狀圖改為顯示已編寫的程式碼。這樣一來,樹狀結構就會更接近您在 IDE 中看到的來源檔案,而且這些檔案現在已與「已部署的程式碼」分開。
如要在 Chrome 開發人員工具中啟用這個選項,請依序前往「Settings」 >「Experiments」,然後勾選「Group sources into Authored and Deployed trees」。
「Just my code」
使用依附元件或在架構上進行建構時,第三方檔案可能會造成干擾。您通常只想查看自己的程式碼,而非 node_modules
資料夾中隱藏的第三方程式庫。
為彌補這項缺點,開發人員工具預設會啟用額外設定:「自動新增已知的第三方指令碼以忽略清單」。您可以依序前往「開發人員工具」 >「設定」 >「忽略清單」。
啟用這項設定後,DevTools 會隱藏架構或建構工具標示為要忽略的任何檔案或資料夾。
自 Angular 14.1.0 版起,node_modules
和 webpack
資料夾的內容已標示為此類內容。因此,這些資料夾、其中的檔案和其他類似的第三方構件不會顯示在 DevTools 的各個位置。
作者無須採取任何行動,即可啟用這項新功能。這項變更的實作方式取決於架構。
在堆疊追蹤中忽略清單中的程式碼
這些檔案不會再顯示在堆疊追蹤記錄中。作者現在可以查看更多相關的堆疊追蹤記錄。
如要查看堆疊追蹤記錄的所有呼叫框架,請隨時按一下「Show more frames」連結。
偵錯及逐步執行程式碼時,您看到的呼叫堆疊也適用相同的做法。當架構或 bundler 向 DevTools 提供第三方指令碼資訊時,DevTools 會自動隱藏所有不相關的呼叫框架,並在逐步偵錯時跳過所有已列入忽略清單的程式碼。
檔案樹狀結構中的忽略清單程式碼
如要在「Sources」面板的「Authored Code」檔案樹狀檢視畫面中隱藏已忽略的檔案和資料夾,請在 DevTools 中依序前往「Settings」 >「Experiments」,然後勾選「Hide ignore-listed code in sources tree view」。
在 Angular 範例專案中,node_modules
和 webpack
資料夾現在已隱藏。
「快速開啟」選單中的忽略清單程式碼
已列入忽略清單的程式碼不僅會從檔案樹狀結構中隱藏,也會從「快速開啟」選單中隱藏 (Control + P (Linux/Windows) 或 Command + P (Mac))。
進一步改善堆疊追蹤
除了相關堆疊追蹤,Chrome 開發人員工具還針對堆疊追蹤進行了更多改善。
已連結的堆疊追蹤
當部分作業排定為非同步執行時,DevTools 中的堆疊追蹤目前只能提供部分資訊。
舉例來說,以下是假設 framework.js
檔案中的簡易排程器:
function makeScheduler() {
const tasks = [];
return {
schedule(f) {
tasks.push({ f });
},
work() {
while (tasks.length) {
const { f } = tasks.shift();
f();
}
},
};
}
const scheduler = makeScheduler();
function loop() {
scheduler.work();
requestAnimationFrame(loop);
};
loop();
… 以及開發人員如何在 example.js
檔案中使用自家程式碼:
function someTask() {
console.trace("done!");
}
function businessLogic() {
scheduler.schedule(someTask);
}
businessLogic();
在 someTask
方法中加入中斷點,或檢查控制台中顯示的追蹤記錄時,您不會看到任何與此作業的「根本原因」相關的 businessLogic()
呼叫。
您只會看到導致工作執行的架構排程邏輯,堆疊追蹤中不會顯示麵包屑,因此無法協助您找出導致這項工作的事件之間的因果關係。
多虧「非同步堆疊標記」這項新功能,我們可以將非同步程式碼的兩個部分連結在一起,進而完整呈現整個情況。
非同步堆疊標記 API 推出了名為 console.createTask()
的新 console
方法。API 簽名如下:
interface Console {
createTask(name: string): Task;
}
interface Task {
run<T>(f: () => T): T;
}
console.createTask()
呼叫會傳回 Task
例項,您之後可以使用該例項執行工作內容 f
。
// Task Creation
const task = console.createTask(name);
// Task Execution
task.run(f);
任務會在建立的背景與執行中的非同步函式之間建立連結。
套用至上述 makeScheduler
函式後,程式碼會變成以下內容:
function makeScheduler() {
const tasks = [];
return {
schedule(f) {
const task = console.createTask(f.name);
tasks.push({ task, f });
},
work() {
while (tasks.length) {
const { task, f } = tasks.shift();
task.run(f); // instead of f();
}
},
};
}
因此,Chrome 開發人員工具現在可以顯示更完善的堆疊追蹤。
請注意,businessLogic()
現已納入堆疊追蹤中!不僅如此,工作名稱也改為熟悉的 someTask
,而非先前的一般 requestAnimationFrame
。
友善呼叫框
建構專案時,架構通常會從各種範本語言產生程式碼,例如 Angular 或 JSX 範本,可將看起來像 HTML 的程式碼轉換為純 JavaScript,最終在瀏覽器中執行。有時,這類產生的函式會以不太友善的名稱命名,例如經過精簡後的單字母名稱,或是不太友善或不熟悉的名稱。
在範例專案中,您會在堆疊追蹤中看到 AppComponent_Template_app_button_handleClick_1_listener
的例子。
為解決這個問題,Chrome 開發人員工具現在支援透過原始碼對照圖重新命名這些函式。如果來源對應圖包含函式範圍開頭的名稱項目,呼叫框架應會在堆疊追蹤中顯示該名稱。
作者無須採取任何行動,即可啟用這項新功能。這項變更的實作方式取決於架構。
展望未來
有了這篇文章中所述的新增功能,Chrome 開發人員工具就能提供更優質的偵錯體驗。團隊還想探索更多領域。特別是如何改善開發人員工具中的分析體驗。
Chrome 開發人員工具團隊鼓勵架構作者採用這些新功能。個案研究:使用開發人員工具進行更完善的 Angular 偵錯作業提供實作方式的相關指南。