前端缓存介绍以及实现方案
1.HTTP code 为304
HTTP 304 是一种服务器响应状态码,表示资源未被修改,客户端可以使用本地缓存**[浏览器内存缓存、本地电脑磁盘缓存]**的副本而不需要重新下载资源。这个过程通常涉及到浏览器向服务器发送请求,并在请求头中带有资源的 ETag 或 Last-Modified 时间戳,服务器检查资源是否有更新。如果没有更新,服务器返回 304 状态码,浏览器则从缓存中加载资源。这减少了数据传输,提高了页面加载速度。
2.内存缓存(Memory Cache)
内存缓存是指将资源存储在浏览器的内存中。这种缓存非常快速,因为访问内存的速度远远快于访问磁盘或网络。然而,内存缓存是短暂的,一旦浏览器或页面关闭,内存缓存的内容就会被清除。内存缓存通常用于缓存那些在短时间内频繁使用的资源,比如图片、样式表和脚本文件,以便在页面切换或重新加载时能够快速访问。
3. 磁盘缓存(Disk Cache)
磁盘缓存是指将资源存储在硬盘上。相对于内存缓存,磁盘缓存的存储时间更长,并且即使在浏览器关闭后也能保留。下次访问相同的资源时,浏览器会优先从磁盘缓存中读取。这种缓存的读取速度虽然比内存缓存慢,但比重新从网络加载要快得多。磁盘缓存通常用于存储那些不需要频繁更新的资源。
4. 如何触发磁盘缓存
要实现磁盘缓存,通常是通过浏览器的 HTTP 缓存机制来完成的。浏览器会根据服务器返回的 HTTP 响应头中的缓存策略,决定是否将资源存储到磁盘上,以及何时使用缓存。以下是实现磁盘缓存的常见方法和步骤:
4.1 设置 HTTP 响应头
服务器通过设置以下几个 HTTP 响应头来控制资源的缓存行为,包括是否存储到磁盘以及缓存的有效期。
常见的 HTTP 响应头字段:
**Cache-Control:**控制缓存行为的最重要字段,可以设置是否允许缓存、缓存的最大存活时间等。常用的指令包括:
max-age=:指定资源的缓存时间,单位是秒。在这个时间内,浏览器可以直接从缓存中读取资源,而不需要向服务器重新请求。
**no-store:**告诉浏览器不要缓存这个资源,既不保存在内存中,也不保存在磁盘上。
no-cache:浏览器可以缓存资源,但每次使用缓存前需要向服务器验证资源是否更新(例如通过 ETag 或 Last-Modified)。
public/private:指定资源是否可以被公共缓存或仅限于用户的本地缓存。
**Expires:**指定一个绝对时间,表示缓存的到期时间。在这个时间之前,资源可以直接从缓存中读取。该字段被 Cache-Control: max-age 所取代,但仍然可以用作备用方案。
ETag:是资源的一个唯一标识符。当客户端发送带有 ETag 的请求时,服务器会检查资源是否更新。如果未更新,返回 304 状态码,从而让浏览器继续使用缓存。
**Last-Modified:**标识资源的最后修改时间。与 ETag 类似,浏览器在请求资源时可以带上 If-Modified-Since 请求头,服务器根据这个时间判断资源是否更新。
Cache-Control: public, max-age=31536000
ETag: "abcdef12345"
last-modified:Fri, 02 Aug 2024 12:54:18 GM
这个响应头表示资源可以被缓存 1 年,并使用 ETag 来检测资源更新。
4.2 如何触发磁盘缓存
浏览器根据 Cache-Control 头中的 max-age 指令决定资源是否缓存。如果资源的缓存时间较长,并且资源大小较大,浏览器往往会将其存储在磁盘上。这是因为内存缓存一般用于短期且频繁的资源访问,而磁盘缓存用于长期存储。
常见触发磁盘缓存的条件:
- 资源的缓存时间较长(max-age 设置较大)。
- 资源的大小比较大(例如图片、视频等静态资源)。
- 浏览器关闭后,资源仍然可以从缓存中读取。
4.3 使用 Service Worker 缓存
除了传统的 HTTP 缓存策略,现代 Web 开发中可以使用 Service Worker 来更灵活地控制缓存行为。Service Worker 允许开发者直接编写脚本来拦截网络请求,并将资源缓存到磁盘中,这为离线应用和更高级的缓存策略提供了支持。
self.addEventListener('install', function(event) {
event.waitUntil(
caches.open('my-cache').then(function(cache) {
return cache.addAll([
'/index.html',
'/styles.css',
'/script.js',
]);
})
);
});
self.addEventListener('fetch', function(event) {
event.respondWith(
caches.match(event.request).then(function(response) {
return response || fetch(event.request);
})
);
});
这个示例展示了如何通过 Service Worker 将资源缓存到磁盘中,并在请求时优先从缓存中读取资源。
5. 浏览器开发者工具查看缓存
你可以使用浏览器的开发者工具(通常是 F12)来查看缓存策略的执行情况:
- 在 Network 选项卡下,可以看到每个请求的缓存状态,如 from disk cache 或 from memory cache。
- 在 Application 选项卡下的 Cache Storage 或 Service Workers 选项,可以查看缓存的资源。
总结:
- 设置合适的 HTTP 缓存头(如 Cache-Control, ETag, Last-Modified)是实现磁盘缓存的关键。
- Service Worker 可以提供更精细的缓存控制
- 浏览器会根据缓存策略和资源大小、生命周期自动决定是否将资源存储到磁盘上。
- HTTP 304:是一种服务器响应状态码,用于确认客户端的缓存副本是最新的,从而避免不必要的数据传输。
- 内存缓存:存储在浏览器内存中,读取速度最快,但生命周期较短,适合短期内频繁使用的资源。
- 磁盘缓存:存储在硬盘中,读取速度相对较慢,但生命周期较长,适合较长时间内可能会重复使用的资源。
缓存虽然也会送http请求,但是它减少了从服务器端发送回数据并解析的时间,从而提升了页面的渲染速度,提高了性能