1. 程式人生 > >使用 Chrome 開發者工具進行 JavaScript 問題定位與除錯

使用 Chrome 開發者工具進行 JavaScript 問題定位與除錯

引言

Google Chrome 是由 Goole 公司開發的一款網頁瀏覽器,自 2008 年 9 月第一個測試版本釋出以來,其市場佔有率逐步上升,至 2014 年 5 月,Chrome 已超越 Firefox 成為全球市場佔有率第二的瀏覽器。Chrome 的受歡迎程度與其優秀的效能與相容性密不可分,並且越來越多的網路應用程式都添加了對 Chrome 的支援,也足以體現網路應用的開發人員對 Chrome 的認可與青睞,而其中最重要的原因之一,莫過於 Chrome 所提供的強大的開發者工具。Chrome 開發者工具包含諸多強大的功能模組,適應於多個不同場合的需要。本文先簡單介紹 Chrome 開發者工具的各個模組及其基本功能,再著重針對網頁尾本除錯,闡述如何巧妙運用 Chrome 開發者工具定位與除錯問題。(本文所選的 Chrome 開發者工具為 Chrome V35 版本中內建,較之前版本可能略有不同,請留意)

Chrome 開發者工具介紹

雖然對於 Chrome 開發者工具的介紹,Google 官方以及網際網路中都有眾多文章進行闡述,但為了有助於讀者更好地理解本文後面對如何巧妙運用開發者工具定位及除錯指令碼的闡述,在此對開發者工具中的各個模組做一個概要性的介紹。如果對其中某些模組特別有興趣,請參考文末的連結,從中進行深入瞭解。

Chrome V35 版本中的開發者工具分為 8 個大模組,每個模組及其主要功能為:

  • Element 標籤頁: 用於檢視和編輯當前頁面中的 HTML 和 CSS 元素。
  • Network 標籤頁:用於檢視 HTTP 請求的詳細資訊,如請求頭、響應頭及返回內容等。
  • Source 標籤頁:用於檢視和除錯當前頁面所載入的指令碼的原始檔。
  • TimeLine 標籤頁: 用於檢視指令碼的執行時間、頁面元素渲染時間等資訊。
  • Profiles 標籤頁:用於檢視 CPU 執行時間與記憶體佔用等資訊。
  • Resource 標籤頁:用於檢視當前頁面所請求的資原始檔,如 HTML,CSS 樣式檔案等。
  • Audits 標籤頁:用於優化前端頁面,加速網頁載入速度等。
  • Console 標籤頁:用於顯示指令碼中所輸出的除錯資訊,或執行測試指令碼等。

後文會在闡述過程中,會提及使用 Element 標籤頁探測頁面元素並檢視該元素的 HTML 內容,也會使用 Source 標籤頁與 Console 標籤頁除錯指令碼及檢視除錯資訊,並不會詳細介紹他們的基本功能,請在閱讀時提前瞭解以上相關標籤頁的基本功能。

使用 Chrome 開發者工具巧妙定位指令碼程式碼

目前很多的網頁應用程式都會使用各種諸如 JavaScript 之類的指令碼語言,來增強事件處理、頁面展現或是樣式控制等方面的功能。很多網站或網路應用系統都已做成單頁面模式,該頁面只負責載入相關的指令碼與樣式,這些指令碼與樣式來負責動態生成更多的子頁面或對話方塊。因此,該類網頁應用程式的指令碼數量會非常大,從而使開發人員在如此之多的指令碼中定位某個問題變得困難起來,但也並非毫無技巧。

單頁面的網路應用程式一般會引入複雜的 JavaScript 框架,如 JQuery, Dojo 或 ExtJS 等。這些框架都支援宣告自定義的網頁小元件,如 Dojo 中的 widget。一般而言,每一個 widget 會被單獨寫在一個 JS 檔案中。因此,在定義該元件時,可以將儲存它的 JS 檔名做為其 id 成員屬性的一部分(例如字首),並在描述該元件的 HTML 模板中,將 id 的值加入到 HTML 標籤的屬性中。當應用程式在 Chrome 瀏覽器中執行時,在使用 Chrome 開發者工具的"元素"模組中的元素探測功能查詢 HTML 時,可以很直觀地看見每一個 div 對應的 JS 檔案。因此,當某一個 div 出現問題時,對其 HTML 進行探測後,便可根據其中的 id 定位到相應的指令碼檔案,從而使問題除錯的範圍大大縮小。以下通過實際專案中的例子加以說明。

