成人午夜视频全免费观看高清-秋霞福利视频一区二区三区-国产精品久久久久电影小说-亚洲不卡区三一区三区一区

HTTP緩存的作用和規(guī)則簡(jiǎn)介

本篇內(nèi)容介紹了“HTTP緩存的作用和規(guī)則簡(jiǎn)介”的有關(guān)知識(shí),在實(shí)際案例的操作過(guò)程中,不少人都會(huì)遇到這樣的困境,接下來(lái)就讓小編帶領(lǐng)大家學(xué)習(xí)一下如何處理這些情況吧!希望大家仔細(xì)閱讀,能夠?qū)W有所成!

創(chuàng)新互聯(lián)擁有網(wǎng)站維護(hù)技術(shù)和項(xiàng)目管理團(tuán)隊(duì),建立的售前、實(shí)施和售后服務(wù)體系,為客戶提供定制化的成都做網(wǎng)站、網(wǎng)站制作、網(wǎng)站維護(hù)、成都機(jī)柜租用解決方案。為客戶網(wǎng)站安全和日常運(yùn)維提供整體管家式外包優(yōu)質(zhì)服務(wù)。我們的網(wǎng)站維護(hù)服務(wù)覆蓋集團(tuán)企業(yè)、上市公司、外企網(wǎng)站、商城建設(shè)、政府網(wǎng)站等各類型客戶群體,為全球近千家企業(yè)提供全方位網(wǎng)站維護(hù)、服務(wù)器維護(hù)解決方案。

前言

HTTP 緩存機(jī)制作為 Web 應(yīng)用性能優(yōu)化的重要手段,對(duì)于從事 Web 開(kāi)發(fā)的同學(xué)們來(lái)說(shuō),應(yīng)該是知識(shí)體系的基礎(chǔ)環(huán)節(jié),也是想要成為前端架構(gòu)的必備技能。

緩存的作用

我們?yōu)槭裁词褂镁彺妫且驗(yàn)榫彺婵梢越o我們的 Web 項(xiàng)目帶來(lái)以下好處,以提高性能和用戶體驗(yàn)。

  • 加快了瀏覽器加載網(wǎng)頁(yè)的速度;

  • 減少了冗余的數(shù)據(jù)傳輸,節(jié)省網(wǎng)絡(luò)流量和帶寬;

  • 減少服務(wù)器的負(fù)擔(dān),大大提高了網(wǎng)站的性能。

由于從本地緩存讀取靜態(tài)資源,加快瀏覽器的網(wǎng)頁(yè)加載速度是一定的,也確實(shí)的減少了數(shù)據(jù)傳輸,就提高網(wǎng)站性能來(lái)說(shuō),可能一兩個(gè)用戶的訪問(wèn)對(duì)于減小服務(wù)器的負(fù)擔(dān)沒(méi)有明顯效果,但如果這個(gè)網(wǎng)站在高并發(fā)的情況下,使用緩存對(duì)于減小服務(wù)器壓力和整個(gè)網(wǎng)站的性能都會(huì)發(fā)生質(zhì)的變化。

緩存規(guī)則簡(jiǎn)介

為了方便理解,我們認(rèn)為瀏覽器存在一個(gè)緩存數(shù)據(jù)庫(kù),用于存儲(chǔ)緩存信息(實(shí)際上靜態(tài)資源是被緩存到了內(nèi)存和磁盤(pán)中),在瀏覽器第一次請(qǐng)求數(shù)據(jù)時(shí),此時(shí)緩存數(shù)據(jù)庫(kù)沒(méi)有對(duì)應(yīng)的緩存數(shù)據(jù),則需要請(qǐng)求服務(wù)器,服務(wù)器會(huì)將緩存規(guī)則和數(shù)據(jù)返回,瀏覽器將緩存規(guī)則和數(shù)據(jù)存儲(chǔ)進(jìn)緩存數(shù)據(jù)庫(kù)。

HTTP緩存的作用和規(guī)則簡(jiǎn)介

當(dāng)瀏覽器地址欄輸入地址后請(qǐng)求的 index.html 是不會(huì)被緩存的,但 index.html 內(nèi)部請(qǐng)求的其他資源會(huì)遵循緩存策略,HTTP 緩存有多種規(guī)則,根據(jù)是否需要向服務(wù)器發(fā)送請(qǐng)求主要分為兩大類,強(qiáng)制緩存和協(xié)商緩存。

強(qiáng)制緩存

1、強(qiáng)制緩存流程

