Quiet
  • 主页
  • 归档
  • 分类
  • 标签
  • 链接
  • 关于我

bajiu

  • 主页
  • 归档
  • 分类
  • 标签
  • 链接
  • 关于我
Quiet主题
  • 前端工程化

vite中预加载模块 `modulepreload`

bajiu
前端

2021-08-30 21:40:27

最近用vite 构建项目的时候发现 vite 加入了 <link rel="modulepreload" > 参考文章Preloading modules

虽然文章上说的已经很明白了, 但鉴于这是2017年的文档, 所以还需要翻译翻译

浏览器最近已经原生的支持JS modules, 包括静态和动态的 import, 这意味着现在们可以在浏览器内直接基于模块编写JS不用编译和打包

但是, 模块依赖项会带来加载问题, 因为浏览器需要先等待模块加载, 然后才能找到其依赖项. 解决此问题的一种方法是预加载依赖项, 以便浏览器提前知道所有文件并可以保持连接

Chrome 64附带 ‘实验性Web平台功能’ 标志后的<link rel ='modulepreload'> <link rel ='modulepreload'> 是 <link rel =' preload'>特定于模块的版本, 它解决了后者的许多问题

Chrome在50版中添加了对<link rel ='preload'> 的支持, 这是一种在浏览器需要资源之前以声明方式提前请求资源的方法

<head>
  <link rel="preload" as="style" href="critical-styles.css">
  <link rel="preload" as="font" crossorigin type="font/woff2" href="myfont.woff2">
</head>

为什么 <link rel ='preload'>对module不生效?

源有多种凭证模式, 为了获得高速缓存命中, 它们必须匹配, 否则最终将获取资源两次. 双重获取是不好的, 因为它浪费用户的带宽并使他们等待更长的时间, 这没有充分的理由

对于 <script> 和 <link> 标签, 可以使用 crossorigin 属性设置凭据模式. 事实证明, 没有crossorigin属性的 <script type ='module'> 不具有凭据模式

此外, 获取文件只是实际运行代码的第一步. 首先, 浏览器必须解析和编译它. 理想情况下, 这也应该提前发生, 以便在需要模块时, 代码就可以运行了. 但是 V8 解析和编译模块的方式与其他JavaScript不同.<link rel ='preload'>没有提供任何方式表明正在加载的文件是模块, 因此浏览器所能做的就是加载文件并将其放入缓存. 使用<script type ='module'>标记加载脚本(或由其他模块加载)后, 浏览器将代码解析并编译为JavaScript模块

那么对于模块来说, <link rel ='modulepreload'>只是 <link rel ='preload'>吗?

是的 通过为预加载模块使用特定的链接类型, 我们可以编写简单的HTML, 而不必担心我们使用的是哪种凭据模式.

<head>
  <link rel="modulepreload" href="super-critical-stuff.mjs">
</head>
[...]
<script type="module" src="super-critical-stuff.mjs">

而且由于Chrome现在知道您要预加载的是模块, 因此它可以很聪明地在完成获取操作后立即解析并编译该模块, 而不必等到它尝试运行为止

预加载模块是否有助于提高性能

通过向浏览器告知需要获取的内容, 预加载可以帮助最大程度地利用带宽, 从而避免在长途往返期间无所事事

上一篇

Electron 应用 `electron-updater` 自动更新

下一篇

音视频系列 --- yuv

©2024 By bajiu.