清單 1. Dojo 中自定義 widget 引入 id 的宣告方式
dojo.declare("exc.fe.bijits.FeLogon.FeLogonLogonPanel",[exc.kc._Bijit, dojox.dtl._Templated,], {
 templatePath: dojo.moduleUrl('exc.fe.bijits.FeLogon', "FeLogonLogonPanel.html"),
    select : null,
    SESSION_ID_OFFSET : 0,
    sessionid : null,
    launchType: "Standard Login",
    langcnt: 0,
    currentLang:null,
	……//省略之後不相關的方法和屬性
	……
});

在清單 1 中給出的是使用 Dojo 建立自定義 widget 並將該 widget id 引入其模板 HTML 中的方式。自定義的 widget 在繼承了 dojox.dtl._Templated 之後,Dojo 有內部機制可將該 widget 宣告的名稱作為 id 自動加到其 HTML 模板中。因此開發人員只要保證該 widget 宣告的名稱與其所儲存的檔名對應即可。清單 1 中的 id 與儲存該指令碼的檔名均為"exc.fe.bijits.FeLogon.FeLogonLog-

-onPanel"。

在此前提下,開啟瀏覽器執行網頁載入該 widget 後,使用 Chrome 開發者工具的網頁元素探測功能找到該 widget,便可看見其 id,即相應的指令碼檔案,如圖 1 所示。如若該 widget 中的行為出現異常,例如 user id 不能進行校驗,便可開啟其相關的指令碼檔案進行除錯。

圖 1. 檢視 widget 在 HTML 模板中的 id
檢視 widget 在 HTML 模板中的 id

開啟執行時錯誤自動暫停功能,準確定位出錯指令碼位置

在 Chrome 開發者工具中,可以開戶執行時錯誤自動暫停這一功能(如圖 2 所示),從而使開發者工具能在發現執行時指令碼異常時,在異常指令碼處暫停執行,跳轉至除錯頁面,供開發人員進一步查詢該執行時異常產生的原因。

圖 2. Source 面板中的自動暫停按鈕
Source 面板中的自動暫停按鈕

自動暫停按鈕的下方有一個選項,Pause On Caught Exceptions,如果勾選上,則即使所發生執行時異常的程式碼在 try/catch 範圍內,Chrome 開發者工具也能夠在錯誤程式碼處停住。

合理新增除錯日誌,通過 Console 標籤頁定位

在進行指令碼開發過程中,在重要的方法中新增必要的除錯日誌輸出語句,可以方便開發人員進行問題定位與除錯。清單 2 中的 JavaScript 指令碼方法中,在其開始和結束處添加了 debug 級別的日誌輸出,從而使該方法在被執行時,可在 Console 標籤頁找到相關日誌,並且能通過點選該日誌的末端檔案連結直接跳轉到 Source 標籤頁的指令碼原始檔中,極大方便了相關程式碼的定位,如圖 3 所示。

清單 2. Dojo 中自定義 widget 引入 id 的宣告方式
_containerSelect : function( /*ContentPane*/ cp ) {
        var F = this.declaredClass + "._containerSelect(): ";
        console.debug(F,"Starting: ", cp);//當方法被執行時,在控制檯輸出相關日誌
        
        dojo.forEach( this.children, function(child) {
            if ( cp.id === child.targetId ) {
                this.showChild( child.id );
                //-- Save requested module
                this._history.push( child.id );
                //kak
                if(this.globalArgs._showModuleTopic)
                  dojo.publish(this.globalArgs._showModuleTopic, [ child.id,"open" ]);
            }
        }, this);
		console.debug(F,"End");//當方法執行結束後,在控制檯輸出相關日誌
    },
圖 3. Console 面板中的日誌輸出
Console 面板中的日誌輸出

使用 Chrome 開發者工具除錯 JavaScript 的技巧與心得

