Chrome DevTools 的 Sources 調試


在 Chrome 中調試 JS 代碼,那你不得不與 Chrome DevTools 的 Sources 面板打交道,所以文章主要通過介紹 Sources 面板上的各部分功能來介紹如何調試網頁中的 JS。

熟悉 Sources 面板

先來認識一下 Sources 面板(以我的 Github 首頁舉例)。

可以看到面板被分為左中右三個部分,左邊是文件導航,中間是文件的具體內容,右邊可以統稱為調試面板。整個面板就像一個 IDE,所以還是挺親切的。

左邊的文件導航面板包含 3 個面板:,分別是:

  • Sources:這個面板很好理解,展示了網頁所用到的所有文件

  • Content scripts:Content scripts 指的是 Chrome 拓展注入在網頁中的腳本。比如我安裝了一個叫 JSONView 的 Chrome 拓展,打開我的 Content scripts 面板會看到:

  • Snippets:Snippets 的含義是片段,在這里指的是一小段程序,這個一小段程序跟在其他地方不一樣的是,可以訪問這個頁面中的變量和函數等。

中間面板的其他操作都比較顯而易見,只是有 4 點需要簡單提一下。

標記 1、2 處可以隱藏/展開左右兩個面板,標記 3 處格式化代碼,使得代碼變得易於閱讀,當代碼被壓縮時尤其有用。另外需要提一下的是打開文件的快捷方式,可以用 Cmd + p / Ctrl + p 在任何一個功能面板上搜索一個文件,按 enter 鍵在 Sources 面板上打開。

右邊的調試面板比較復雜,需要借助調試的例子來解釋作用。不過我們可以先大概熟悉一下:

右側的面板為上下結構,上面是一組功能按鈕,下面由很多面板組成,這些面板中,看名字大概能知道第二個顯示的是調用棧,從四個開始就是各種類型的斷點。那真相是什么呢?我們下面結合調試實例來解釋這些按鈕/面板的功能。

添加斷點與斷點類型

本文用到的測試代碼為自己所寫的 Demo。

添加斷點

打開一個文件,中間的面板中顯示了代碼,代碼的左側有代碼行號,代碼行號所在的位置叫做行號槽,點擊行號槽,為相應的行添加斷點,並在相應的行號上面加上一個類似肩章的五邊形圖標。特別提一下的是,這個圖標的顏色是藍色的。如下:

另外,如果一條語句由多行組成,如果在這條語句的行中添加斷點的話,那么斷點將會被加到下一條語句。舉例如下:

在上面的代碼中,你可以在 13 行添加斷點,但如果你想在 14-17 行添加斷點的話,那么斷點將會被添加到 19 行。另外,你也不能為空行添加斷點,那也會被添加到下一條語句上。比如你想在 18 行添加斷點,但實際會被添加到 19 行。

條件斷點

右鍵一個沒有添加斷點的行號,選擇 "Add conditional breakpoint",輸入你的條件,當條件滿足時,斷點才會生效。回車后,效果如下:

可以看見,條件斷點跟一般斷點的區別就是顏色變成了黃色。

行內斷點

之前有人在評論里問,為什么我的這個系列文章要加一個 v57 這個前提,行內斷點就是一個很好的回答。行內斷點是從 Chrome(v55) 才有的一個功能,意思是你可以在一行內添加多個斷點。看下面的例子:

跟前面添加斷點方式一樣,我先在 15 行添加了一個斷點,當程序中斷在 15 行時,出現了上圖的例子。但與一般的例子不同的是,上面有 3 處標紅的位置,表示 3 處斷點。但第 1 個斷點跟后 2 個不一樣的是,第 1 個斷點是默認處於激活狀態,而后 2 個則不是,只有點擊激活后才能生效。

斷點的其他操作

  • 忽略:如果你想暫時忽略某個斷點,右鍵斷點,選擇 "Disable breakpoint"
  • 修改:修改斷點生效的條件。你可以將一個非條件斷點通過這個方式修改成條件斷點,也可以將條件斷點變成非條件斷點
  • 刪除:你可以直接點擊斷點,或者右鍵 "Remove breakpoint"

黑盒腳本

右鍵行號槽的時候,第一個選項總是:"Blackbox Script"。

那什么是黑盒腳本呢?

我們寫項目時,很多時候是要引用第三方庫或框架的,當我們調試時,調試的對象應該是我們自己寫的代碼,但很多時候,我們經常在焦灼地進行下一步下一步時,突然代碼跳到了第三方庫或框架的源碼上去,這讓我們焦灼的內心更添了一把柴火。黑盒腳本就是用來解決這個問題的。它能夠將一個腳本文件標記為 "Blackbox Script",那么我們就永遠不可能進入這個文件內部,這個文件對我們來講就是一個黑盒子。為什么要強調“永遠”呢?因為不僅普通的斷點不能訪問這個被標記了的腳本,其他的,比如說 DOM 斷點、事件斷點等等都無法訪問那個腳本文件內部。

面板介紹 -- Breakpoints

這個面板會顯示你所有的通過行號留下的斷點。你可以右鍵管理某個或全部斷點:

  • Remove Breakpoints:刪除選中的斷點
  • Deactivate Breakpoints:暫時忽略所有斷點
  • Disable all Breakpoints:功能同上(與上一功能有細微差別,但表現類似)
  • Remove all Breakpoints:刪除所有斷點

除了普通的中斷類型,我們下面再介紹幾款其他類型的。

