前端性能-使Javascript和CSS外聯

使用外聯的Javascript和CSS

我們應該使用外聯拓展Javascript和Css還是在頁面中內聯他們?我們將會發現,使用拓展文件通常會更好。

內聯VS外聯

讓我們開始來權衡下內聯和外聯這兩種方式。

在原始條件下,內聯比較快

我制作了兩個例子來說明內聯JS和CSS比外聯引用他們有更快的響應。

內聯JS和CSS http://stevesouders.com/hpws/inlined.php
外聯JS和CSS http://stevesouders.com/hpws/external.php

內聯例子包含一個87K大的HTML文檔,所有的JS和CSS都在頁面里面。外聯的例子包含一個7K的HTML文檔,一個59K的樣式文件,和三個JS(1K,11K和9K),總共87K,雖然總大小是一樣的,但是內聯要去外聯的例子快30%-50%。主要原因是因為外聯的例子有多個HTTP請求的開銷,即便部件是平行下載的,但還是要比內聯來的慢。

盡管是這個結構,但在真實的世界中,使用外聯文件通常產出更快的頁面訪問。這個得益于外聯文件不需要獲取,JS和CSS有機會被瀏覽器緩存。HTML文檔至少包含動態內容,通常不配置為可緩存。內聯JS和CSS每一次HTML文件請求時,都會去下載。另一邊,如果JS和CSS被瀏覽器緩存,HTML文檔的尺寸減少了,因為減少了好幾個HTTP請求。

關鍵因素是外聯JS和CSS與HTML文檔相關緩存的頻繁度,這個比較難評估,可以使用下面的測量標準。

頁面訪問數量

每個用戶的頁面瀏覽量越少,就是該使用內聯JS和CSS的有力論據。想象一下,一個典型的用戶訪問你的網站每月一次,在每次訪問中間,任何的JS和CSS緩存都可能已經失效,即便部件有一個很長的expire頭。

另一方面,如果一個典型用戶有很多的頁面訪問量,瀏覽器更可能有外聯部件的緩存。使用JS和CSS外聯文件的益處是隨著每月每個用戶額訪問量或者每次session每個用戶的頁面訪問量而水漲船高的。

空緩存VS命中緩存

比較內聯和外聯時,知道緩存外聯文件的潛能非常重要。我們在Yahoo上測量,發現單個用戶一天至少命中緩存一次的人數在40%-60%之間。相同的研究表明頁面訪問命中緩存的數量在75%-85%之間。注意第一個統計的是“單個用戶”而第二個統計的是“頁面訪問"。用戶可能一天中碰到一次空緩存訪問,但是更多的后來頁面訪問都來自命中緩存。

這些度量非常依賴網站的類型。知道這些數據幫助評估使用拓展文件相對內聯潛在的好處。如果你的網站對你的用戶有一個較高的命中緩存,使用外聯文件更好。否則,內聯會使一種更好的選擇。

部件重用

部件在不同網頁中重用慮比較大,使用外聯;如果重用慮低,使用內聯

多因數考慮典型的結果

權衡內聯和外聯,關鍵是訪問多個HTML請求相關的被緩存的外聯JS和CSS的頻率。在上面部分說的,我描述了三個指標(頁面訪問量,空緩存VS命中緩存,和組件重用)能夠幫助你做出最好的決定。

很多網站都在這三個指標之中,他們每個用戶每月訪問5-15個頁面,每個用戶每次session訪問2-5個頁面。40%-60%用戶每天有一次命中緩存,每天頁面訪問的75%-85%命中緩存。

考慮這些指標,最好的解決辦法是發布JS和CSS為外聯文件。

首頁

唯一的例外是內聯使用在首頁上。

兩者結合的最佳實踐

兩個技術在這里介紹,讓你同時獲得內聯和外聯兩者的益處。

提前下載

首頁是網頁訪問的開始,對于首頁我們想要內聯js和css,但是對于所有的二級頁面使用外聯文件。這個完全可以在首頁加載完成后,動態地下載二級頁面的外聯文件。使得外聯文件駐留在瀏覽器緩存中,為用戶繼續訪問其他頁面而使用。

預下載例子:
http://stevesouders.com/hpws/post-onload.php

<script type="text/javascript">
function doOnload( ) {
 setTimeout("downloadComponents( )", 1000);
}
window.onload = doOnload;
// Download external components dynamically using JavaScript.
function downloadComponents( ) {
 downloadJS("http://stevesouders.com/hpws/testsma.js");
 downloadCSS("http://stevesouders.com/hpws/testsm.css");
}
// Download a script dynamically.
function downloadJS(url) {
 var elem = document.createElement("script");
 elem.src = url;
 document.body.appendChild(elem);
}
// Download a stylesheet dynamically.
function downloadCSS(url) {
 var elem = document.createElement("link");
 elem.rel = "stylesheet";
 elem.type = "text/css";
 elem.href = url;
 document.body.appendChild(elem);
}
</script>
動態內聯

如果一個首頁的服務端知道一個部件是否在瀏覽器緩存中,它能夠做出決定是否使用內聯還是外聯文件。雖然沒有辦法讓服務端知道瀏覽器緩存中有什么,但cookie似乎是有用的。返回服務端一個基于session的cookie,服務端基于cookie值出現使用外聯,不出現使用內聯;

動態內聯的例子:
http://stevesouders/hpws/dynamic-inlinling.php

<?php
if ( $_COOKIE["CA"] ) {
 // If the cookie is present, it's likely the component is cached.
 // Use external files since they'll just be read from disk.
 echo <<<OUTPUT
<link rel="stylesheet" href="testsm.css" type="text/css">
<script src="testsma.js" type="text/javascript"></script>
OUTPUT;
}
else {
 // If the cookie is NOT present, it's likely the component is NOT cached.
 // Inline all the components and trigger a post-onload download of the files.
 echo "<style>\n" . file_get_contents("testsm.css") . "</style>\n";
 echo "<script type=\"text/javascript\">\n" . file_get_contents("testsma.js") .
"</script>\n";
 // Output the Post-Onload Download JavaScript code here.
 echo <<<ONLOAD
<script type="text/javascript">
function doOnload( ) {
 setTimeout("downloadComponents( )", 1000);
}
window.onload = doOnload;
// Download external components dynamically using JavaScript.
function downloadComponents( ) {
 document.cookie = "CA=1";
[snip...]
ONLOAD;
}
?>
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 227,250評論 6 530
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 97,923評論 3 413
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 175,041評論 0 373
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 62,475評論 1 308
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 71,253評論 6 405
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 54,801評論 1 321
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 42,882評論 3 440
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,023評論 0 285
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 48,530評論 1 331
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 40,494評論 3 354
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 42,639評論 1 366
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,177評論 5 355
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 43,890評論 3 345
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,289評論 0 25
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 35,552評論 1 281
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 51,242評論 3 389
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 47,626評論 2 370

推薦閱讀更多精彩內容