Spring MVC 在控制器中設(shè)置Cache-Control、ETag和Last-Modified響應(yīng)頭

2018-07-26 14:45 更新

控制器能處理帶有'Cache-Control'、'ETag'及/或'If-Modified-Since'頭的請(qǐng)求,如果服務(wù)端在響應(yīng)中設(shè)置了'Cache-Control'響應(yīng)頭,那么我們推薦在控制器內(nèi)對(duì)這些請(qǐng)求頭進(jìn)行處理。這涉及一些工作:計(jì)算最后更改時(shí)間long和/或請(qǐng)求的ETag值、與請(qǐng)求頭的'If-Modified-Since'值做比較,并且在資源未更改的情況下在響應(yīng)中返回一個(gè)304(資源未更改)狀態(tài)碼。

正如在"使用HttpEntity"一節(jié)中所講,控制器可以通過HttpEntity類與請(qǐng)求/響應(yīng)交互。返回ResponseEntity的控制器可以在響應(yīng)中包含HTTP緩存的信息,如下代碼所示:

@RequestMapping("/book/{id}")
public ResponseEntity<Book> showBook(@PathVariable Long id) {

    Book book = findBook(id);
    String version = book.getVersion();

    return ResponseEntity
                .ok()
                .cacheControl(CacheControl.maxAge(30, TimeUnit.DAYS))
                .eTag(version) // 這里也能操作最后修改時(shí)間lastModified,只不過沒有一一展示
                .body(book);
}

這樣做不僅會(huì)在響應(yīng)頭中設(shè)置'ETag''Cache-Control'相關(guān)的信息,同時(shí)也會(huì) 嘗試將響應(yīng)狀態(tài)碼設(shè)置為HTTP 304 Not Modified(資源未修改)及將響應(yīng)體置空——如果客戶端攜帶的請(qǐng)求頭信息與控制器設(shè)置的緩存信息能夠匹配的話。

如果希望在@RequestMapping方法上也能完成同樣的事,那么你可以這樣做:

@RequestMapping
public String myHandleMethod(WebRequest webRequest, Model model) {

    long lastModified = // 1. 應(yīng)用相關(guān)的方式計(jì)算得到(application-specific calculation)

    if (request.checkNotModified(lastModified)) {
        // 2. 快速退出 — 不需要更多處理了
        return null;
    }

    // 3. 若資源更改了,那么再進(jìn)行請(qǐng)求處理階段,一般而言是準(zhǔn)備響應(yīng)內(nèi)容
    model.addAttribute(...);
    return "myViewName";
}

這里最重要的兩個(gè)地方是:調(diào)用request.checkNotModified(lastModified)方法,以及返回null。前者(方法調(diào)用)在返回true之前會(huì)將響應(yīng)狀態(tài)碼設(shè)為304;而后者,在檢查是否更改的方法調(diào)用返回true的基礎(chǔ)上直接將方法返回,這會(huì)通知Spring MVC不再對(duì)請(qǐng)求做任何處理。

另外要注意的是,檢查資源是否發(fā)生了更改有3種方式:

  • request.checkNotModified(lastModified)方法會(huì)將傳入的參數(shù)值(最后修改時(shí)間)與請(qǐng)求頭'If-Modified-Since'的值進(jìn)行比較
  • request.checkNotModified(eTag)方法會(huì)將傳入的參數(shù)值與請(qǐng)求頭'ETag'的值進(jìn)行比較
  • request.checkNotModified(eTag, lastModified)方法會(huì)同時(shí)進(jìn)行以上兩種比較。也即是說(shuō),只有在兩個(gè)比較都被判定為未修改時(shí),服務(wù)器才會(huì)返回一個(gè)304響應(yīng)狀態(tài)碼HTTP 304 Not Modified(資源未修改)


以上內(nèi)容是否對(duì)您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號(hào)
微信公眾號(hào)

編程獅公眾號(hào)