瀏覽器端技術體系概覽 -- 前端開發的七種武器

ivon發表於2014-03-28

轉自:http://limu.iteye.com/blog/986724

科普文一則,說說我對前端技術體系(也稱瀏覽器端技術體系)的認識,希望能讓更多人瞭解前端,也希望能借此豐富前端開發的大局觀.

去年我寫了網站效能優化系列文章,看過的朋友會知道,這類文章重點並非介紹各種具體的優化技巧,而是在關注發掘這些優化點的思路和方法.然後介紹給大家多種檢測手段去發現問題,進而有目標的解決問題.所有這些需要我們對有網頁整個生命週期有清晰的認識,對網頁中各種技術極其相互結合的方式有明確的認知.這就回歸到一個更本質的問題:瀏覽器端技術體系是怎樣的.

想用三言兩語說清前端技術不大可能,但是用一篇不長的文章說清何謂前端,還是可以做到的.因為工作中我常會給後臺開發的同學介紹前臺技術,所以會經常涉及這類話題.

解析前端,我想需要回答如下幾個問題. 1.前端涉及幾種技術?分別是做什麼的? 2.在前端內部各種技術之間如何整合協作? 3.前端如何和後臺交流?

回答這些問題我會立即丟出前端開發的"七種武器"論,介紹前端主要涉及七種技術分別是什麼的同時,重點關注"七種武器"如何對內協作,如何對外交流.(鑑於本文的科普文性質,下面具體介紹中出現的"一切","都是","全部"這類定語可能並非絕對,但可以確定在99%的情況下是正確的)

一.HTTP:網頁上的一切來自Http請求 頁面上所有內容都是通過若干Http請求從服務端載入而來. 第一個請求通常是一份(X)HTML文件,也就是瀏覽器中位址列的指向.如圖:

(這張圖可以通過Fixfox的Firebug外掛,IE的Httpwatch工具,或者Chrome直接按Ctrl+Shift+I得到) 位址列中的url通常會包含地址和一些引數,這樣就可以找到對應的後臺服務,同時讓其據這些動態引數來確定輸出內容.

多個Http請求之間是獨立的.那麼其他請求又是由誰觸發的呢? 由瀏覽器觸發!是在瀏覽器解析這第一份(X)HTML文件的過程中發出,接下來我就將介紹這個過程.

二.HTML:在瀏覽器中HTML被解析成DOM樹 HTML文件是一份不那麼嚴謹的XML(文字)文件.在任意網頁上點選右鍵,點選檢視原始碼就可以看到. 瀏覽器按照HTML文件內容自上而下的解析執行.最終HTML文字被完整的解析成一顆樹,稱DOM樹. 注意:DOM樹是瀏覽器內一切所依附的根本,是本文的重點,以後也會多次強調.

(這張圖可以通過Fixfox的Firebug外掛,IE8/9按F12,或者Chrome直接按Ctrl+Shift+I找到) 繼續回答之前的問題:其餘的HTTP請求,除XHR(後面會介紹),CSS的@import和背景圖之外,幾乎都是在解析HTML時,由DOM樹上的幾種特定節點發起的.如圖中重點標示出的那些節點: :用來嵌入圖片 :用來巢狀其他HTML :可以用來引入CSS檔案 :可以用來引入JavaScript檔案 和:通常用來引入Flash檔案 之所以強調這一點,一是它說明了HTML和Http的關係:首個Http載入HTML,解析HTML發起其他Http.二來再次強調了DOM樹,請求在HTML解析為DOM樹過程中,在樹上節點被解析出來時觸發.

三.CSS:使用CSS設定展現樣式和網頁佈局 如何定義網頁的樣式,比如字型的顏色和大小?這是CSS的工作. Html程式碼 收藏程式碼

