本文使用「署名 4.0 國際 (CC BY 4.0)」許可協議,歡迎轉載、或重新修改使用,但需要註明來源。 署名 4.0 國際 (CC BY 4.0)
本文作者: 蘇洋
建立時間: 2018年10月14日
統計字數: 3902字
閱讀時間: 8分鐘閱讀
本文連結: soulteary.com/2018/10/14/…
站點優化記錄
還記得十年前,當時就在追求頁面在1s內開啟,沒想到十年後,我依舊在追求頁面在1s內開啟。
十年裡,不管是客戶端裝置、客戶端和服務端網路環境、服務端技術棧、甚至是開發語言技術棧都發生了不小的變化。
這次優化算是清理了幾年前的技術債,簡單記錄一下吧。
第五次重構
如果你對之前的幾次重構感興趣,可以跳轉文章尾部開始閱讀。
九月的時候,我更新了配置並將執行了幾個月的 Traefik
重啟,進一步進行資料統計。
十一的時候,我購置了一臺新的機器作為 Home Lab
,在將所有已有的服務進行了遷移,同時冗餘的資源,可以提供給所有開發專案測試環境
和預發驗證環境
。
在新環境的加持之下,原本完整編譯釋出的 1 分鐘
可以被縮減到 40 秒
,如果配合快取使用,時間可以縮減到 25 秒
之內。
在環境完備之後,我將九月執行至今(42天)的資料下載並進行統計,發現幾個有趣的資料 (下面分別是包含、不包含爬蟲的資料截圖)。
- 個別請求響應時間慢
- 每天接近
200MB
的流量使用,其中有的資源要完整響應客戶端,最大響應時間甚至到了30s
,個別例子甚至到了分鐘級別,猜測是高頻訪問時刻,頻寬被佔滿所致。
- 每天接近
- 靜態資源效率不高
- 靜態資源中,
common.css
、webfont
、core.js
、common.js
、sidebar-cover.jpg
請求數量巨大,佔用了固定頻寬,影響了一部分使用者的訪問體驗,浪費了這部分使用者的移動流量。
- 靜態資源中,
- 古董瀏覽器使用者不多了
- 訪客作業系統中
Windows
、Mac
、Android
、iOS
等作業系統依次遞減。訪客瀏覽器佔中IE
僅佔4.56%
,IE
系列中IE 9
佔了0.85%
,其他版本佔比低到可以忽略。
- 訪客作業系統中
- 404 資源需要進行相容
- 包含爬蟲在內,請求中有
14.18%
的請求出現了404,雖然流量只消耗了2.97%
,但是感覺應該進一步降低這個數值,畢竟要提供有價值和意義的內容呈現不是。
- 包含爬蟲在內,請求中有
下面的截圖是未重構前,包含非同步載入圖片的首頁資料。
可以看到 384KB
的資料載入,讓頁面 DOM Ready
延遲到了 300ms
, 而頁面完整載入硬是拖到了 994ms
。
尋遍訪問記錄,我發現輪播圖內容的訪問加起來不到 1%
,而且指令碼中用於適配桌面、移動端裝置的輪播程式碼包含元件庫程式碼(指令碼、樣式),加起來接近 3k
,延時載入的幾張圖居然佔用了總流量的 3%
,並且前面說到的完全載入時間被拖慢,這個元件功不可沒,簡直是豬隊友,這種高投入低產出的元件,可以直接幹掉。
為了照顧古董瀏覽器而使用的 jQ
庫佔用了接近 13%
的流量,結合上面的訪客客戶端資料,這個基礎庫該減肥了,在不大規模修改原來程式的基礎上,考慮到最小成本替換,於是暫時使用 Zepto
進行了替換,原始檔減少 60 KB
,GZip
後的檔案尺寸 13KB
,而隨後清理掉頁面載入的一些 inline script
,每個頁面的 GZip
後的尺寸又減少了 1KB
。
對於桌面系統展示的側邊欄的圖片,佔用了超過 10%
的流量,客戶端解析度越來越高,但是這個圖片卻不再好再進行尺寸上的擴張,一來浪費使用者流量,二來還是投入產出比的問題,於是我使用幾張 SVG
化後的圖片對它們進行了替換,在 GZip
壓縮之後,每張圖片只佔用不到 10 KB
,還能夠應對未來解析度的繼續擴張的問題。
在檢視頁面資料的時候,我發現 common.css
和 Web Fonts
分別佔用了總流量的 22.15%
和 13.47%
。前者原始碼居然 include
了大量未被使用的元件(前幾版重構過程中操作失誤)、後者居然沒有使用定製的字型檔案。在簡單修正之後,兩個檔案總共減少了 100 KB
以上。至於暫時不使用 SVG SPRITE
,我是這樣考慮的,雖然將圖示和字型放在 SVG
中,甚至合併到頁面內容中,能夠進一步減少請求,但是勢必要引入額外的指令碼進行資源掛載,而且渲染效能影響過大,頁面DOM複雜度也會提升,還不利於快取複用。等未來 Web Components
支援進一步完善再說吧。
另外,在處理過程,順便修正了 Node
和 Hugo TPL
存在的 ReDoS
的問題,現在網站中的多數文章應該都顯示正常了。
最後貼一下這次重構的戰鬥結果(Lighthouse v3.0.3)。
還有請求資料(無快取)。
暫時的缺陷:
PWA
完全沒有做的情況下,得分58
。- 無障礙訪問
88
分,失分在介面部分內容對比度不足,低解析度的情況下不滿足WCAG 2 AA
高對比度要到7:1
的要求。
回顧歷史
雖然之前有說過,在去年已經對網站進行了全面升級,拋棄了傳統的動態指令碼,取而代之的是 Markdown
配合一個 DataBridge
進行全站靜態生成,但是網站主題使用的還一直是在淘寶工作時使用的編寫的模板。
第一版
2014年最初設計模板的時候,其中有幾個小功能比較有意思。
- 資源載入全憑前端載入器,配合自動切換不同源頭的資源,可以輕鬆做到站點資源永不失效。並且會針對不同的瀏覽器載入不同版本的jQ依賴庫,從而在滿足相容性處理的情況下,提高執行效能。
- 模組粒度很細,但是入口統一由前端指令碼把控,不論指令碼、樣式,還是資源,都由頁面指令碼引入,使用構建工具在編譯時,再進行拆分優化。
- 儘可能避免
inline resource
,每類頁面單獨具備該頁面的指令碼和樣式,減少編寫時需要額外進行名稱空間或者書寫規避,同時減少爬蟲以及使用者重新整理帶來的額外傳輸損耗,提高資源快取利用率,提高響應速度。 - 配合修改過的
nginx concat
,可以做到在不更新資源的情況下,動態對頁面進行除錯。
第二版
隨後,隨著 gulp
的衰落、webpack
的興起,Markdown
的流行,BootStrap
的大版本升級,以及 SSL
證書的獲取從難到易,CDN
流量從貴到便宜,Hexo
缺乏定製,網站伺服器架構的變化… 網站又開始了變化。
- 使用
webpack
進行構建,基於AST
進行資源優化和拆分,替換掉之前使用AMD
進行資源顯示宣告以及手寫工具的模式。 - 子域名合併,在
SSL
未開始普及的時代,從前普通HTTP
流量分發,像是七牛、新浪雲可以作為低成本、甚至無成本的服務商,但是伴隨HTTP 2.0
到來的SSL
,如果還繼續使用多域名,帶來的第一個問題便是你需要申請多個域名的證書(當時泛域名證書非常貴),以及支付不是很便宜的HTTPS
流量成本。 Hexo
之類的的靜態站點生成器很多,但是當時幾乎都需要將文章Meta
資訊寫在文章內部,並且對於特定目錄結構的站點生成極其不友好,而且效能說實話不是很好。
第三版
2017年的時候,隨著 Markdown
工具體驗越來越好,考慮之後,實在沒有必要在堅持使用 WordPress
作為內容管理,於是在部落格架構中廢棄了 WordPress
。並且當文章數量過千篇之後,Hexo
效能瓶頸越來越嚴重,交付於 CI
系統執行構建,需要消耗太多的資源,於是將其替換為 Hugo
。
- 在更換
Hexo
換為Hugo
前,我曾經掙扎著寫過幾個Hexo
的外掛,但是效能真的太差了,如果要日常使用,必須準備一臺起碼2C2G
的雲主機閒置,太浪費了。 - 但是使用
Hugo
之後,失去了對Node.js
這類容易“編輯執行”的程式能力後,想要達到之前的網站生成結果,除了修改Hugo TPL
外,所有的“花樣”便只剩下在構建前後進行檔案處理、或者使用客戶端完善頁面內容了,不過這樣反而更加適合交付CI
,進行完全自動化。
第四版
今年五一假期的時候,網站在上一個版本的基礎上執行了快一年的時間裡,當初沒有轉換清理完畢的文章內容也陸陸續續的補齊了,在補齊內容的過程中,我進一步抽象了 DataBridge
,未來可以輕易切換到更多不同的靜態站點生成工具或者靜態釋出平臺上。
而隨著一次次的迭代優化,CI/CD
流程和周邊指令碼也變的效率越來越高, 準備資料 -> 生成站點 -> 處理檔案 -> 進行釋出
,這一套流程從最初的 2 分鐘縮減到了1 分鐘。
最後
計劃接下來再更新一輪,將未新增的 PWA
功能新增完畢,另外徹底移除不需要的 Lib
依賴,進一步提高網站呈現速度,然後再嘗試能否將網站去中心化,藉助不同服務提供商的 CDN 和 頁面內埋入的版本控制指令碼,變為“分散式”的網站,或許還會把網站關閉許久的評論功能補回來吧。
— EOF
我現在有一個小小的折騰群,裡面聚集了一些喜歡折騰的小夥伴。
在不發廣告的情況下,我們在裡面會一起聊聊軟體、HomeLab、程式設計上的一些問題,也會在群裡不定期的分享一些技術沙龍的資料。
喜歡折騰的小夥伴歡迎掃碼新增好友。(請註明來源和目的,否則不會通過稽核)
關於折騰群入群的那些事