cdn 作為内容分發網絡主要是将資源緩存在 cdn 節點上,然後後續通路即可直接通過 cdn 節點将資源傳回給用戶端,而不再需要回到源站伺服器以加快請求速度。那麼 cdn 到底對于哪些請求加速呢?其緩存規則和緩存時間是怎麼樣的呢?怎麼樣的緩存規則更加合理呢?本文就對 cdn 的緩存規則解讀。
cdn 對于常見的 http 請求均是支援的,具體對不同請求方式的支援情況請參考表一。但是有一點需要注意的是雖然對這些類型的 http 請求均是支援的,但是并不是對所有請求方式都會進行緩存的。 cdn 僅會對于 get 請求進行緩存,而對于其他的請求均不進行緩存,僅是起到中間代理、轉發的功能。是以我們建議添加 cdn 的站點源站最好能夠實作動靜分離。将動态請求和靜态請求的内容獨立成兩個站點,而 cdn 僅僅加速靜态站點中的資源。
表一. cdn 對 http 請求支援情況
請求方式
描述
是否支援
get
從指定的資源請求資料
支援
post
向指定的資源送出要被處理的資料
head
與 get 相同,但隻傳回 http 報頭,不傳回文檔主體
put
上傳指定的 uri
delete
删除指定資源
options
傳回伺服器支援的 http 方法
connect
把請求連接配接轉換到透明的 tcp/ip 通道
不支援
注意:
cdn 處理 head 請求時會将 head 請求轉換成 get 請求回源,是以源站日志中記錄的是 get 請求。
cdn 僅支援 post 和 put 方式發送帶有請求體(body)的 http 請求。
cdn 的緩存配置截圖如圖 1 所示。緩存配置包括目錄和字尾名兩種形式,并且可以針對不同的緩存配置設定不同的權重以決定其優先級。其中字尾名即是針對于特定字尾名設定的緩存規則,而目錄則是對該目錄及其子目錄下的所有檔案均生效的。當對同一檔案同時設定了字尾名和目錄的緩存的話會先依據優先級權值先進行選擇,在優先級權值相同的情況下會字尾名政策優先。
圖 1. cdn 緩存配置示意圖
總體而言,cdn 所有的緩存規則均可以按照圖 2 中所表述的内容進行判斷。下面我們對圖 2 中的詳細内容資訊解讀。
圖 2. cdn 緩存規則示意圖
cdn 處理一個資源是否緩存首先是需要看源站針對于該資源配置的緩存設定。因為源站的不緩存政策是使用者自身控制的,是以是有最高的優先級的,當源站配置了緩存規則則轉 2 。而如果沒有進行任何配置的話則轉 3 ,而對于浏覽器緩存情況轉 7 。
當源站配置了以下的規則時, cdn 會認為該資源源站不允許 cdn 緩存,并且這種情況下浏覽器也是不會做緩存的,是以會每次請求該資源時都回源站,無法進行緩存加速,如果沒有則轉 4 :
1)有s-maxage=0,no-cache,no-store,private其中一種
2)如果沒有s-maxage或者s-maxage=0,并且有max-age=0.
3)帶pragma: no-cache
在源站沒有配置緩存規則需判斷 cdn 控制台是否配置緩存規則,如果配置了緩存規則轉 4 ,如果沒有配置緩存規則轉 5 。
需判斷 cdn 控制台是否有配置緩存規則,如果配置了緩存規則的話那麼
cdn 上的緩存政策将覆寫源站的緩存政策,而控制台緩存配置的優先級為:
1)權重越高的優先級越好;
2)同等優先級字尾名優先級高于目錄優先級;
3)相同權重且相同優先級則随機比對(建議避免第三種場景),如果沒有配置緩存規則則轉 6 。
需根據源站的緩存規則進行緩存,常見的源站緩存規則有 cache-control和 expires 頭,根據 http 協定 cache-control 的優先級高于 expires 頭,并且 s-maxage 設定高于 max-age 設定。
需遵循 cdn 預設緩存規則,預設緩存規則包括:
1)對于 response 頭沒有包括 etag 或者 last-modified 頭的檔案預設是不緩存的(一般認為此類檔案為動态檔案);
2)沒有 last-modified 頭的檔案預設但是有 etag 頭的緩存 10 秒;
3)對于有 last-modified 頭的會按照(目前時間 - last-modified 時間) * 0.1,并且将其限制在 [10,3600] 區間内。
對于源站設定了不緩存的規則時浏覽器是不緩存的;如果 cdn 修改了 cache-control 或者 expires 頭時,浏覽器會按照該修改頭緩存;如果沒有修改即會按照源站的政策緩存。
常見通過 http 的響應頭檢視具體 cdn 的緩存情況,如圖 3 即是常見的通過 cdn 通路的響應頭,可以根據 x-cache 檢視目前該資源是否有在 cdn的 l1 節點緩存,而檢視 l2 節點的緩存情況則需要根據 via 頭中的第一部分檢視,如果是 m 即是 miss,沒有命中的狀态;而出現 h 即是命中緩存。x-swift-savetime 表示該資源緩存到 cdn 節點上的 gmt 時間(相比于中原標準時間晚8小時);而 x-swift-cachetime 表示該資源在 cdn 節點上緩存多長時間會過期。
圖 3. cdn 緩存情況示意圖