文字 文字 文字 我們看到最後一種方式,為節點指定了class屬性myTxt.而myTxt的詳細定義可以以兩種方式加入文件. Html程式碼 收藏程式碼 .myTxt:{color:red,font-size:50px} 當然CSS的功能不止是簡單的樣式定義,還可以通過定義區塊的位置確定網頁佈局方式,CSS也自然有其一套語法,描述CSS的功能,以及確定CSS規則與DOM節點之間的關聯.這些細節並非本文重點. 我們看到CSS或者通過節點的style屬性,或者通過特定的節點影響網頁,這又回到了我們反覆強調的內容,DOM樹,CSS並未脫離DOM樹,而是駐留其上. 四.JavaScript:使用JavaScript處理互動事件 說到JavaScript,不如先澄清下"Java與JavaScript的關係是雷鋒與雷峰塔的關係". 網頁應用是典型的事件驅動GUI系統.JavaScript為互動事件,時間線上的事件定義響應體. 我們看一個簡單的應用,點選按鈕,彈出一個警告框. Html程式碼 收藏程式碼 function test_clk(){ alert(1); }

接下來我們有個問題,js什麼時候執行? 首先,當瀏覽器解析到標籤時,開始執行其內的程式碼. 標籤內程式碼或者其他標籤內的特定屬性中可以定義事件響應體,在事件觸發時執行 script程式碼可以指定某些程式碼在指定時長後開始執行,或每隔一定間隔重複執行

重要的是我們還是看到了,JS同樣沒有脫離DOM樹.同CSS一樣駐留DOM樹上.同時需要明確的是JS是被load到客戶端瀏覽器之後,在瀏覽器中執行的,消耗的是客戶端計算資源.JS為瀏覽器端提供了計算能力,而瀏覽器端則是JS的宿主.JS作為一種指令碼語言,其實並不一定非要工作在瀏覽器這個宿主之上,但這脫離了前端技術體系,這裡不討論.

說到這裡,我們基本瞭解了構成一個獨立網頁的幾項要素,各自負責什麼,相互間如何協作.大家可能注意到,前面曾經說過每個http請求時相互獨立的,那麼如何讓各個網頁關聯起來呢?

首先網頁之間通過連結或表單關聯到一起.一般情況網頁之間通過點選形成一個新的執行a標籤href屬性的HttpGet請求,讓瀏覽器從一個頁面轉向另一個.

當需要瀏覽者通過客戶端提交資料時,我們通常製作一個表單,然後submit表單,將客戶資料將會通過HttpPost請求提交至另一個地址.

除此之外的另一個需求就是保持登陸狀態了,這需要一段資訊始終在各個網頁間傳遞,但是放在url引數中顯然是不安全的.那如何實現這個功能?這正是接下來介紹的內容.

五.Cookie:藉助Cookie標識瀏覽者身份,在頁面間保持會話 再次回到Http本身,它是一種無狀態的協議,分為Header和Body兩部分,Body是http傳遞的主體內容,Header又分為請求頭(RequestHeader)和(ResponseHeader)兩部分,而header中除了包含表明網頁間關係的引數之外也包含一些通用資訊,頭當中的資訊以鍵值對的方式書寫,主要負責通用的快取策略描述和身份標識等功能,如圖:

(這張圖,即為第一張圖中某個http請求點開之後看到的詳情,需要注意圖中上面列出了響應頭,下面是請求頭,和發生順序不一致.firebug就是這個順序,注意區分) 服務端可以通過響應頭種植cookie到客戶端,而客戶端的每個請求的請求頭中都會攜帶域名下的cookie.比如這個到limu.iteye.com的請求,會包含iteye.com下的cookie,同時也包括limu.iteye.com的cookie.服務端可以通過cookie儲存會話id,這樣多個請求之間就有了關聯.同時服務端set cookie時指定cookie設定到哪兒域名及路徑下,以及在客戶端將駐留多久.

