詳解HTTP緩存
HTTP緩存是一項重要且常見的web性能優化手段。當通過瀏覽器發送HTTP請求時,如果瀏覽器本地有所要請求的文檔副本,那麼瀏覽器可以直接從本地存儲中讀取該文檔,而不用到伺服器上下載該文檔。使用HTTP緩存具有如下幾點好處:
減少冗餘的數據傳輸
緩解網路瓶頸
減緩伺服器壓力
降低請求時延
既然HTTP緩存有諸多好處,那麼其背後的原理是怎樣的呢?接下來將為大家揭開HTTP緩存的神秘面紗。
一、第一次發送HTTP請求
為了方便理解,我們可以簡單地認為瀏覽器存在一個緩存資料庫,用於緩存數據。在瀏覽器第一次請求數據時,此時瀏覽器緩存中沒有對應的緩存數據,需要請求伺服器,伺服器返回後,根據伺服器返回的緩存規則,將數據存儲至緩存資料庫中。其大致流程如下圖:
由上圖可知瀏覽器是根據一定的緩存規則對數據進行緩存的,那麼具體是怎樣的緩存規則呢?HTTP緩存有多種規則,根據是否需要重新向伺服器發起請求來分類,可分為兩大類:強制緩存和對比緩存。
二、強制緩存
強制緩存是指如果瀏覽器中存在緩存數據並且數據沒有過期,那麼直接從緩存中讀取數據,而無需向伺服器發起詢問。以下是強制緩存發生的時序圖:
從上圖可知,當使用強制緩存時,瀏覽器無需詢問伺服器就能判斷數據是否過期,那麼瀏覽器是根據什麼來判斷的呢?這就不得不提到跟強制緩存相關的2個HTTP響應頭了,分別是:Expires和Cache-Control。
Expires的值是服務端設置的資源過期時間,瀏覽器就是根據這個過期時間跟發起HTTP請求的當下時間作比較,如果當下時間早於過期時間,則直接使用該緩存資源。但是因為伺服器設置的這個過期時間是絕對時間,而瀏覽器跟伺服器的時間可能不一致,因此可能會產生誤差,所以現在Expires響應頭已經用的比較少了。
Cache-Control的值有如下幾個:private、public、no-cache、max-age,no-store,默認為private。
由此可見Cache-Control的功能更加強大,且過期時間是相對時間,所以現在用的比較多的還是Cache-Control。
三、對比緩存
對比緩存是指如果瀏覽器中存在緩存數據,則必須向伺服器發起請求以詢問該數據是否過期,從而決定是否使用本地緩存。以下是對比緩存的時序圖:
對比緩存指的是每次發送HTTP請求時,如果本地有緩存數據,那麼瀏覽器也需要發送額外的HTTP請求與伺服器進行對比,以確定本地數據是否過期。
對於對比緩存來說,緩存標識的傳遞是我們需要著重理解的,它在請求頭和響應頭間進行傳遞,服務端就是根據該緩存標識來判斷資源是否過期的。一共可分為以下兩種標識傳遞,接下來將分開介紹。
第一種是Last-Modified響應頭和If-Modified-Since請求頭。
Last-Modified的值表示的是資源的最後修改時間,在瀏覽器第一次發起HTTP請求時,伺服器會返回該響應頭。
瀏覽器在下次發起HTTP請求時,會帶上If-Modified-Since請求頭,其值就是第一次發送HTTP請求時,伺服器設置在Last-Modified響應頭中的值。
伺服器收到請求後如果發現有請求頭If-Modified-Since則與被請求資源的最後修改時間進行比對。若資源的最後修改時間大於If-Modified-Since,說明資源有被改動過,則響應完整的資源內容,返回狀態碼為200;若資源的最後修改時間小於或等於If-Modified-Since,說明資源未被修改,則響應HTTP狀態碼為304,告知瀏覽器繼續使用所保存的緩存。
第二種是Etag響應頭和If-None-Match請求頭。
Etag響應頭的值為當前資源在伺服器的唯一標識(生成規則由伺服器決定),在瀏覽器第一次發起HTTP請求時,伺服器會返回該響應頭。
當瀏覽器下次向服務端請求該資源時,會帶上If-None-Match請求頭,其值為第一次請求時伺服器返回的Etag響應頭的值。
伺服器收到請求後如果發現有請求頭頭If-None-Match則與被請求資源的唯一標識進行比對。如果不同,說明資源有被改動過,則響應完整的資源內容,返回狀態碼為200;如果相同,說明資源未被修改過,則響應HTTP304,告知瀏覽器繼續使用所保存的緩存。
四、總結
對於強制緩存,伺服器通知瀏覽器一個緩存時間,在緩存時間內,下次請求,直接用緩存,不在緩存時間內,執行比較緩存策略。
對於比較緩存,將緩存信息中的Etag或者Last-Modified通過請求發送給伺服器,由伺服器校驗,返回304狀態碼時,瀏覽器直接使用緩存。
TAG:全球大搜羅 |