強(qiáng)制緩存是第一次訪問(wèn)服務(wù)器獲取數(shù)據(jù)后,在有效時(shí)間內(nèi)不會(huì)再請(qǐng)求服務(wù)器,而是直接使用緩存數(shù)據(jù),強(qiáng)制緩存的流程如下。

HTTP緩存的作用和規(guī)則簡(jiǎn)介

2、強(qiáng)制緩存判斷到期時(shí)間

那么如何判斷緩存是否到期呢?其實(shí)還是根據(jù)第一次訪問(wèn)時(shí)服務(wù)器的響應(yīng)頭來(lái)實(shí)現(xiàn)的,在 HTTP 1.0 版本和 HTTP 1.1 版本有所不同。

HTTP 1.0 版本,服務(wù)器使用的響應(yīng)頭字段為 Expires,值為未來(lái)的絕對(duì)時(shí)間(時(shí)間戳),瀏覽器請(qǐng)求時(shí)的當(dāng)前時(shí)間超過(guò)了 Expires 設(shè)置的時(shí)間,代表緩存失效,需要再次向服務(wù)器發(fā)送請(qǐng)求,否則都會(huì)直接從緩存數(shù)據(jù)庫(kù)中獲取數(shù)據(jù)。

HTTP 1.1 版本,服務(wù)器使用的響應(yīng)頭字段為 Cache-Control,有多個(gè)值,意義各不相同。

  • private:客戶端可以緩存;

  • public:客戶端和代理服務(wù)器都可以緩存(對(duì)于前端而言,可以認(rèn)為與 private 效果相同);

  • max-age=xxx:緩存的內(nèi)容將在 xxx 秒后過(guò)期(相對(duì)時(shí)間,秒為單位);

  • no-cache:需要使用協(xié)商緩存(后面介紹)來(lái)驗(yàn)證數(shù)據(jù)是否過(guò)期;

  • no-store:所有內(nèi)容都不會(huì)緩存,強(qiáng)制緩存和協(xié)商緩存都不會(huì)觸發(fā)。

Cache-Control 的值中最常用的為 max-age=xxx,緩存本身就是為了數(shù)據(jù)傳輸?shù)膬?yōu)化和性能而存在的,所以 no-store 幾乎不會(huì)使用。

注意:在 HTTP 1.0 版本中,Expires 字段的絕對(duì)時(shí)間是從服務(wù)器獲取的,由于請(qǐng)求需要時(shí)間,所以瀏覽器的請(qǐng)求時(shí)間與服務(wù)器接收到請(qǐng)求所獲取的時(shí)間是存在誤差的,這也導(dǎo)致了緩存命中的誤差,在 HTTP 1.1 版本中,因?yàn)?Cache-Control 的值 max-age=xxx 中的 xxx 是以秒為單位的相對(duì)時(shí)間,所以在瀏覽器接收到資源后開(kāi)始倒計(jì)時(shí),規(guī)避了 HTTP 1.0 中緩存命中存在誤差的缺點(diǎn),為了兼容低版本 HTTP 協(xié)議,正常開(kāi)發(fā)中兩種響應(yīng)頭會(huì)同時(shí)使用,HTTP 1.1 版本的實(shí)現(xiàn)優(yōu)先級(jí)高于 HTTP 1.0。

3、通過(guò) Network 查看強(qiáng)制緩存

我們通過(guò) Chrome 瀏覽器的開(kāi)發(fā)者工具,打開(kāi) NetWork 查看強(qiáng)制緩存的相關(guān)信息。

HTTP緩存的作用和規(guī)則簡(jiǎn)介

上面是百度網(wǎng)站 Logo 圖片的響應(yīng),我們可以清楚的看到,其中兼容了 HTTP 1.0HTTP 1.1 版本,并使用強(qiáng)制緩存存儲(chǔ)了 10 年。

下面看一看通過(guò)緩存取出的數(shù)據(jù)在 Network 中與其他資源的區(qū)別。

HTTP緩存的作用和規(guī)則簡(jiǎn)介

其實(shí)緩存的儲(chǔ)存是內(nèi)存和磁盤(pán)兩個(gè)位置,由當(dāng)前瀏覽器本身的策略決定,比較隨機(jī),從內(nèi)存的緩存中取出的數(shù)據(jù)會(huì)顯示 (from memory cache),從磁盤(pán)的緩存中取出的數(shù)據(jù)會(huì)顯示 (from disk cache)。