最後說一下JavaScript和Cookie的關係,JavaScript可以讀寫所在頁面域名下的cookie值. 需要注意在http://www.a.com下面引入了http://www.b.com/b.js,b.js能讀取所在頁面,也就是www.a.com以及a.com下的cookie,而非b.com下的cookie.而b.js這個http的請求頭中則帶有b.com系列的cookie,這個請求的響應頭中,也只能給b.com種植cookie.這裡有點繞,但有必要澄清,可以遇到問題的時候可以再仔細看.

到此為止,我們瞭解了一個網頁的構成要素,也瞭解了網頁之間的聯絡,這樣我們就瞭解了一個傳統網站的前端技術體系.接下來我們介紹一些新花樣,正是這些帶來了Web2.0的前端變革.

六.DHTML:使用JavaScript操作Dom樹 回到網頁之內,其實我們只是獲得了一顆DOM樹,其他內容都駐留在樹上. 接下來我們想一下,如果有一種手段能夠隨心所欲的改變動態這棵樹,那豈不是我們就在客戶端擁有了完全控制一個網頁的能力.這項能力自然由JavaScript承擔.

接下來設想一下,操作一個棵樹,也就是一份結構化的XML文件我們需要怎樣的API? 找到一個或一組葉子節點,從一個節點出發找到相關節點:父,子,兄弟. 新增/複製節點,並插入到文件中指定位置,以及刪除節點. 增刪改葉子節點某個屬性以及節點包含的文字. 於是W3C(全球資訊網聯盟)的 DOM Level 1,2&3中定義了3個層次一系列Dom上的操作介面.其中Level1主要包含上面這些介面.在各種瀏覽器下Level 1基本都能被正確實現.

回憶一下,之前我們提到了JS的三個執行入口,很重要的一個是響應各種滑鼠鍵盤事件,如何為節點繫結事件響應動作,IE有獨特的事件模型.其餘瀏覽器的事件模型符合W3C DOM介面定義.

這一系列技術被稱為D(Dynamic)HTML,其核心是通過JS將Http,HTML,CSS,JavaScript更好的粘合在一起.通過JavaScript可以改變網頁內的一切,甚至包括動態引入新的CSS和JS. 很酷是麼?但單獨DHTML並未流行起來,因為我們空有力量卻不知道用到哪裡合適.於是當接下來介紹的技術被引入,當我們能夠根據服務端的指示來運用前臺的力量,一場影響深遠的真正的技術變革就此發生了.而在此之前,我們有必要意識到,DHTML不過是瀏覽器中JavaScript能力的一種擴充套件.

七.Ajax:使用JavaScript在網頁內與伺服器端互動 有了DHTML,JavaScript已經具有能力完全的改變所在網頁的每個細節.JavaScript的野心不止於此,如果JS能由事件驅動,從伺服器端源源不斷的獲取新鮮資料,那理論上不再需要第二個頁面了. 我們再回憶下,網頁上一切來自HTTP,獲取資料自然需要JavaScript發起HTTP請求,並且可以讀懂這個Http請求響應內容.於是有了XHR(XmlHttpRequest),首先作為一個ActiveX控制元件被IE5引入(這裡必須要感謝IE對不對?). XHR就是這樣一個可以由JS傳送Http請求,且當請求資料返回後將服務端資料交給JS的物件.而且XHR支援非同步請求,在Http請求的過程中(因為是和服務端打交道,所以這個操作耗時可能較長),頁面還可以正常工作,直到Http響應後會才觸發一個事件回撥JS方法處理資料.

如今Ajax並不單指XHR.所有在不離開當前頁面的前提下,由JS主動發起的從伺服器端獲取JS可解析資料的方案,皆可稱Ajax. 最常見的另一種Ajax實現方案是JSONP,JS通過DOM介面,建立一個節點,指定節點的src為一個http地址到資料伺服器,資料被包裝成可執行的JS,在http響應結束後立即執行.(這裡我們再一次涉及到了JS的執行入口之一,在瀏覽器遇到節點是執行).