上文介紹了 3 種定位相關指令碼的方法,在定位指令碼之後,通常會對指令碼中的部分程式碼進行除錯,本章主要詳細講解高效快捷地利用 Chrome 開發者工具進行 JavaScript 指令碼除錯的幾種技巧與心得。

設定條件斷點

與 Java 除錯類似,Chrome 開發者工具提供了斷點設定、刪除與斷點儲存等基本功能。同時,開發者工具也提供了設定條件斷點的功能,使開發者可以控制該斷點只有在滿足某一條件時才會被觸發。

條件斷點的設定如圖 4 所示,在所需要設定斷點的行最前端的行號處點選右鍵,選擇新增條件斷點後,會彈出一個對話方塊用於輸入具體的條件。合理運用好條件斷點能夠提高除錯的效率與準確性,使開發人員能更專注於在期望的場景下進行除錯。

圖 4. Source 面板中新增條件斷點
Source 面板中新增條件斷點

修改 JavaScript 檔案中的程式碼

這是 Chrome 開發者工具提供的一種非常實用的功能,即使開發人員可直接對開發者工具的 Source 標籤頁中的程式碼進行修改,並將其儲存,使瀏覽器在下次執行該段指令碼時,直接載入最新修改的版本。目前的 Firebug 及 IE 自帶的開發者工具都不支援對指令碼的直接修改,導致在 Firefox 或 IE 中除錯指令碼時,如果需要對程式碼進行修改,需要先去修改指令碼原始檔,再同步至應用伺服器,再清理瀏覽器快取,最終再次開啟應用程式時,才會看到程式碼修改後的效果。可見 Chrome 開發者工具提供的這一功能,大大提供了開發者除錯指令碼的效果。

需要注意的是,由於這種修改是儲存在瀏覽器快取中,因此它不會影響到指令碼的原始檔。當開發人員決定採用修改之後的指令碼時,需要將其複製到指令碼的原始檔中。

使用控制檯列印變數值或方法的返回結果

當斷點被觸發進入到除錯模式時,我們可以將當前任意存在的變數或方法輸入到控制檯中,按下回車後,控制檯便會返回相關的結果。該功能可使開發人員方便了解程式執行至斷點處時各個所需要變數或方法的返回值。

需要注意的是,當在控制檯中輸入的方法名字不帶括號時,控制檯輸出的是該方法所包含的程式碼資訊,而並不是執行結果。

結合 Element 標籤頁除錯 JavaScript 中對 CSS 的控制

在網頁開發過程中,經常需要在指令碼中控制不同條件下頁面的樣式展示,例如要求某一個按鈕的顏色在使用者停留十秒鐘之後由白色變成灰色。此時我們便需要在指令碼中通過具體的數值指定這個"灰色"該如何表示,一般情況下我們需要查詢相關資料或使用其他工具才能得到期望的"灰色"所對應的 RGB 數值或十六進位制數值。然而在 Chrome 開發者工具的 Element 標籤頁中,其實已經提供了包括該功能在內的一系列對樣式進行實時修改的功能,並且在修改之後能夠立即從頁面中看到變化。

圖 4 給出的是 Element 標籤頁的右半部分,當要對某個樣式類中的顏色進行修改時,它提供出一個非常直觀的圖譜供選擇,並在下方將其十六進位制程式碼顯示出來。開發人員可直接在此進行顏色選擇,確定顏色後,在 JavaScript 程式碼中引用其十六進位制數值即可。

圖 5. Element 面板中的顏色樣式編輯
Element 面板中的顏色樣式編輯

結語

Chrome 開發者工具的功能豐富而強大,本文著眼於對 JavaScript 的定位與除錯,介紹了其中的技巧與心得。相對於 Firebug 與 IE 開發者工具而言,Chrome 所提供的一些獨特功能如對指令碼原始碼的直接修改,極大方便了開發者對指令碼的開發與除錯。隨著 Chrome 新版本的推出,相信其開發者工具的功能也會日益增強,我們可以通過閱讀其官方更新說明,瞭解到新功能,藉助 Chrome 開發者工具的支援,提高網頁應用程式開發與除錯的效率。