1、 Babel的编译过程
  • Babel的作用是 从一种源码到另一种源码,充当转换编译器的作用,可以简述为解析(解析Js代码)-> 转换(解析和修改AST)-> 重建(将修改后的AST转换成另一种Js代码)

    • image.png

      1、解析
      • 解析步骤接受代码并输出AST,这一部分,与我们在大学中所学的编译原理颇为相关,这一步骤分为两个阶段:词法分析语法分析

        1、词法分析
        1. - 词法分析阶段把字符串形式的代码转换为 **令牌(tokens)流**。
        2. - tokens是词法分析过程中不可分割的最小单元。例如var就是一个token对象,只能作为整体存在时有作用,语义上不可分解。

        2、语法分析
        1. - 语法分析阶段会把令牌流转换成AST的形式。这个阶段会使用令牌中的信息把它们转换成AST的表述结构。
        2. - **code(字符串形式代码) -> tokens(令牌流-词法单元序列) -> AST(抽象语法树)**
        3. - **Babel 使用 @babel/parser 解析代码,输入的 js 代码字符串根据 ESTree 规范生成 AST(抽象语法树)。**

        2、转换
        • 转换步骤接收 AST 并对其进行遍历,在此过程中对节点进行添加、更新及移除等操作。 这是 Babel 或是其他编译器中最复杂的过程。
        • Babel提供了@babel/traverse(遍历)方法维护这AST树的整体状态,并且可完成对其的替换,删除或者增加节点,这个方法的参数为原始AST和自定义的转换规则,返回结果为转换后的AST。

          3、生成
        • 代码生成步骤最终的AST转换成字符串形式的代码,同时还会创建源码映射(source maps)。

        • 代码生成:通过深度优先遍历整个AST,然后构建可以表示转换后代码的字符串。
        • Babel使用@babel/generator将修改后的AST转换成代码,生成过程可以对是否压缩以及是否删除注释等进行配置,并且支持sourceMap。
          2、CDN的加速原理(缓存)
  • CDN(Content Delivery Network,内容分发网络)是构建在现有互联网基础之上的一层智能虚拟网络,通过在网络各处部署节点服务器,实现将源站内容分发至所有CDN节点,使用户可以就近获得所需的内容。

    • CDN服务缩短了用户查看内容的访问延迟,提高了用户访问网站的响应速度与网站的可用性,解决了网络带宽小、用户访问量大、网点分布不均等问题。
  • 当用户访问使用了CDN服务的网站时,本地DNS服务器通过CNAME方式(是域名系统(DNS)的一种记录,将一个域名(同名)映射到另一个域名(真实名称))将最终域名请求重定向CDN服务。CDN通过一组预先定义好的策略(如内容类型、地理区域、网络负载均衡等),将当时能够最快响应用户的CDN节点IP地址提供给用户,使用户可以以最快的速度获得网站内容。
  • 使用CDN后的HTTP请求处理过程如下
    • CDN节点有缓存场景image.png
    • CDN节点无缓存场景image.png
  • CDN缓存策略/CDN回源策略
    • CDN边缘节点缓存策略因服务商不同而不同,但一般都会遵循http标准协议,通过http响应头中的Cache-control: max-age的字段来设置CDN边缘节点数据缓存时间。
    • 当客户端向CDN节点请求数据时,CDN节点会判断缓存数据是否过期,若缓存数据并没有过期,则直接将缓存数据返回给客户端;否则,CDN节点就会向源站发出回源请求,从源站拉取最新数据,更新本地缓存,并将最新数据返回给客户端。
    • CDN服务商一般会提供基于文件后缀、目录多个维度来指定CDN缓存时间,为用户提供更精细化的缓存管理。
    • CDN缓存时间会对“回源率”产生直接的影响。若CDN缓存时间较短,CDN边缘节点上的数据会经常失效,导致频繁回源,增加了源站的负载,同时也增大的访问延时;若CDN缓存时间太长,会带来数据更新时间慢的问题。开发者需要增对特定的业务,来做特定的数据缓存时间管理。
  • CDN缓存缺点
    • 当网站更新时,如果CDN节点上数据没有及时更新,即便用户在浏览器使用Ctrl +F5的方式使浏览器端的缓存失效,也会因为CDN边缘节点没有同步最新数据而导致用户访问异常。
  • CDN层级划分中心层、边缘层)

    • CDN系统中,直接面向用户,负责给用户提供内容服务的的Cache设备都部署在整个 CDN网络的边缘位置,所以将这一层称为边缘层。
    • CDN系统中,中心层负责全局的管理和控制,同时也保存了最多的内容Cache。在边缘层设备未能命中Cache时,需要向中心层设备请求;而中心层未能命中时,则需要向源站请求。不同的CDN系统设计存在差异,中心层可能具备用户服务的能力,也可能只会向下一层提供服务。
    • 如果CDN系统比较庞大,边缘层向中心层请求内容太多,会造成中心层负载压力太大。此时,需要在中心层和边缘层之间部署一个区域层,负责一个区域的管理和控制,也可以提供一些内容Cache供边缘层访问。
      3、Web缓存
  • image.png

    HTTP 缓存的两个阶段
    • 浏览器缓存一般分为两类:强缓存(也称本地缓存)和协商缓存(也称弱缓存)。
      • 强缓存:浏览器发送请求前,会先去缓存里查看是否命中强缓存,如果命中,则直接从缓存中读取资源,不会发送请求到服务器。否则,进入下一步。
      • 协商缓存:当强缓存没有命中时,浏览器一定会向服务器发起请求。服务器会根据 Request Header 中的一些字段来判断是否命中协商缓存。如果命中,服务器会返回 304 响应,但是不会携带任何响应实体,只是告诉浏览器可以直接从浏览器缓存中获取这个资源。如果本地缓存和协商缓存都没有命中,则从直接从服务器加载资源。
      • image.png
    • 使用HTML Meta标签 Web开发者可以在HTML页面的节点中加入标签,如下

      • image.png
      • 上述代码是告知浏览器当前页面不被缓存,但仅有IE才能识别这段meta的标签含义,其他大部分主流浏览器只识别“Cache-control:no-store”的meta标签。
      • 在 IE 中识别到该 meta 标签含义,并不一定会在请求字段加上 Pragma,但的确会让当前页面每次都发新请求(仅限页面,页面上的资源则不受影响)。
      • HTTP 响应头 | 规则 | 消息报头 | 值/示例 | 类型 | 作用 | | —- | —- | —- | —- | —- | | 新鲜度 | Expires | Sun,16 Oct2016 06:43:02 GMT | 响应 | 告诉浏览器在过期时间前可以使用副本(有可能存在时间不一样的情况)。 | | | Pragma | no-cache | 响应 | 告诉浏览器忽略资源的缓存副本(HTTP1.1可以用Cache-control代替) | | | Cache-control | No-cache | 响应 | 告诉浏览器忽略资源的缓存副本,强制每次请求直接发送给服务器。 | | | | no-store | 响应 | 强制缓存在任何情况下都不要保留副本。 | | | | Max-age = [秒] | 响应 | 指明缓存副本的有效时长,从请求时间开始到过期时间之间的秒数。 | | | | public | 响应 | 任何途径的缓存者(本地缓存、代理服务器),可以无条件的缓存该资源。 | | | | private | 响应 | 只针对单个用户或实体(不同用户,窗口)缓存资源。 | | | | | | | | | Last-Modified | Sun,16 Oct2016 06:43:02 GMT | 响应 | 告诉浏览器当前资源的最后修改时间 | | | If-Modified-Since | Sun,16 Oct2016 06:43:02 GMT | 请求 | 如果浏览器第一次请求时响应中Last-Modified非空,第二次请求同一个资源时,会把它作为该项的值发给服务器。 | | | | | | | | 校验值 | Etag | 50b1c1d4f775c61:df3 | 响应 | 告诉浏览器当前资源在服务器的唯一标识符(生成规则由服务器决定)。 | | | If-None-Match | 50b1c1d4f775c61:df3 | 请求 | 如果浏览器第一次请求时响应中Etag非空,第二次请求同一个资源时,会把它作为该项的值发给服务器。 | | | | | | | | 辅助 | Vary | Accept-Encoding | 响应 | 辅助从多个缓存副本中筛选合适的版本。 | | | | | | |

      • Cache-control

        • HTTP1.1 提出的特性,为了弥补 Expires 缺陷加入的,提供了更精确细致的缓存功能。
        • 详细看几个常见的指令: max-age:功能和 Expires 类似,但是后面跟一个以“秒”为单位的相对时间,来供浏览器计算过期时间。 no-cache:提供了过期验证机制。image.png
      • Expires
        • HTTP1.0 的特性,标识该资源过期的时间点,它是一个绝对值,格林威治时间(Greenwich Mean Time, GMT),即在这个时间点之后,缓存的资源过期
        • 优先级:Cache-Control 优先级高于 Expires,为了兼容,通常两个头部同时设置
        • 浏览器默认行为:其实就算 Response Header 中沒有设置 Cache-Control 和 Expires,浏览器仍然会缓存某些资源,这是浏览器的默认行为,是为了提升性能进行的优化,每个浏览器的行为可能不一致,有些浏览器甚至没有这样的优化。
      • Last-Modified(Response Header)If-Modified-Since(Request Header)是一对报文头,属于 HTTP 1.0
        • If-Modified-Since 是一个请求首部字段,并且只能用在 GET 或者 HEAD 请求中。
        • Last-Modified 是一个响应首部字段,包含服务器认定的资源作出修改的日期及时间。
        • 当带着 If-Modified-Since 头访问服务器请求资源时,服务器会检查 Last-Modified,如果 Last-Modified 的时间早于或等于 If-Modified-Since 则会返回一个不带主体的 304 响应,否则将重新返回资源。
        • image.png
      • ETagIf-None-Match 是一对报文头,属于 HTTP 1.1
        • ETag 是一个响应首部字段,它是根据实体内容生成的一段 hash 字符串,标识资源的状态,由服务端产生。
        • If-None-Match 是一个条件式的请求首部。如果请求资源时在请求首部加上这个字段,值为之前服务器端返回的资源上的 ETag,则当且仅当服务器上没有任何资源的 ETag 属性值与这个首部中列出的时候,服务器才会返回带有所请求资源实体的 200 响应,否则服务器会返回不带实体的 304 响应。
        • image.png
        • Etag能解决什么问题?
          • Last-Modified 标注的最后修改只能精确到秒级,如果某些文件在 1 秒钟以内,被修改多次的话,它将不能准确标注文件的新鲜度。
          • 某些文件也许会周期性的更改,但是他的内容并不改变(仅仅改变的修改时间),但 Last-Modified 却改变了,导致文件没法使用缓存。
          • 有可能存在服务器没有准确获取文件修改时间,或者与代理服务器时间不一致等情形。
          • 优先级:ETag 优先级Last-Modified 高,同时存在时会以 ETag 为准
          • image.png
    • 缓存位置
      • 浏览器可以在内存、硬盘中开辟一个空间用于保存请求资源副本。我们经常调试时在 DevTools Network 里看到 Memory Cache(內存缓存)和 Disk Cache(硬盘缓存),指的就是缓存所在的位置。请求一个资源时,会按照优先级(Service Worker -> Memory Cache -> Disk Cache -> Push Cache)依次查找缓存,如果命中则使用缓存,否则发起请求。
      • 200 from memory cache
        • 表示不访问服务器,直接从内存中读取缓存。因为缓存的资源保存在内存中,所以读取速度较快,但是关闭进程后,缓存资源也会随之销毁,一般来说,系统不会给内存分配较大的容量,因此内存缓存一般用于存储较小文件。同时内存缓存在有时效性要求的场景下也很有用(比如浏览器的隐私模式)。
      • 200 from disk cache
        • 表示不访问服务器,直接从硬盘中读取缓存。与内存相比,硬盘的读取速度相对较慢,但硬盘缓存持续的时间更长,关闭进程之后,缓存的资源仍然存在。由于硬盘的容量较大,因此一般用于存储大文件。
      • 下图可清晰看出差别:
        • image.png
      • 200 from prefetch cache
        • 在 preload 或 prefetch 的资源加载时,两者也是均存储在 http cache,当资源加载完成后,如果资源是可以被缓存的,那么其被存储在 http cache 中等待后续使用;如果资源不可被缓存,那么其在被使用前均存储在 memory cache。
        • image.png
      • CDN Cache
        • 以腾讯 CDN 为例:X-Cache-Lookup:Hit From MemCache 表示命中 CDN 节点的内存;X-Cache-Lookup:Hit From Disktank 表示命中 CDN 节点的磁盘;X-Cache-Lookup:Hit From Upstream 表示没有命中 CDN。
        • image.png
        • 整体流程
          • image.png
  • 其他Web缓存策略

    IndexDB

    1. - IndexedDB 就是浏览器提供的本地数据库,能够在客户端存储可观数量的结构化数据,并且在这些数据上使用索引进行高性能检索的 API
    2. - 异步 API 方法调用完后会立即返回,而不会阻塞调用线程。要异步访问数据库,要调用 window 对象 indexedDB 属性的 open() 方法。该方法返回一个 IDBRequest 对象 (IDBOpenDBRequest);异步操作通过在 IDBRequest 对象上触发事件来和调用程序进行通信。
    3. - 常用异步 API 如下:![image.png](https://cdn.nlark.com/yuque/0/2021/png/22079037/1627378577049-6027d23f-f679-4c63-a5d3-86b3632ba239.png#align=left&display=inline&height=533&id=u03e668ad&margin=%5Bobject%20Object%5D&name=image.png&originHeight=533&originWidth=1080&size=378207&status=done&style=stroke&width=1080)

    LocalStorage

    1. - localStorage 属性允许你访问一个 Document 源(origin)的对象 Storage 用于存储当前源的数据,除非用户人为清除(调用 localStorage api 或则清除浏览器数据), 否则存储在 localStorage 的数据将被长期保留。

    Service Worker

    1. - SW 2014 年提出的草案到现在已经发展很成熟了,基于 SW 做离线缓存,让用户能够进行离线体验,消息推送体验,离线缓存能力涉及到 Cache CacheStorage 的概念,篇幅有限,不展开了。

    SessionStorage

    1. - sessionStorage 属性允许你访问一个 session Storage 对象,用于存储当前会话的数据,存储在 sessionStorage 里面的数据在页面会话结束时会被清除。页面会话在浏览器打开期间一直保持,并且重新加载或恢复页面仍会保持原来的页面会话。