Apache靜態資源緩存配置


1、緩存機制了解

ExpiresCache-ControlLast-ModifiedETag 是和網頁緩存相關的幾個字段。在看如何設置之前,我們先了解一下這幾個字段的作用。

1.1 強制緩存

強制緩存的含義是,當客戶端請求后,會先訪問緩存數據庫看緩存是否存在。如果存在則直接返回;不存在則請求真的服務器,響應后再寫入緩存數據庫。

● Expires

這是 HTTP 1.0 的字段,用來指定資源到期的時間,是服務器端的具體的時間點。表示緩存到期時間,是一個絕對的時間 (當前時間+緩存時間),如

Expires: Thu, 10 Nov 2017 08:45:11 GMT

在響應消息頭中設置這個字段之后,就可以告訴瀏覽器在未過期之前不需要再次請求。但是如果修改了本地時間,可能會造成緩存失效。

● Cache-control

HTTP/1.1中,增加了一個字段Cache-control,該字段表示資源緩存的最大有效時間,在該時間內,客戶端不需要向服務器發送請求。
ExpiresCache-control的區別就是前者是絕對時間,而后者是相對時間。如下:

Cache-control: max-age=2592000

下面列舉一些 Cache-control 字段常用的值:

no-cache:雖然字面意思是“不要緩存”,但實際上還是要求客戶端緩存內容的,只是是否使用緩存則需要經過協商緩存來驗證決定。

no-store: 真正意義上的“不要緩存”。所有內容都不走緩存,即不使用強制緩存,也不使用協商緩存。

public:所有的內容都可以被緩存 (包括客戶端和代理服務器, 如 CDN)。

private:所有的內容只有客戶端才可以緩存,中間節點不允許緩存,例如代理服務器。Cache-Control的默認值。

max-age:即最大有效時間,表示緩存內容將在xxx秒后失效。

must-revalidate:如果超過了 max-age 的時間,瀏覽器必須向服務器發送請求,驗證資源是否還有效。

Cache-control 的優先級高於 Expires,為了兼容 HTTP/1.0 和 HTTP/1.1,實際項目中兩個字段我們都會設置。

1.2 協商緩存

協商緩存就是強制緩存失效后,瀏覽器攜帶緩存標識向服務器發起請求,由服務器根據緩存標識決定是否使用緩存的過程。

● Last-Modified & If-Modified-Since

瀏覽器在第一次訪問資源時,服務器返回資源的同時,在response header中添加 Last-Modified字段,告知瀏覽器資源最后一次被修改的時間,例如
Last-Modified: Fri, 22 Jul 2016 01:47:00 GMT
瀏覽器將這個值和內容一起記錄在瀏覽器緩存中。瀏覽器下一次請求這個資源,瀏覽器檢測到有 Last-Modified這個header,於是添加If-Modified-Since這個header,值就是Last-Modified中的值;服務器再次收到這個資源請求,會根據 If-Modified-Since 中的值與服務器中這個資源的最后修改時間對比,如果沒有變化,返回304和空的響應體,直接從緩存讀取,如果If-Modified-Since的時間小於服務器中這個資源的最后修改時間,說明文件有更新,於是返回新的資源文件和200。

缺點:

  • 如果資源更新的速度是秒以下單位,那么該緩存是不能被使用的,因為它的時間單位最低是秒。
  • 如果文件是通過服務器動態生成的,那么該方法的更新時間永遠是生成的時間,盡管文件可能沒有變化,所以起不到緩存的作用。
● Etag & If-None-Match

為了解決上述問題,出現了一組新的字段 EtagIf-None-Match
Etag 存儲的是文件的特殊標識(一般都是 hash 生成的),服務器存儲着文件的 Etag 字段。之后的流程和 Last-Modified 一致,只是 Last-Modified 字段和它所表示的更新時間改變成了 Etag 字段和它所表示的文件 hash,把 If-Modified-Since 變成了 If-None-Match。服務器同樣進行比較,命中返回 304, 不命中返回新資源和 200。

Etag 的優先級高於 Last-Modified

更多關於緩存知識請查看:

深入理解瀏覽器的緩存機制

一文讀懂前端緩存

2. Apache緩存配置例子

對於一般的純靜態頁面,如html、gif、jpg、css、js,默認安裝的Apache服務器,不會在響應頭添加這個字段。在Apache的配置文件中進行靜態資源配置即可,這里我用的是Apache2.4版本。

2.1 Apache設置Express

使用Apachemod_expires.so 模塊來設置,這包括控制應答時的Expires頭內容和Cache-Control頭的max-age指令

啟用expires_module模塊:

a2enmod expires

重啟Apache

server apache2 reload

修改apache2.conf文件:

# 啟用有效期控制
ExpiresActive On
# 圖片
ExpiresByType image/jpg "access plus 1 month" 
ExpiresByType image/jpeg "access plus 1 month"
ExpiresByType image/gif "access plus 1 month"
ExpiresByType image/png "access plus 1 month"
ExpiresByType image/x-icon "access plus 1 month"
# css/js
ExpiresByType text/css "access plus 4 weeks"
ExpiresByType text/javascript "access plus 4 weeks"
# html
ExpiresByType text/html "access plus 2 days"

或者

<ifmodule mod_expires.c>
# image
<filesmatch "\.(jpg|jpeg|gif|png|ico)$">
ExpiresActive on
ExpiresDefault "access plus 1 month "
</filesmatch>
# css/js
<filesmatch "\.(css|js)$">
ExpiresActive on
ExpiresDefault "access plus 4 weeks "
</filesmatch>
# html
ExpiresByType text/html "access plus 2 days"
</ifmodule>

注:當設置了expires后,在response header會自動輸出Cache-Control 的max-age 信息

2.2 Apache設置Cache-Control

啟用 headers_module 模塊

a2enmod headers

重啟 Apache

server apache2 reload

修改apache2.conf文件:

# 配置mod_headers模塊
<FilesMatch "\.(ico|pdf|flv|jpg|jpeg|png|gif|woff|js|css|swf)$">
	Header set Cache-Control "max-age=604800"
</FilesMatch>

2.3 Apache設置Last-Modified

一般純靜態頁面本身都會有Last-Modified信息,Apache服務器會讀取頁面文件中的Last-Modified信息,並添加到http響應頭部。
對於動態頁面,如果在頁面內部沒有通過函數強制加上Last-Modified,例如

header(”Last-Modified: ” . gmdate(”D, d M Y H:i:s”) . ” GMT”)

Apache服務器會把當前時間作為Last-Modified,返回給瀏覽器。

2.4 Apache設置Etag

Apache中設置Etag的支持比較簡單,可以通過FileETag指令配置該選項, 例如在Apache配置文件里面加入:

FileETag MTime Size // 大小(Size)和最后修改時間(MTime)進行Hash后得到文件的ETag的值
FileETag None // 可以使響應頭不再包含ETag字段

3.完整例子

<VirtualHost *:80>
ServerName www.xxxx.com
DocumentRoot /xx/xxx/
# 配置mod_expires模塊
# 啟用有效期控制
ExpiresActive On
# image
ExpiresByType image/jpg "access plus 1 month" 
ExpiresByType image/jpeg "access plus 1 month"
ExpiresByType image/gif "access plus 1 month"
ExpiresByType image/png "access plus 1 month"
ExpiresByType image/x-icon "access plus 1 month"
# css/js
ExpiresByType text/css "access plus 4 weeks"
ExpiresByType text/javascript "access plus 4 weeks"
# html
ExpiresByType text/html "access plus 2 days"
# 配置mod_headers模塊
<FilesMatch "\.(ico|pdf|flv|jpg|jpeg|png|gif|woff|js|css|swf)$">
Header set Cache-Control "max-age=604800"
FileETag MTime Size
</FilesMatch>
<VirtualHost>


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM