当前位置: 首页 > news >正文

前端常用的缓存技术

CDN缓存

CDN(Content DeliveryNetwork),即内容分发网络。CDN是构建在网络之上的内容分发网络,依靠部署在各地的边缘服务器,通过中心平台的负载均衡、内容分发、调度等功能模块,使用户就近获取所需内容,降低网络拥塞,提高用户访问响应速度和命中率

具体是什么意思呢? 当我们使用CDN时,CDN会优先调度离我们最近的边缘服务器并检测是否有该请求的缓存数据,如果有则返回缓存数据;如果没有则向中心服务器请求并返回。

优点:

  1. 减少带宽的占用,减轻网络拥堵,提高访问速度
  2. 减轻本地服务器负担

DNS缓存

DNS(Domin Name System)是域名和IP相互映射的分布式数据库,可将域名解析成供计算机识别的IP地址

DNS查询耗时大约20ms,在DNS查询过程中,浏览器不进行任何活动,会导致浏览器出现空白页;如果DNS查询很多,会导致网页加载性能受到影响

DNS缓存机制: 当首次访问一个域名,通过DNS解析获取其IP,并将域名及对应的IP缓存下来,当下次访问该域名时,则不再进行DNS查询,直接使用缓存下来的IP

缓存时间: 不同的浏览器DNS缓存时间也不同,IE默认的DNS缓存时间为30min,Firfox、Chrome默认的DNS缓存时间为1min

若域名对应的ip已更改,则需要清除DNS缓存(ipconfig/flushdns)

HTTP缓存

当客户端第一次完成数据请求后,浏览器会缓存本次请求的数据,当下次执行相同请求,则直接在缓存数据库中返回;但HTTP缓存有多种规则,根据是否向服务器发送请求分为 “强制缓存”“对比缓存” 两种

强制缓存

当客户端发送请求时,若浏览器中有该请求的缓存数据,则直接返回缓存数据;

若浏览器中未有本次请求的缓存数据或缓存数据过期,则本次请求会抵达服务器去请求数据;

那么如何去判断缓存数据是否已经失效(过期)呢?

当客户端与服务器完成一次请求后,服务器会在Response Headers 报文中返回缓存规则信息;在Response Body报文中返回响应的数据;缓存规则有 ExpiresCache-Control 两种

Expires

Expires表示缓存数据的到期时间,若下次请求的日期小于到期时间,则直接从缓存数据中读取;若大于到期时间,则直接请求服务器

  • 由于到期时间是有服务器端生成的,这与客户端的时间会有偏差,所以从HTTP 1.1 版本后此方案由 Cache-Control 代替

Cache-Control

目前HTTP标准的缓存规则,包含“private”、“public”,“max-age=”、“no-cache”、“no-store”

  • private:客户端可以缓存
  • public:客户端和服务端都可以缓存
  • max-age=xxx:缓存的总时长,单位为秒
  • no-cache:使用对比缓存验证缓存数据
  • no-store:不适用强制缓存和对比缓存

此例子中,缓存时间为3153600秒(1年),在1年内请求这条数据,都只会从缓存中返回

对比缓存

浏览器完成一次完整请求后,服务器返回数据和缓存规则,客户端收到并缓存在缓存数据库中;

对比缓存顾名思义就是每次请求,客户端都会拿缓存标识去服务器判断该缓存是否可用,若可用,服务器返回304并通知客户端从缓存中读取,若不可用则服务器返回200和最新的数据和缓存规则

缓存标识分为以下两种

Last-Modified / If-Modified-Since

服务器返回资源最后一次修改的时间

再次请求时,客户端在请求头携带If-Modified-Since;服务器拿If-Modified-Since与资源最后修改时间做对比,若大于或等于,则命中对比缓存,返回304,从缓存中读取;反之,则服务器返回最新的数据和缓存规则,并返回200

Etag / If-None-Match(优先级高于Last-Modified / If-Modified-Since)

第一次请求,浏览器返回资源唯一标识(一般都是hash生成的)

服务器存储着文件的Etag字段,可以在与每次客户端传送If-no-match的字段进行比较。如果相等,则表示未修改,响应304;反之,则表示已修改,响应200状态码,返回数据。

Service Worker 离线缓存

Service Worker能够充当网络代理服务器的功能,能拦截网络请求(fetch)、离线缓存

  • Service Worker是运行在worker上下文,所以不能访问DOM
  • 运行在其他线程中,不会造成拥堵,完全异步,因此同步API不可使用
  • 只能在https或本地localhost上运行
  1. 注册serviceWorker
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <meta http-equiv="X-UA-Compatible" content="ie=edge">
  <title>serviceWorker</title>
  <script type="text/javascript">
    if ('serviceWorker' in navigator) {
      navigator.serviceWorker.register('./serviceWorker.js', {scope: './'})
        .then(registration => {
          console.log('注册成功', registration.scope)
        })
        .catch(err => {
          console.log('注册失败', err)
        })
    }
  </script>
</head>
<body>
</body>
复制代码
  1. ServiceWorker.js
let self = this;
// 完成serviceWorker的注册与缓存文件
self.addEventListener('install', function (event) {
  event.waitUntil(
    caches.open('v1').then(function (cache) {
      return cache.addAll([
        './index.html' //缓存文件
      ])
    })
  )
})

// 监听拦截http请求,做资源缓存
self.addEventListener('fetch', function (event) {
  event.responseWith(
    // 在缓存中匹配请求
    caches.match(event.request)
      .then(function (response) {
        // 若缓存存在,则直接返回
        if (response) {
          return response
        }
        // 拷贝request副本
        let fetchRequest = event.request.clone()
        // 未命中缓存,发起网络请求
        return fetch(fetchRequest).then(function (response) {
          // 判断是否请求成功
          if (!response || response.status != 200 || response.type != 'basic') {
            return response
          }
          // 缓存请求和响应数据
          let fetchResponse = response.clone()
          caches.open('v1').then(function (cache) {
            cache.put(event.request, fetchResponse) 
          })
          // 返回真实的网络请求数据
          return response
        })
      })
  )
})
复制代码

mainfest

html5引入的新标准,可以离线缓存静态文件

优点

  • 离线浏览
  • 已缓存资源加载速度更快
  • 减轻服务器负载 - 只需从服务器中获取更新或修改过的资源

步骤

  1. 新建一个后缀为'manifest.appcache'的文件,文件内容如下
    CACHE MANIFEST // 首次完成请求后进行缓存,离线可访问
    manifest.css
    
    NETWORK: // 每次请求都需要网络,不缓存
    network.css
    
    FALLBACK: // 页面无法连接网络时显示的页面
    404.html
    复制代码
  2. 在中加入manifest属性并指定文件所在地址
    <html manifest="manifest.appcache">
    复制代码

首次访问,请求静态文件

再次访问,manifest.css已被缓存

当离线后,network.css无法访问,但仍能从缓存中读取manifest.css

转载于:https://juejin.im/post/5cb92f28f265da03b051592e

相关文章:

  • 阿里云IoT边缘计算助力企业零改造实现远程运维 ...
  • 女程序媛与男程序猿的一天,萌萌哒!
  • Qt编写自定义控件1-汽车仪表盘
  • solr8.0 springboot整合solr(四)
  • 18.C#--for循环的正序输出和倒序输出,在屏幕上打印1 - 10正序和倒序
  • 云计算的资源管理特性及服务类型
  • Manjaro 显示蓝牙耳机已连接但是没有声音
  • OMD图(对象模型图)的阅读
  • SQL server 数据库中dbo的含义
  • 国内唯一,阿里云入选全球区块链云服务报告,领先AWS、Google ...
  • 前端小白程序员入门之前知道这些,半年后都拿到8K+的offer
  • (四) 虚拟摄像头vivi体验
  • 链表(下)—— 6个技巧教你写出正确的链表代码
  • 一份阿里P7的面试题
  • svn统计代码行数(增量)
  • android高仿小视频、应用锁、3种存储库、QQ小红点动画、仿支付宝图表等源码...
  • classpath对获取配置文件的影响
  • CSS相对定位
  • HTTP中的ETag在移动客户端的应用
  • Java新版本的开发已正式进入轨道,版本号18.3
  • laravel with 查询列表限制条数
  • mongo索引构建
  • webpack+react项目初体验——记录我的webpack环境配置
  • 大快搜索数据爬虫技术实例安装教学篇
  • 京东美团研发面经
  • 如何用Ubuntu和Xen来设置Kubernetes?
  • 实战:基于Spring Boot快速开发RESTful风格API接口
  • 数据科学 第 3 章 11 字符串处理
  • 远离DoS攻击 Windows Server 2016发布DNS政策
  • 蚂蚁金服CTO程立:真正的技术革命才刚刚开始
  • ###51单片机学习(2)-----如何通过C语言运用延时函数设计LED流水灯
  • (2)(2.4) TerraRanger Tower/Tower EVO(360度)
  • (33)STM32——485实验笔记
  • (Git) gitignore基础使用
  • (动手学习深度学习)第13章 计算机视觉---微调
  • (附源码)流浪动物保护平台的设计与实现 毕业设计 161154
  • (十二)springboot实战——SSE服务推送事件案例实现
  • (五)IO流之ByteArrayInput/OutputStream
  • (一)WLAN定义和基本架构转
  • (原創) 博客園正式支援VHDL語法著色功能 (SOC) (VHDL)
  • (转)IOS中获取各种文件的目录路径的方法
  • *_zh_CN.properties 国际化资源文件 struts 防乱码等
  • .NET/C# 编译期能确定的字符串会在字符串暂存池中不会被 GC 垃圾回收掉
  • .NET/C# 在 64 位进程中读取 32 位进程重定向后的注册表
  • .net连接MySQL的方法
  • .NET中的十进制浮点类型,徐汇区网站设计
  • .pyc文件是什么?
  • .secret勒索病毒数据恢复|金蝶、用友、管家婆、OA、速达、ERP等软件数据库恢复
  • @converter 只能用mysql吗_python-MySQLConverter对象没有mysql-connector属性’...
  • [ 环境搭建篇 ] 安装 java 环境并配置环境变量(附 JDK1.8 安装包)
  • [ 数据结构 - C++]红黑树RBTree
  • [1] 平面(Plane)图形的生成算法
  • [1159]adb判断手机屏幕状态并点亮屏幕
  • [BZOJ2850]巧克力王国
  • [C#]猫叫人醒老鼠跑 C#的委托及事件