4、NodeJS 服務(wù)器實(shí)現(xiàn)強(qiáng)制緩存

// 強(qiáng)制緩存
const http = require("http");
const url = require("url");
const path = require("path");
const mime = require("mime");
const fs = require("fs");

const server = http.createServer((req, res) => {
 let { pathname } = url.parse(req.url, true);
 pathname = pathname !== "/" ? pathname : "/index.html";

 // 獲取讀取文件的絕對(duì)路徑
 let p = path.join(__dirname, pathname);

 // 查看路徑是否合法
 fs.access(p, err => {
  // 路徑不合法則直接中斷連接
  if (err) return res.end("Not Found");

  // 設(shè)置強(qiáng)制緩存
  res.setHeader("Expires", new Date(Date.now() + 30000).toGMTString());
  res.setHeader("Cache-Control", "max-age=30");

  // 設(shè)置文件類型并響應(yīng)給瀏覽器
  res.setHeader("Content-Type", `${mime.getType(p)};charset=utf8`);
  fs.createReadStream(p).pipe(res);
 });
});

server.listen(3000, () => {
 console.log("server start 3000");
});

上面 mime 模塊的 getType 方法可以成功返回傳入路徑下文件對(duì)應(yīng)的文件類型,如 text/htmlapplication/javascript 等,是第三方模塊,使用之前需要安裝。

npm install mime

協(xié)商緩存

1、協(xié)商緩存流程

協(xié)商緩存又叫對(duì)比緩存,設(shè)置協(xié)商緩存后,第一次訪問(wèn)服務(wù)器獲取數(shù)據(jù)時(shí),服務(wù)器會(huì)將數(shù)據(jù)和緩存標(biāo)識(shí)一起返回給瀏覽器,客戶端會(huì)將數(shù)據(jù)和標(biāo)識(shí)存入緩存數(shù)據(jù)庫(kù)中,下一次請(qǐng)求時(shí),會(huì)先去緩存中取出緩存標(biāo)識(shí)發(fā)送給服務(wù)器進(jìn)行詢問(wèn),當(dāng)服務(wù)器數(shù)據(jù)更改時(shí)會(huì)更新標(biāo)識(shí),所以服務(wù)器拿到瀏覽器發(fā)來(lái)的標(biāo)識(shí)進(jìn)行對(duì)比,相同代表數(shù)據(jù)未更改,響應(yīng)瀏覽器通知數(shù)據(jù)未更改,瀏覽器會(huì)去緩存中獲取數(shù)據(jù),如果標(biāo)識(shí)不同,代表服務(wù)器更改過(guò)數(shù)據(jù),所以會(huì)將新的數(shù)據(jù)和新的標(biāo)識(shí)返回瀏覽器,瀏覽器會(huì)將新的數(shù)據(jù)和標(biāo)識(shí)存入緩存中,協(xié)商緩存的流程如下。

HTTP緩存的作用和規(guī)則簡(jiǎn)介

協(xié)商緩存和強(qiáng)制緩存不同的是,協(xié)商緩存每次請(qǐng)求都需要跟服務(wù)器通信,而且命中緩存服務(wù)器返回狀態(tài)碼不再是 200,而是 304。

2、協(xié)商緩存判斷標(biāo)識(shí)

強(qiáng)制緩存是通過(guò)過(guò)期時(shí)間來(lái)控制是否訪問(wèn)服務(wù)器,而協(xié)商緩存每次都要與服務(wù)器交互對(duì)比緩存標(biāo)識(shí),同樣的,對(duì)于協(xié)商緩存的實(shí)現(xiàn)在 HTTP 1.0 版本和 HTTP 1.1 版本也有所不同。

HTTP 1.0 版本中,服務(wù)器通過(guò) Last-Modified 響應(yīng)頭來(lái)設(shè)置緩存標(biāo)識(shí),通常取請(qǐng)求數(shù)據(jù)的最后修改時(shí)間(絕對(duì)時(shí)間)作為值,而瀏覽器將接收到返回的數(shù)據(jù)和標(biāo)識(shí)存入緩存,再次請(qǐng)求會(huì)自動(dòng)發(fā)送 If-Modified-Since 請(qǐng)求頭,值為之前返回的最后修改時(shí)間(標(biāo)識(shí)),服務(wù)器取出 If-Modified-Since 的值與數(shù)據(jù)的上次修改時(shí)間對(duì)比,如果上次修改時(shí)間大于了 If-Modified-Since 的值,說(shuō)明被修改過(guò),則通過(guò) Last-Modified 響應(yīng)頭返回新的最后修改時(shí)間和新的數(shù)據(jù),否則未被修改,返回狀態(tài)碼 304 通知瀏覽器命中緩存。

HTTP 1.1 版本中,服務(wù)器通過(guò) Etag 響應(yīng)頭來(lái)設(shè)置緩存標(biāo)識(shí)(唯一標(biāo)識(shí),像一個(gè)指紋一樣,生成規(guī)則由服務(wù)器來(lái)決定),瀏覽器接收到數(shù)據(jù)和唯一標(biāo)識(shí)后存入緩存,下次請(qǐng)求時(shí),通過(guò) If-None-Match 請(qǐng)求頭將唯一標(biāo)識(shí)帶給服務(wù)器,服務(wù)器取出唯一標(biāo)識(shí)與之前的標(biāo)識(shí)對(duì)比,不同,說(shuō)明修改過(guò),返回新標(biāo)識(shí)和數(shù)據(jù),相同,則返回狀態(tài)碼 304 通知瀏覽器命中緩存。

HTTP 協(xié)商緩存策略流程圖如下:

HTTP緩存的作用和規(guī)則簡(jiǎn)介

注意:使用協(xié)商緩存時(shí) HTTP 1.0 版本還是不太靠譜,假設(shè)一個(gè)文件增加了一個(gè)字符后又刪除了,文件相當(dāng)于沒(méi)更改,但是最后修改時(shí)間變了,會(huì)被當(dāng)作修改處理,本應(yīng)該命中緩存,服務(wù)器卻重新發(fā)送了數(shù)據(jù),因此 HTTP 1.1 中使用的 Etag 唯一標(biāo)識(shí)是根據(jù)文件內(nèi)容或摘要生成的,保證了只要文件內(nèi)容不變,則一定會(huì)命中緩存,為了兼容低版本 HTTP 協(xié)議,開(kāi)發(fā)中兩種響應(yīng)頭也會(huì)同時(shí)使用,同樣 HTTP 1.1 版本的實(shí)現(xiàn)優(yōu)先級(jí)高于 HTTP 1.0

3、通過(guò) Network 查看協(xié)商緩存

我們同樣通過(guò) Chrome 瀏覽器的開(kāi)發(fā)者工具,打開(kāi) NetWork 查看協(xié)商緩存的相關(guān)信息。

再次請(qǐng)求服務(wù)器的請(qǐng)求頭信息:

HTTP緩存的作用和規(guī)則簡(jiǎn)介

命中協(xié)商緩存的響應(yīng)頭信息:

HTTP緩存的作用和規(guī)則簡(jiǎn)介

下面看一看通過(guò)協(xié)商緩存取出的數(shù)據(jù)在 Network 中與第一次加載的區(qū)別。

第一次請(qǐng)求:

HTTP緩存的作用和規(guī)則簡(jiǎn)介

緩存后請(qǐng)求:

HTTP緩存的作用和規(guī)則簡(jiǎn)介

通過(guò)兩圖的對(duì)比,我們可以發(fā)現(xiàn),協(xié)商緩存生效時(shí)的狀態(tài)碼為 304,并且報(bào)文大小和請(qǐng)求時(shí)間大大減少,原因是服務(wù)端在進(jìn)行標(biāo)識(shí)比對(duì)后只返回了 header 部分,通過(guò)狀態(tài)碼來(lái)通知瀏覽器使用緩存,不再需要將報(bào)文主體部分一起返回給瀏覽器。

4、NodeJS 服務(wù)器實(shí)現(xiàn)協(xié)商緩存

// 協(xié)商緩存
const http = require("http");
const url = require("url");
const path = require("path");
const mime = require("mime");
const fs = require("fs");0
const crytpo = require("crytpo");

