การเกิดของคุกกี้
เนื่องจากโปรโตคอล HTTP ไร้สัญชาติบริการฝั่งเซิร์ฟเวอร์จะต้องเป็นสถานะ วัตถุประสงค์ดั้งเดิมของการเกิดของคุกกี้คือการจัดเก็บข้อมูลสถานะในเว็บเพื่อใช้งานง่ายบนฝั่งเซิร์ฟเวอร์ ตัวอย่างเช่นตรวจสอบว่าผู้ใช้กำลังเยี่ยมชมเว็บไซต์เป็นครั้งแรกหรือไม่ ข้อกำหนดล่าสุดคือ RFC 6265 ซึ่งเป็นข้อกำหนดที่ใช้โดยเซิร์ฟเวอร์เบราว์เซอร์
การประมวลผลของคุกกี้แบ่งออกเป็น:
เซิร์ฟเวอร์ส่งคุกกี้เช่นไคลเอนต์
เบราว์เซอร์บันทึกคุกกี้
หลังจากนั้นทุกครั้งที่มีการร้องขอคำขอ HTTP เบราว์เซอร์จะส่งคุกกี้ไปยังเซิร์ฟเวอร์
ส่งและแยกวิเคราะห์ทางฝั่งเซิร์ฟเวอร์
ส่งคุกกี้
คุกกี้ฝั่งเซิร์ฟเวอร์ที่ส่งโดยไคลเอนต์จะถูกนำไปใช้ผ่านแพ็คเก็ตตอบกลับ HTTP ในการตั้งค่าการดูแลคุกกี้ที่ต้องส่งโดยลูกค้าจะถูกตั้งค่า รูปแบบคุกกี้มีดังนี้:
set-cookie: "name = value; domain = .domain.com; path =/; expires = sat, 11 มิ.ย. 2016 11:29:42 gmt; httponly;
โดยที่ชื่อ = ค่าเป็นตัวเลือกที่ต้องการและอื่น ๆ เป็นทางเลือก องค์ประกอบหลักของคุกกี้มีดังนี้:
ชื่อ: ชื่อคุกกี้ที่ไม่ซ้ำกันและชัดเจน โดยทั่วไปแล้วชื่อของคุกกี้เป็นตัวพิมพ์ใหญ่
ค่า: ค่าสตริงที่เก็บไว้ในคุกกี้ เป็นการดีที่สุดที่จะ URL เข้ารหัสชื่อและค่าของคุกกี้
โดเมน: คุกกี้ใช้ได้กับโดเมนใด คำขอทั้งหมดที่ส่งไปยังโดเมนนี้จะมีข้อมูลคุกกี้นี้ ค่านี้สามารถมีโดเมนย่อย (เช่น:
yq.aliyun.com) หรือไม่สามารถรวมได้ (ตัวอย่างเช่น: .aliyun.com มันถูกต้องสำหรับโดเมนย่อยทั้งหมดของ Aliyun.com)
เส้นทาง: ระบุเส้นทางที่ได้รับผลกระทบจากคุกกี้นี้ เบราว์เซอร์จะส่งคุกกี้ตามการกำหนดค่านี้เช่นการจับคู่พา ธ ในโดเมนที่ระบุ
หมดอายุ: เวลาหมดอายุการประทับเวลาระบุว่าควรลบคุกกี้เมื่อใด (นั่นคือเมื่อคุกกี้ควรหยุดส่งไปยังเซิร์ฟเวอร์) หากคุณไม่ได้ตั้งค่าการประทับเวลานี้เบราว์เซอร์จะลบคุกกี้ทั้งหมดเมื่อปิดหน้า อย่างไรก็ตามคุณสามารถตั้งค่าเวลาการลบด้วยตัวเอง ค่านี้อยู่ในรูปแบบเวลา GMT หากเวลาไคลเอนต์และเซิร์ฟเวอร์ไม่สอดคล้องกันจะมีการเบี่ยงเบนเมื่อใช้หมดอายุ
Max-Age: ฟังก์ชั่นเดียวกับที่หมดอายุใช้เพื่อบอกเบราว์เซอร์ว่าคุกกี้นี้จะหมดอายุนานแค่ไหน (ในไม่กี่วินาที) แทนที่จะเป็นจุดเวลาคงที่ ภายใต้สถานการณ์ปกติอายุสูงสุดมีลำดับความสำคัญสูงกว่าการหมดอายุ
httponly: แจ้งให้เบราว์เซอร์ไม่อนุญาตให้เอกสารสคริปต์ Cookie เปลี่ยนค่านี้และค่านี้ยังไม่ปรากฏใน document.cookie แต่คุกกี้นี้จะยังคงดำเนินการตามคำขอ HTTP โปรดทราบว่าแม้ว่าค่านี้จะไม่สามารถใช้ได้ในสคริปต์ แต่ก็ยังคงมีอยู่ในไดเรกทอรีการติดตั้งเบราว์เซอร์เป็นไฟล์ การตั้งค่านี้มักจะตั้งค่าไว้ที่ฝั่งเซิร์ฟเวอร์
Secure: Security Flag หลังจากระบุแล้วจะสามารถส่งไปยังเซิร์ฟเวอร์เมื่อใช้ลิงก์ SSL เท่านั้น หากเป็นลิงค์ HTTP ข้อมูลนี้จะไม่ถูกส่งผ่าน แม้ว่าจะมีการตั้งค่าแอตทริบิวต์ที่ปลอดภัย แต่ก็ไม่ได้หมายความว่าคนอื่นไม่สามารถเห็นข้อมูลคุกกี้ที่บันทึกไว้ในเครื่องของคุณได้ดังนั้นอย่าใส่ข้อมูลที่สำคัญลงในคุกกี้และตั้งค่าไว้ที่ฝั่งเซิร์ฟเวอร์
ตัวอย่างของคุกกี้มีดังนี้:
var http = require ('http'); var fs = ต้องการ ('fs'); http.createserver (ฟังก์ชั่น (req, res) {res.setheader ('สถานะ', '200 ok'); res.setheader ('set-cookie', ' World '); Res.end ();}). ฟัง (8888);การตั้งค่า Set-Cookie โดยตรงเป็นต้นฉบับเกินไป เราสามารถห่อหุ้มกระบวนการตั้งค่าคุกกี้ได้ดังนี้:
var serilize = function (ชื่อ, val, ตัวเลือก) {ถ้า (! ชื่อ) {โยนข้อผิดพลาดใหม่ ("cooleie ต้องมีชื่อ"); } var enc = encodeuricomponent; var parts = []; val = (val! == null && val! == undefined)? val.tostring (): ""; ตัวเลือก = ตัวเลือก || - parts.push (enc (ชื่อ) + "=" + enc (val)); // จะต้องมีสองจุดในโดเมนถ้า (ตัวเลือกโดเมน) {parts.push ("domain =" + opotions.domain); } if (options.path) {parts.push ("path =" + opotions.path); } // หากคุณไม่ได้ตั้งค่าหมดอายุและเบราว์เซอร์อายุสูงสุดจะล้างคุกกี้เมื่อหน้าถูกปิดหาก (ตัวเลือกที่มีคนงาน) {parts.push ("expires =" + opotions.expires.togmtstring ()); } if (ตัวเลือก maxage && ตัวเลือก typeof.maxage === "number") {parts.push ("max-age =" + opotions.maxage); } if (options.httponly) {parts.push ("httponly"); } if (opptionss.secure) {parts.push ("ปลอดภัย"); } return parts.join (";");}ควรสังเกตว่าหากคุกกี้ถูกตั้งค่าเป็นเวลาที่ผ่านมาเบราว์เซอร์จะลบคุกกี้ทันที นอกจากนี้รายการโดเมนจะต้องมีสองจุดดังนั้นจึงไม่สามารถตั้งค่าเป็น localhost:
สิ่งที่ไม่ชัดเจนสำหรับฉันที่นี่และทำให้ฉันสับสนโดยสิ้นเชิงสักพักหนึ่งคือชื่อโดเมนจะต้องมีจุดอย่างน้อยสองจุด (.) ดังนั้น 'localhost' ไม่ถูกต้องและเบราว์เซอร์จะปฏิเสธที่จะตั้งคุกกี้!
คุกกี้การวิเคราะห์ฝั่งเซิร์ฟเวอร์
คุกกี้สามารถตั้งค่าโดเมนและเส้นทางที่แตกต่างกันดังนั้นสำหรับค่าชื่อเดียวกันสามารถทำซ้ำได้ภายใต้เส้นทางที่แตกต่างกันในโดเมนที่แตกต่างกันและเส้นทางที่แตกต่างกัน เบราว์เซอร์จะเรียงลำดับคำสั่งซื้อตามลำดับที่ตรงกับ URL หรือที่อยู่หน้าเว็บที่ร้องขอมากที่สุด
ดังนั้นเมื่อคุกกี้ส่งผ่านไปยังฝั่งเซิร์ฟเวอร์ในด้านปัจจุบันมีค่าชื่อที่ซ้ำกันหลายค่าเราต้องการเพียงอันที่ตรงกับที่มากที่สุดนั่นคืออันแรก รหัสการแยกวิเคราะห์ฝั่งเซิร์ฟเวอร์มีดังนี้:
var parse = function (cstr) {ถ้า (! cstr) {return null; } var dec = decodeuricomponent; var cookies = {}; var parts = cstr.split (// s*;/s*/g); parts.foreach (ฟังก์ชัน (p) {var pos = p.indexof ('='); // ชื่อและค่าจะต้องถูกเข้ารหัสก่อนที่คุกกี้จะถูกเก็บไว้ชื่อ var name = pos> -1? dec (p.substr (0, pos)): p; var val = pos> -1? dec (p.substr (pos + 1)) คุกกี้ [ชื่อ] = Val; กลับมาคุกกี้;}การเข้าถึงลูกค้า
เบราว์เซอร์จัดการคุกกี้ที่ผ่านพื้นหลังและอนุญาตให้นักพัฒนาใช้เอกสาร Cookies ใน JavaScript เพื่อเข้าถึงคุกกี้ แต่อินเทอร์เฟซนี้มีความอ่อนแอมากที่จะใช้ มันจะแสดงพฤติกรรมที่แตกต่างกันเนื่องจากวิธีการต่าง ๆ ที่ใช้
เมื่อใช้เพื่อรับค่าแอตทริบิวต์เอกสาร Cookie ส่งคืนสตริงทั้งหมดที่มีอยู่ในหน้าปัจจุบัน (ขึ้นอยู่กับโดเมนของคุกกี้เส้นทางเวลาหมดอายุและการตั้งค่าความปลอดภัย) รูปแบบของสตริงมีดังนี้:
"name1 = value1; name2 = value2; name3 = value3";
เมื่อใช้ในการตั้งค่าคุณสมบัติเอกสาร Cookie สามารถตั้งค่าเป็นสตริงคุกกี้ใหม่ สตริงนี้ถูกตีความและเพิ่มเข้าไปในคอลเลกชันคุกกี้ที่มีอยู่ ชอบ:
document.cookie = "_fa = aaaffffasdsf; domain = .dojotoolkit.org; path =/"
การตั้งค่า Document.Cookie ไม่ได้แทนที่คุกกี้เว้นแต่เส้นทางโดเมนค่าชื่อที่ตั้งไว้จะถูกทำซ้ำด้วยคุกกี้ที่มีอยู่
เนื่องจากมันไม่สะดวกมากที่จะอ่านและเขียนคุกกี้เราจึงสามารถห่อหุ้มฟังก์ชั่นบางอย่างเพื่อจัดการคุกกี้ส่วนใหญ่สำหรับการเพิ่มการดัดแปลงและการลบคุกกี้
var cookieutils = {get: function (ชื่อ) {var cookiename = encodeuricomponent (ชื่อ) + "="; // รับชื่อที่ตรงกันมากที่สุด Vale var cookiestart = document.cookie.indexof (cookiename); var cookievelue = null; if (cookiestart> -1) {// จาก cookiestart var cookieend = document.cookie.indexof (';', cookiestart); // จาก = หลัง = (cookieend> -1) {cookieViewalue = decodeuricomponent (document.cookie.substring (cookiestart + cookiename.length, cookieend)); } else {cookieVieLue = decodeuricomponent (document.cookie.substring (cookiestart + cookiename.length, docound.cookie.length)); }} return cookievalue; }, set: function (ชื่อ, val, ตัวเลือก) {ถ้า (! ชื่อ) {โยนข้อผิดพลาดใหม่ ("cooliie ต้องมีชื่อ"); } var enc = encodeuricomponent; var parts = []; val = (val! == null && val! == undefined)? val.tostring (): ""; ตัวเลือก = ตัวเลือก || - parts.push (enc (ชื่อ) + "=" + enc (val)); // โดเมนจะต้องมีสองจุดถ้า (ตัวเลือกโดเมน) {parts.push ("domain =" + opotions.domain); } if (options.path) {parts.push ("path =" + opotions.path); } // หากคุณไม่ได้ตั้งค่าหมดอายุและเบราว์เซอร์อายุสูงสุดจะล้างคุกกี้เมื่อหน้าถูกปิดถ้า (ตัวเลือกที่มีคนงาน) {parts.push ("expires =" + opotions.path); } // หากคุณไม่ได้ตั้งค่าหมดอายุและเบราว์เซอร์อายุสูงสุดจะล้างคุกกี้เมื่อหน้าถูกปิดถ้า (ตัวเลือกที่มีคนงาน) {parts.push ("expires =" + opotions.expires.togmtstring ()); } if (ตัวเลือก maxage && ตัวเลือก typeof.maxage === "number") {parts.push ("max-age =" + opotions.maxage); } if (options.httponly) {parts.push ("httponly"); } if (opptionss.secure) {parts.push ("ปลอดภัย"); } document.cookie = parts.join (";"); }, ลบ: ฟังก์ชั่น (ชื่อ, ตัวเลือก) {ตัวเลือก expires = วันที่ใหม่ (0); // ตั้งค่าเป็นวันที่ผ่านมา this.set (ชื่อ, null, ตัวเลือก); -ข้อดีของการแคช
โดยทั่วไปเรียกว่าแคชเว็บหมายถึงอุปกรณ์ HTTP ที่สามารถบันทึกสำเนาคำขอ HTTP ทั่วไปโดยอัตโนมัติ สำหรับนักพัฒนาส่วนหน้าเบราว์เซอร์มีบทบาทสำคัญ นอกจากนี้ยังมีเซิร์ฟเวอร์พร็อกซีทั่วไปที่สามารถใช้สำหรับการแคชได้ เมื่อคำขอเว็บมาถึงแคชแคชจะแยกเนื้อหาแบบจำลองออกจากแบบจำลองท้องถิ่นโดยไม่ต้องผ่านเซิร์ฟเวอร์ สิ่งนี้นำมาซึ่งข้อดีต่อไปนี้:
การแคชช่วยลดการส่งข้อมูลซ้ำซ้อนและบันทึกการรับส่งข้อมูล
แคชช่วยบรรเทาปัญหาคอขวดแบนด์วิดธ์ หน้าสามารถโหลดได้เร็วขึ้นโดยไม่ต้องใช้แบนด์วิดท์เพิ่มเติม
แคชช่วยลดความแออัดทันทีและลดข้อกำหนดสำหรับเซิร์ฟเวอร์ดั้งเดิม
แคชลดความล่าช้าของระยะทางเนื่องจากการโหลดหน้าจากสถานที่ไกลออกไปจะช้าลง
ประเภทแคช
แคชสามารถทุ่มเทให้กับผู้ใช้รายเดียวหรือแชร์โดยผู้ใช้หลายคน แคชเฉพาะที่เรียกว่าแคชส่วนตัวและแคชที่ใช้ร่วมกันเรียกว่าแคชสาธารณะ
แคชส่วนตัว
แคชส่วนตัวสำหรับผู้ใช้ที่เป็นกรรมสิทธิ์เท่านั้นดังนั้นจึงไม่ต้องใช้พื้นที่มากและราคาถูก เว็บเบราว์เซอร์มีแคชส่วนตัวในตัว - เบราว์เซอร์ส่วนใหญ่จะแคชทรัพยากรทั่วไปบนดิสก์และหน่วยความจำพีซีของคุณ ตัวอย่างเช่นตำแหน่งที่เก็บแคชของเบราว์เซอร์ Chrome คือ: C:/ผู้ใช้/YOUR_ACCOUNT/APPDATA/LOCAL/Google/Chrome/Data/ผู้ใช้/ค่าเริ่มต้น
แคชสาธารณะ
แคชสาธารณะเป็นเซิร์ฟเวอร์พร็อกซีที่ใช้ร่วมกันเป็นพิเศษเรียกว่าเซิร์ฟเวอร์แคชพร็อกซีหรือแคชพร็อกซี (วัตถุประสงค์ของพร็อกซีย้อนกลับ) แคชสาธารณะจะยอมรับการเข้าถึงจากผู้ใช้หลายคนดังนั้นจึงสามารถลดปริมาณการใช้งานที่ซ้ำซ้อนได้ดีขึ้น
ในรูปด้านล่างไคลเอนต์แต่ละตัวจะเข้าถึงทรัพยากรซ้ำ ๆ ไปยังเซิร์ฟเวอร์ (ไม่ได้อยู่ในแคชส่วนตัวในเวลานี้) เพื่อให้สามารถเข้าถึงเซิร์ฟเวอร์ได้หลายครั้งเพิ่มความดันบนเซิร์ฟเวอร์ เมื่อใช้แคชสาธารณะที่ใช้ร่วมกันแคชจะต้องดึงมาจากเซิร์ฟเวอร์เพียงครั้งเดียวและไม่ต้องผ่านเซิร์ฟเวอร์ในอนาคตซึ่งสามารถลดแรงกดดันบนเซิร์ฟเวอร์ได้อย่างมาก
ในความเป็นจริงแคชสาธารณะแบบลำดับชั้นมักใช้ในแอปพลิเคชันจริง แนวคิดพื้นฐานคือการใช้แคชขนาดเล็กและราคาถูกใกล้กับลูกค้าในขณะที่อยู่ในระดับที่สูงขึ้นแคชขนาดใหญ่และทรงพลังยิ่งขึ้นจะค่อยๆนำไปใช้กับการโหลดทรัพยากรที่ใช้ร่วมกันโดยผู้ใช้หลายคน
กระแสการประมวลผลแคช
สำหรับนักพัฒนาส่วนหน้าส่วนใหญ่เราจัดการกับแคชในเบราว์เซอร์ดังนั้นกระบวนการข้างต้นจะง่ายขึ้นกับ:
ภาพต่อไปนี้แสดงผลลัพธ์การร้องขอของเว็บไซต์สำหรับทรัพยากรที่แตกต่างกัน จะเห็นได้ว่าทรัพยากรบางอย่างถูกอ่านโดยตรงจากแคชทรัพยากรบางอย่างได้รับการตอบกลับด้วยเซิร์ฟเวอร์และทรัพยากรบางอย่างได้รับการจัดหาใหม่จากเซิร์ฟเวอร์
โปรดทราบว่าคำถามทั้งหมดที่เราพูดถึงเกี่ยวกับทรัพยากรแคชนั้นมีไว้สำหรับการร้องขอรับเท่านั้น สำหรับการดำเนินงานเชิงพฤติกรรมเช่นโพสต์ลบและใส่มักจะไม่มีแคช
ขีด จำกัด ความสดใหม่
HTTP เก็บสำเนาทรัพยากรเซิร์ฟเวอร์ไว้เป็นระยะเวลาหนึ่งผ่านแคชซึ่งเรียกว่าขีด จำกัด ความสดใหม่ สิ่งนี้ขอทรัพยากรเดียวกันเป็นระยะเวลาหนึ่งและจะไม่ผ่านเซิร์ฟเวอร์อีกครั้ง แคชควบคุมและหมดอายุในโปรโตคอล HTTP สามารถใช้เพื่อกำหนดขีด จำกัด ของความสดใหม่ อดีตคือส่วนหัวการตอบกลับใหม่ที่เพิ่มเข้ามาใน http1.1 และหลังคือส่วนหัวการตอบกลับใน http1.0 ทั้งสองทำสิ่งเดียวกัน แต่เนื่องจากแคชควบคุมใช้เวลาสัมพัทธ์และการหมดอายุอาจมีปัญหาว่าเวลาไคลเอนต์และเซิร์ฟเวอร์แตกต่างกันเราจึงชอบแคชควบคุม
การควบคุมแคช
ลองมาดูกันว่าแคชแคชควบคุมค่าใด:
อายุสูงสุด (หน่วยคือ S) ระบุเวลาที่ถูกต้องสูงสุดในการตั้งค่าแคชซึ่งกำหนดระยะเวลา เมื่อเบราว์เซอร์ส่งคำขอไปยังเซิร์ฟเวอร์เบราว์เซอร์จะไม่ส่งคำขอไปยังเซิร์ฟเวอร์อีกต่อไปในช่วงอายุสูงสุด
<html> <head> <meta http-equiv = "content-type" content = "text /html; charset = utf-8"> <meta name = "viewport" content = "width = อุปกรณ์-ความกว้างเริ่มต้น" meta-cale content = "ie = edge"/> <title> เว็บแคช </title> <link rel = "ไอคอนทางลัด" href = "./ ทางลัด png"> <script> </script> </head> <body> <img src = " ต้องการ ('fs'); http.createserver (ฟังก์ชั่น (req, res) {ถ้า (req.url === '/' || req.url === '' || req.url === '/index.html') สำหรับเอกสารหลัก res.setheader ('cache-control', "ไม่มีแคช, max-age =" + 5); fs.readfile ('./ cache.png', ฟังก์ชั่น (err, ไฟล์) {res.setheader ('cache-control', "max-age =" + 5); // แคชห้าวินาที res.setheader ('content-type', 'images/png'); }). ฟัง (8888)เมื่อหน้าถูกเข้าถึงเป็นครั้งที่สองภายใน 5 วินาทีเบราว์เซอร์จะได้รับทรัพยากรโดยตรงจากแคช
สาธารณะระบุว่าการตอบสนองสามารถแคชในแคชพร็อกซีและผู้ใช้หลายคนสามารถแชร์ได้ หากไม่ได้ระบุส่วนตัวอย่างชัดเจนก็จะเริ่มต้นต่อสาธารณะ
การตอบสนองส่วนตัวสามารถแคชในแคชส่วนตัวและไม่สามารถวางไว้ในแคชพร็อกซี ทรัพยากรที่มีความอ่อนไหวต่อข้อมูลผู้ใช้บางอย่างมักจะต้องตั้งค่าเป็นส่วนตัว
ไม่มีแคชหมายความว่าคุณต้องยืนยันกับเซิร์ฟเวอร์ก่อนว่าทรัพยากรมีการเปลี่ยนแปลงหรือไม่ (พึ่งพาการจับคู่หากไม่มีการจับคู่และ ETAG) ก่อนตัดสินใจว่าจะใช้แคชท้องถิ่นหรือไม่
หากการประมวลผลข้างต้นของ cache.png ถูกเปลี่ยนเป็นต่อไปนี้ทุกครั้งที่คุณเยี่ยมชมหน้าเบราว์เซอร์จะต้องไปที่เซิร์ฟเวอร์เพื่อตรวจสอบว่าทรัพยากรมีการเปลี่ยนแปลงหรือไม่
fs.readfile ('./ cache.png', ฟังก์ชั่น (err, ไฟล์) {console.log (req.headers); console.log (req.url) ถ้า (! req.headers ['if-none-match'] {res.setheader ('cache-control' 'ภาพ/png'); Res.setheader ('Cache-Control', "Max-age =" + 5);ไม่มีร้านค้าห้ามแคชของทรัพยากรใด ๆ ซึ่งหมายความว่าทุกครั้งที่ผู้ใช้ร้องขอทรัพยากรคำขอจะถูกส่งไปยังเซิร์ฟเวอร์และทรัพยากรที่สมบูรณ์จะถูกดาวน์โหลดทุกครั้ง มักจะใช้สำหรับทรัพยากรที่เป็นความลับ
เกี่ยวกับการใช้แคชควบคุมดูภาพด้านล่าง (จากจำนวนมาก)
ขีด จำกัด ความสดใหม่ของลูกค้า
แคชควบคุมไม่เพียง แต่ตั้งค่าในส่วนหัวการตอบกลับเท่านั้น แต่ยังอยู่ในส่วนหัวคำขอด้วย เบราว์เซอร์สามารถตัดสินใจได้ว่าจะอ่านทรัพยากรจากแคชโดยการตั้งค่าการควบคุมแคชในส่วนหัวคำขอหรือไม่ นี่คือเหตุผลที่บางครั้งการคลิกปุ่มรีเฟรชเบราว์เซอร์และป้อนในแถบที่อยู่เพื่อดูผลลัพธ์ที่แตกต่างอย่างสิ้นเชิงในโมดูลเครือข่าย
หมดอายุ
ไม่แนะนำให้หมดอายุแล้วจะระบุวันหมดอายุที่เฉพาะเจาะจงมากกว่าหนึ่งวินาที เนื่องจากเซิร์ฟเวอร์และลูกค้าจำนวนมากมีนาฬิกาไม่สอดคล้องกันจึงเป็นการดีที่สุดที่จะใช้การควบคุมแคช
การยืนยันเซิร์ฟเวอร์
ทรัพยากรที่แคชในเบราว์เซอร์หรือแคชพร็อกซีหมดอายุไม่ได้หมายความว่าจริง ๆ แล้วมันแตกต่างจากทรัพยากรบนเซิร์ฟเวอร์ดั้งเดิม แต่ก็หมายความว่าถึงเวลาตรวจสอบ สถานการณ์นี้เรียกว่าการตรวจสอบเซิร์ฟเวอร์ใหม่
หากทรัพยากรเปลี่ยนแปลงคุณจะต้องได้รับทรัพยากรใหม่และแทนที่ทรัพยากรเก่าในแคช
หากทรัพยากรไม่เปลี่ยนแปลงแคชจะต้องได้รับส่วนหัวการตอบกลับใหม่และเวลาหมดอายุใหม่เพื่ออัปเดตเวลาหมดอายุของทรัพยากรในแคช
วิธีการตรวจสอบที่แนะนำสำหรับ http1.1 คือ if-none-match/etag และ if-modified-since/modified ล่าสุดใช้ใน http1.0
etag และถ้าไม่มีการจับคู่
สร้างสตริงแฮชตามเนื้อหาเอนทิตีระบุสถานะของทรัพยากรและสร้างโดยเซิร์ฟเวอร์ เบราว์เซอร์จะส่งสตริงนี้กลับไปที่เซิร์ฟเวอร์เพื่อตรวจสอบว่าทรัพยากรได้รับการแก้ไขแล้ว หากยังไม่ได้รับการแก้ไขกระบวนการดังกล่าวมีดังนี้ (ภาพมาจากการสนทนาสั้น ๆ เกี่ยวกับเว็บแคช):
ในการสาธิตข้างต้นเราได้เห็นวิธีการตรวจสอบ ETAG บนเซิร์ฟเวอร์:
เนื่องจาก ETAG มีโครงสร้างเซิร์ฟเวอร์จึงต้องมั่นใจในความเป็นเอกลักษณ์ของ ETAG ในสภาพแวดล้อมคลัสเตอร์
if-modified-snice vs. modified ล่าสุด
ทั้งสองนี้เป็นส่วนหัวคำขอ/ตอบกลับที่ใช้ใน HTTP 1.0 เพื่อตรวจสอบว่าทรัพยากรหมดอายุหรือไม่ ส่วนหัวทั้งสองนี้เป็นวันที่ กระบวนการตรวจสอบนั้นคล้ายกับ ETAG ดังนั้นเราจะไม่แนะนำรายละเอียดที่นี่ เมื่อใช้ส่วนหัวทั้งสองนี้เพื่อตรวจสอบว่าทรัพยากรได้รับการอัปเดตปัญหาต่อไปนี้มีอยู่:
ทรัพยากรเอกสารบางส่วนถูกเขียนใหม่เป็นระยะ แต่เนื้อหาจริงไม่เปลี่ยนแปลง ในเวลานี้ข้อมูลเมตาของไฟล์จะแสดงให้เห็นว่าวันที่แก้ไขล่าสุดของไฟล์นั้นแตกต่างจาก IF-Modified-SNING ซึ่งส่งผลให้เกิดการตอบสนองที่ไม่จำเป็น
ทรัพยากรเอกสารบางส่วนได้รับการแก้ไข แต่เนื้อหาของการดัดแปลงไม่สำคัญและแคชทั้งหมดไม่จำเป็นต้องได้รับการปรับปรุง (เช่นความคิดเห็นของรหัส)
เกี่ยวกับการอัปเดตแคชโปรดตรวจสอบคำตอบของ Zhang Yunlong ที่นี่ บทความนี้จะไม่ถูกขยายอย่างละเอียด
รหัสตัวอย่างในบทความนี้มีดังนี้:
<! doctype html> <html> <head> <meta http-equiv = "content-type" content = "text /html; charset = utf-8"> <meta name = "viewport" content = "width = ความกว้างของอุปกรณ์ http-equiv = "x-ua ที่เข้ากันได้" เนื้อหา = "ie = edge"/> <title> เว็บแคช </title> <link rel = "ไอคอนทางลัด" href = "./ ทางลัด png"> <script> </script> </head> ต้องการ ('http'); var fs = ต้องการ ('fs'); http.createserver (ฟังก์ชั่น (req, res) {ถ้า (req.url === '/' || req.url === '' | req.url === '/index.html' console.log (req.url) // ตั้งค่าแคชสำหรับเอกสารหลักไม่มีผลกระทบต่อ ('cache-control', "ไม่มีแคช, max-age =" + 5); === '/shortcut.png') {fs.readfile ('./ ทางลัด png', ฟังก์ชั่น (err, ไฟล์) {console.log (req.url) res.setheader ('content-type', 'images/png'); res.writehead ('200', "); '/cache.png') {fs.readfile ('./ cache.png', ฟังก์ชั่น (err, ไฟล์) {console.log (req.headers); console.log (req.url) ถ้า (req.headers ['if-none-match']) Res.setheader ('content-type', 'images/png'); Res.end ()} lemes {res.setheader ('cache-control', "Max-age =" + 5); }}) ฟัง (8888)ตกลงบทนำของบทความนี้เกี่ยวกับคุกกี้จะสิ้นสุดที่นี่ฉันหวังว่าทุกคนจะชอบ