在MS,Google等先驅的引導之下,Ajax的出現引起了前端領域,乃至整個網際網路開發領域的深刻變革,即為我們熟知的Web2.0.但回到本源,Ajax依然是瀏覽器中JavaScript能力的另一種擴充套件而已.

總結一下 HTTP:一切內容通過HTTP請求獲得 HTML:瀏覽器把HTML解析成DOM樹 CSS:定義HTML的佈局和樣式 JavaScript:提供計算能力,處理互動事件 Cookie:網頁間,請求間會話保持(JS可以操作Cookie) DHTML:JavaScript操作Dom樹(包括CSS) AJAX:JavaScript操縱HTTP 所有前端應用託生於這些基礎特性的整合 Web2.0主要託生於DHTML和AJAX這類JavaScript的能力擴充套件

前端技術體系的介紹可以告一段落,我們並沒有把一個個概念的英文縮寫展開,然後抄來晦澀的官方的解釋. "使用Http傳輸HTML文件,文件被解析成DOM樹,CSS負責佈局和樣式,JS提供計算能力,處理事件響應,Cookie維持會話." 沒錯,如果換你來寫一個瀏覽器,會不會也這樣做?那麼其他的客戶端圖形互動系統,是不是也一樣要完成傳輸,展現,事件互動等等功能? 如果我繼續介紹一下firebug這類前端開發工具,將其與七種武器對應上,再輔以一些API文件,就可以嘗試體驗下前端開發了.

最後和前端開發講幾句 讀到這裡的前端開發,先說聲抱歉,寫了這麼長,通篇都是你爛熟於心的內容.而且你明明瞭解更多,這裡卻沒有提到. 其實要點就在這裡,如何在你所有知道的內容中提出來若干要點,完整的描述前端技術體系,這件事情對於前端開發而言,重要麼?不重要麼?重要麼?不重要麼?我們看幾個問題:

為什麼會有DHTML? 我們瞭解Http,HTML,CSS,JS的協作關係,知道DOM樹是一切的依託,我們才會想到通過改變DOM樹來操縱網頁內的一切.

為什麼會有Ajax? 我們瞭解DHTML的能力,卻不知道其用武之地,後來我們想到依靠服務端指導.接下來我們又知道所有服務端內容都是通過Http獲得,自然我們需要JavaScript能夠操作的Http物件.

這些問題需要前端開發去發現,去解決.雖然大家都在跟著先賢們的步子走,很少能成為領域的開拓者,但是否瞭解整個前端技術體系的區別是你是否是在盲目跟風.區別是當一項新技術出現的時候是否能發現其解決的核心問題以及為解決問題付出的額外代價.

引入新技術的需要付出的額外代價是我要強調的另一個重點,使用DHTML的代價是什麼,嚴重依賴Ajax的代價又是什麼?瞭解這些然後我們才能更好的權衡要不要使用.

前端的發展依然在繼續,遇到什麼問題?如何解決? Cookie容量小,每次隨Http傳送,是否通過JS在客戶端儲存更多資料? -- LocalStorage JS單執行緒,能否讓JS進行大量計算的時候,頁面不再掛起? -- WebWorkers JS語言過於隨意,依賴繁雜,如何組織程式碼能方便共享智慧? -- CommonJS Modules Http無狀態短連線,能否讓客戶端更及時收到服務端訊息? -- 各種Comet Http頭較大無法壓縮,無法一個請求返回多個資料物件,怎麼辦? -- 使用SPDY協議

解決問題付出什麼代價?是否涵蓋了所有常用瀏覽器,如果不能是否做到了漸進增強?我們要不要這樣做?這些是做一名合格的前端,做一名對技術架構有影響力的前端,必然面對的問題.

前端技術體系,看起來題目很大,但其實並沒有玄之又玄的東西在裡邊,所以即便我寫的算不得優秀,但是說清楚還是可以的.我在面試高階前端的時候其實很在意前端大局觀,不然叫我如何放心的把一個將會持續發展的產品交到他手裡.

相關文章