const server = http.createServer((req, res) => {
 let { pathname } = url.parse(req.url, true);
 pathname = pathname !== "/" ? pathname : "/index.html";

 // 獲取讀取文件的絕對(duì)路徑
 let p = path.join(__dirname, pathname);

 // 查看路徑是否合法
 fs.stat(p, (err, statObj) => {
  // 路徑不合法則直接中斷連接
  if (err) return res.end("Not Found");

  let md5 = crypto.createHash("md5"); // 創(chuàng)建加密的轉(zhuǎn)換流
  let rs = fs.createReadStream(p); // 創(chuàng)建可讀流

  // 讀取文件內(nèi)容并加密
  rs.on("data", data => md5.update(data));

  rs.on("end", () => {
   let ctime = statObj.ctime.toGMTString(); // 獲取文件最后修改時(shí)間
   let flag = md5.digest("hex"); // 獲取加密后的唯一標(biāo)識(shí)

   // 獲取協(xié)商緩存的請(qǐng)求頭
   let ifModifiedSince = req.headers["if-modified-since"];
   let ifNoneMatch = req.headers["if-none-match"];

   if (ifModifiedSince === ctime || ifNoneMatch === flag) {
    res.statusCode = 304;
    res.end();
   } else {
    // 設(shè)置協(xié)商緩存
    res.setHeader("Last-Modified", ctime);
    res.setHeader("Etag", flag);

    // 設(shè)置文件類型并響應(yīng)給瀏覽器
    res.setHeader("Content-Type", `${mime.getType(p)};charset=utf8`);
    rs.pipe(res);
   }
  });
 });
});

server.listen(3000, () => {
 console.log("server start 3000");
});

在上面的代碼中是通過(guò)可讀流讀取文件內(nèi)容,并通過(guò) crypto 模塊進(jìn)行了 md5 加密后的結(jié)果作為了唯一標(biāo)識(shí),這樣就能保證只要文件內(nèi)容不變,就會(huì)命中緩存,其中兼容了 HTTP 1.0HTTP 1.1 兩個(gè)版本,只要滿足一個(gè)則直接返回 304 通知瀏覽器命中緩存。

注意:其實(shí)讀取文件內(nèi)容加密這種做法并不可取,假如讀取的是大文件,在讀取文件內(nèi)容和進(jìn)行 md5 加密這個(gè)過(guò)程會(huì)非常消耗時(shí)間,所以在開(kāi)發(fā)中要針對(duì)業(yè)務(wù)的實(shí)際情況選擇可以保證服務(wù)器性能的方式生成唯一標(biāo)識(shí),比如根據(jù)文件的摘要。

總結(jié)

為了使緩存策略更加健壯、靈活,HTTP 1.0 版本 和 HTTP 1.1 版本的緩存策略會(huì)同時(shí)使用,甚至強(qiáng)制緩存和協(xié)商緩存也會(huì)同時(shí)使用,對(duì)于強(qiáng)制緩存,服務(wù)器通知瀏覽器一個(gè)緩存時(shí)間,在緩存時(shí)間內(nèi),下次請(qǐng)求,直接使用緩存,超出有效時(shí)間,執(zhí)行協(xié)商緩存策略,對(duì)于協(xié)商緩存,將緩存信息中的 EtagLast-Modified 通過(guò)請(qǐng)求頭 If-None-MatchIf-Modified-Since 發(fā)送給服務(wù)器,由服務(wù)器校驗(yàn)同時(shí)設(shè)置新的強(qiáng)制緩存,校驗(yàn)通過(guò)并返回 304 狀態(tài)碼時(shí),瀏覽器直接使用緩存,如果協(xié)商緩存也未命中,則服務(wù)器重新設(shè)置協(xié)商緩存的標(biāo)識(shí)。

“HTTP緩存的作用和規(guī)則簡(jiǎn)介”的內(nèi)容就介紹到這里了,感謝大家的閱讀。如果想了解更多行業(yè)相關(guān)的知識(shí)可以關(guān)注創(chuàng)新互聯(lián)網(wǎng)站,小編將為大家輸出更多高質(zhì)量的實(shí)用文章!

網(wǎng)頁(yè)名稱:HTTP緩存的作用和規(guī)則簡(jiǎn)介
本文來(lái)源:http://jinyejixie.com/article26/gggdjg.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供手機(jī)網(wǎng)站建設(shè)網(wǎng)站內(nèi)鏈、網(wǎng)站建設(shè)、網(wǎng)站策劃、網(wǎng)站設(shè)計(jì)公司Google

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)

外貿(mào)網(wǎng)站制作
二手房| 和龙市| 大渡口区| 合山市| 新源县| 施秉县| 苍南县| 临夏县| 基隆市| 廉江市| 宁都县| 客服| 崇礼县| 长治市| 精河县| 滁州市| 出国| 唐河县| 黔南| 邵阳县| 卓资县| 新营市| 乌兰浩特市| 塔河县| 台山市| 保定市| 登封市| 东平县| 雷州市| 那坡县| 盐边县| 满城县| 隆化县| 涿州市| 鹿泉市| 沙湾县| 始兴县| 义马市| 吕梁市| 新化县| 桑植县|