面板介紹 -- DOM Breakpoints

在 Elements 面板,右鍵 body 元素,插入 "attribute modifications breakpoint",在 Sources 面板中顯示如下:

查看 DOM 斷點的詳細信息請查看另一篇博客:Elements

面板介紹 -- XHR Breakpoints

XHR 斷點跟 DOM 斷點很類似,通過 XHR 斷點可以很容易的找到 ajax 調用的觸發點和調用堆棧。最新的 Chrome DevTools 中要么為所有 ajax 調用添加斷點,要么都不添加斷點。

面板介紹 -- Event Listener Breakpoints

展開 Event Listener Breakpoints 可以看到一組事件類型,展開一個事件類型可以看到具體的事件名稱。

每個事件名稱和事件類型前面都有個復選框,選中即指當頁面中觸發了所選的事件的話,就會觸發中斷。

面板介紹 -- Global Listeners

顯示全局監聽器,在瀏覽器中 window 是全局對象,所以在 Global Listeners 面板中顯示綁定在 window 對象上的事件監聽。

異常中斷

這個跟上面幾種不一樣,這個是放在功能按鈕組里面的。

選中 "Pause on exceptions" 按鈕,如上圖,當執行的腳本出現異常時會觸發中斷。

介紹了如何添加斷點的方式以及幾款中斷類型,下面介紹一下如何利用斷點進行調試。

斷點調試

功能按鈕

我們先來介紹幾個功能按鈕:

  • :當程序中斷在斷點處時,點擊去往下一個斷點
  • :當程序中斷在斷點處時,長按上面的按鈕出現,點擊這個按鈕可以在 0.5s 內忽略任何中斷,當中斷出現在循環內部時一般比較有用
  • :執行下一條語句
  • :當中斷停留在一個函數調用處時,點擊這個按鈕會進入函數內部,而上面的按鈕則會執行函數調用的下一句,不會進入函數內部
  • :當中斷停留在函數內部時,點擊這個按鈕則會跳出函數內部,停留在函數調用的下一個語句
  • :在不取消斷點標記的情況下,使得所有斷點失效

面板介紹 -- Scope

Scope 面板顯示了你當前定義的所有屬性的值,例子如上圖。除了 Scope 面板,你還可以在左側的代碼區域,中斷的旁邊看到語句中包含的變量的值。除此以外,你還可以把鼠標放在變量上面,也顯示對應變量的值。

Scope 會顯示三種類型的值: Local、Closure 和 Global。

面板介紹 -- Call Stack

當代碼中斷在一處時,Call Stack 面板會顯示代碼的執行路徑。比如在 a() 中調用了 b(),b() 中調用了 c(),那么中斷如果在 c() 內部的話,那么 Call Stack 面板會依次顯示 c、b、a。

在 JS 中,我們常常會寫匿名函數,顯而易見,在調試時,尤其在查看調用棧時,這樣很不友好,所以建議盡量為每個函數命名。

如果還記得前面所講的黑盒腳本(Blackbox Script)的話,這里就再重復一句,是的,黑盒腳本永遠不可見,所以你即使在查看調用棧時你也沒法看到黑盒腳本里的內容。這種情況下會出現下面這樣的結果:

查看與修改你的值

前面講 Scope 面板時介紹了三種查看中斷狀態下的變量值,還有一個隱蔽的小技巧也能查看,按 esc 按鍵打開 Console drawer(不清楚是什么可以看Console),然后在里面輸入你想查看的值,回車,bingo~

如果你以為 Chrome DevTools 就簡單看看這些值那就太小瞧她了,在中斷狀態下,還能動態修改變量的值。比如中斷處有個變量叫 v,值是 1,如果我直接按 "Resume script execution" 的話,那么下一次的 v 也是 1,但如果我在按恢復執行按鈕之前,我在 Console drawer 中輸入 v = 2 回車,那么,下一處的 v 就是 2 了。

還有更厲害的,你不僅可以修改變量的值,你還可以修改代碼!當程序中斷時,你可以在 Sources 面板修改你的代碼。

介紹到這,還有一個面板:Watch,下面就講講這個。

面板介紹 -- Watch

正如名字所表示的,觀察,觀察什么呢?主要觀察變量。

前面我們講過,當程序中斷時,可以查看這個狀態下的變量的值,但局限是只能一個一個查看,而 Watch 的好處是可以讓我們同時查看多個變量。你可以通過 "+" 來添加變量,當添加的變量存在時會顯示對應的值,不存在的話則會顯示 "not availble"。需要注意的是,這里的變量不會隨着代碼的執行而發生改變,所以到了下一個狀態時,你需要點擊刷新按鈕來獲得關注的變量的新的值。

源碼調試

現在的項目幾乎都是經過編譯過的,所以當我們調試時會與編譯后的代碼打交道,但那並不是我們想要的。不要急,Chrome DevTools 提供了預處理過的代碼與源碼的映射,主要表現在兩點:

  • 在 console 上,源鏈接指向的是源碼,而不是編譯后的文件
  • 在 debug 時,在 Call Stack 面板上的源鏈接指向的也是源碼,不是編譯后的文件

不過需要注意的是,上面所講的能查看源碼的前提是 Chrome DevTools 在設置中提供了相應權限,具體是:Settings - Sources - Enable Javascript source maps / Enable CSS source maps,勾選這兩項即可。不過,默認情況下就是勾選。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM