# 3.1 Cache-Control
> 作者:肖鵬-SpiritLing 時間:2018-05-13
> 通過指定首部字段 `Cache-Control` 的指令,來進行緩存操作的工作機制,多個參數之間可以使用“,”分隔
```http
例:Cache-Control: private,max-age=0,no-cache
```
- `Cache-Control` 指令一覽
- 緩存請求指令
| 指令 | 參數 | 說明 |
| ---|--- | --- |
| `no-cache` | 無 | 強制向源服務器再次驗證 |
| `no-store` | 無 | 不緩存請求或響應的任何內容 |
| `max-age`=[秒] | 必需 | 響應最大的Age值 |
| `min-fresh`(=[秒]) | 可省略 | 接受已過期的響應 |
| `min-fresh`=[秒] | 必需 | 期望在指定時間內的響應仍有效 |
| `no-transform` | 無 | 代理不可更改類型 |
| `only-if-cached` | 無 | 從緩存獲取資源 |
| `cache-extension` | - | 新指令標記(token) |
- 緩存響應指令
| 指令 | 參數 | 說明 |
| ---|--- | --- |
| `public` | 無 | 可向任意方提供響應的緩存 |
| `private` | 可省略 | 僅向特定用戶返回響應 |
| `no-cache` | 可省略 | 緩存前必須確認其有效性 |
| `no-store` | 無 | 不緩存請求或響應的任何內容 |
| `no-transform` | 無 | 代理不可更改媒體類型 |
| `must-revalidate` | 無 | 可緩存但必須向源服務器進行確認 |
| `proxy-revalidate` | 無 | 需求中間緩存服務器對緩存的響應有效性再進行確認 |
| `max-age`=[秒] | 必需 | 響應的最大Age值 |
| `s-maxage`=[秒] | 必需 | 公眾緩存服務器響應的最大Age值 |
| `cache-extension` | - | 新指令標記(token) |
# 3.1.1 表示是否能緩存的指令
- `public` 指令
```http
Cache-Control: public
```
`public` 意思公共的,表示所有人都可以利用緩存
- `private` 指令
```http
Cache-Control: private
```
`private` 意思私人的,表示響應只以特定的用戶作為對象,這與 `public` 指令的行動相反
- `no-cache` 指令
```http
Cache-Control: no-cache
```
`no-cache` 意思是不要過期的緩存資源,表示為了防止從緩存中返回過期的資源
* 客戶端發送攜帶:表示客戶端將不會接受緩存過的響應。于是,“中間”的緩存服務器必須把客戶端請求轉發給源服務器。
* 服務器端發送攜帶:表示緩存服務器不能對資源進行緩存。源服務器以后也將不再對緩存服務器請求中提出的資源有效性進行確認,且禁止對其響應資源進行緩存操作
```http
Cache-Control: no-cache=Location
```
由服務器返回的響應中,若報文首部字段 `Cache-Control` 中對 `no-cache` 字段名進行具體指定參數值,那么客戶端在接受到這個被指定參數值的首部字段對應的響應報文后,就不能使用緩存。換言之,無參數值的首部字段可以使用緩存。只能在響應指令中指定該參數
> 請注意,這里 `no-cache` **不是代表著不緩存,而是代表著,不要過期的緩存**,意思就是說,當請求時,中間緩存服務器會向服務器進行有效期確認,不使用當前緩存的過期資源,也許 `no-cache` 稱為 `do-not-serve-from-cache-without-revalidation` 更為恰當
# 3.1.2 控制可執行緩存的對象的指令
- `no-store` 指令
```http
Cache-Control: no-store
```
`store` 意識是倉庫,儲存,代表著請求(和對應的響應)或響應中包含機密信息,因此,改指令才是真正的不緩存,規定不能緩存在本地存儲請求或響應的任一部分
# 3.1.3 指定緩存期限和認證的指令
- `s-maxage` 指令
```http
Cache-Conntrol: x-maxage=604800 (單位:秒)
```
`s-maxage` 指令的功能和 `max-age` 指令相同,它們的不同點就是 `s-maxage` 指令只適用于多位用戶使用的公共緩存服務器(一般指代理)。也就是說,對于同一用戶重復返回響應的服務器來說,這個指令沒有任何作用。另外,當使用 `s-maxage` 指令后,則直接忽略對 `Expires` 首部字段及 `max-age` 指令的處理
- `max-age` 指令
```http
Cache-Control: max-age=604800(單位:秒)
```
當客戶端發送的請求中包含 `max-age` 指令時,如果判斷緩存資源的緩存時間數值比指定時間的數值更小,那么客戶端就接收到緩存的資源。另外,當指定 `max-age` 值為0,那么緩存服務器通常需要將請求轉發給源服務器。
當服務器返回的響應中包含 `max-age` 指令時,緩存服務器將不對資源的有效性進行再度確認,而 `max-age` 數字代表資源保存為緩存的最長時間。
應用 `HTTP/1.1` 版本的緩存服務器遇到同時存在Expiress首部字段的情況時,會優先處理 `max-age` 指令,而忽略掉 `Expires` 首部字段。而 `HTTP/1.0` 版本的緩存服務器的情況剛好相反,`max-age` 指令會被忽略。
- `min-fresh` 指令
```http
Cache-Control: min-fresh=60 (單位:秒)
```
`min-fresh` 指令是要求緩存服務器返回至少還未過指定時間的緩存資源。
比如:當指定 `min-fresh` 為60秒時,在這60秒以內如果有超過有效期限的資源都無法作為響應返回了。
- `max-stale` 指令
```http
Canche-Control: max-stale=3600(單位:秒)
```
使用 `max-stale` 可指示緩存資源,即使過期頁照常接收。
如果指令未指定參數值,那么無論經過多久,客戶端都會接收響應;如果指令中指定了具體的數值,那么即使過期,只要仍然處于 `max-stale` 指定的時間內,仍舊會被客戶端接收。
- `only-if-cached` 指令
```http
Cache-Control: only-if-cached
```
使用 `only-if-cached` 指令表示客戶端僅在緩存服務器本地緩存目標資源的情況下才會被要求其返回,換言之,該指令要求緩存服務器不重新加載響應,也不會再次確認資源有效性。若發生請求緩存服務器的本地緩存無響應,則返回狀態碼 504 Gateway Timeout (請求網關超時)
- `must-revalidate` 指令
```http
Cacnhe-Control: must-revalidtae
```
使用 `must-revalidtae` 指令,代理會向源服務器再次驗證即將返回的響應緩存目前是否依然有效。
若代理無法連通源服務器再次獲取有效資源的話,緩存必須給客戶端一條 504 Gateway Timeout (請求網關超時)狀態碼。
另外,使用 `must-revalidtae` 指令會忽略請求的 `max-stale` 指令(即使已經在首部使用了 `max-stale` ,也不會再有效果)。
- `proxy-revalidate` 指令
```http
Cacnhe-Control: proxy-revalidtae
```
`proxy-revalidtae` 指令要求所有的緩存服務器在接收到客戶端帶有該指令的請求返回響應之前,必須再次驗證緩存的有效性。
- `no-transform` 指令
```http
Cacnhe-Control: no-transform
```
使用 `no-transform` 指令規定無論是在請求還是響應中,緩存都不能改變實體主體的媒體類型。
這樣可以防止緩存或代理壓縮圖片等類似操作。
- **`Canche-Control` 擴展**
- `cache-extension token`
```http
Cache-Control: private,community="UCI"
```
通過 `cache-extension` 標記(`token`),可以擴展 `Cache-Control` 首部字段內的指令。
如上例,`Cache-Control` 首部字段本身沒有 `community` 這個指令。借助 `extension tokens` 實現了改指令的添加。如果緩存服務器不能理解 `community` 這個新指令,就會直接忽略。因此,`extension tokens` 僅對能理解它的緩存服務器來說是有意義的。
> 作者:肖鵬-SpiritLing 時間:2018-05-13
- 首語
- 第一章 HTTP協議及網絡基礎
- 第二章 協議返回狀態碼
- 第三章 HTTP通用首部字段
- 第一節 Cache-Control字段
- 第二節 Connection 字段
- 第三節 Date 字段
- 第四節 Pragma 字段
- 第五節 Trailer 字段
- 第六節 Transfer-Encoding 字段
- 第七節 Upgrade 字段
- 第八節 Via 字段
- 第九節 Warning 字段
- 第四章 HTTP請求首部字段
- 第一節 Accept 字段
- 第二節 Accept-Charset 字段
- 第三節 Accept-Encoding 字段
- 第四節 Accept-Language 字段
- 第五節 Authorization 字段
- 第六節 Expect 字段
- 第七節 From 字段
- 第八節 Host 字段
- 第九節 If-Match 字段
- 第十節 If-Modified-Since 字段
- 第十一節 If-None-Match 字段
- 第十二節 If-Range 字段
- 第十三節 If-Unmodified-Since 字段
- 第十四節 Max-Forwards 字段
- 第十五節 Proxy-Authorization 字段
- 第十六節 Range 字段
- 第十七節 Referer 字段
- 第十八節 TE 字段
- 第十九節 User-Agent 字段
- 第五章 HTTP響應首部字段
- 第一節 Accept-Ranges 字段
- 第二節 Age 字段
- 第三節 ETge 字段
- 第四節 Location 字段
- 第五節 Proxy-Authenticate 字段
- 第六節 Retry-After 字段
- 第七節 Server 字段
- 第八節 Vary 字段
- 第九節 WWW-Authenticate 字段
- 第六章 HTTP實體首部字段
- 第一節 Allow 字段
- 第二節 Content-Encoding字段
- 第三節 Content-Language 字段
- 第四節 Content-Length 字段
- 第五節 Content-Location 字段
- 第六節 Content-MD5 字段
- 第七節 Content-Range 字段
- 第八節 Content-Type 字段
- 第九節 Expires 字段
- 第十節 Last-Modified 字段
- 第七章 Cookie相關和其他的首部字段