Vite 的理解

# 模块化规划

  • 常见的模块化规范

    • commonjs,使用 require 引入模块,使用 module.exports 或 exports 导出模块;模块加载是同步的;主要用于服务端,所以需要打包工具转成浏览器可识别的代码。

    • amd,异步模块定义,使用 define 定义模块;依赖模块会在模块执行之前异步加载(预加载),因此模块执行时,依赖模块已经准备好了;代表库 RequireJS。

    • cmd,使用 define 定义模块,但是依赖的模块在需要的时候才执行(懒加载),所以模块加载是按需的。

    • esm(es module),是 js 官方模块系统;模块是异步加载的,而且加载是静态的,import 会在编译的时候就进行解析。

正是 esm 的浏览器支持,才有了 bundleless 方案

  • bundleless

    • 打包:通过 webpack 或其他打包工具,通过模块化规范支持,依赖分析之后构建依赖图 dep-graph

    • bundleless 提倡少打包、不打包,js 不用打包直出,但是 ts tsx jsx vue css 字体文件 woff2 需要打包

    • 针对需要打包的资源,做转换的处理,使用插件化机制来实现:vite-plugin-xxx vite-plugin-react 等等

      • esbuild 构建 jsx ts tsx 文件

      • postcss 构建 css 文件

# vite 原理

  • vite 开发阶段

    • 基于 esm,不需要进行打包,启动开发服务器时,直接为 html 文件提供服务,浏览器请求 js 文件的话,vite 直接从源文件中提供该模块,并且通过响应头 type=moudle 告诉浏览器将其作为 es 模块进行加载

    • 按需加载,利用 esm 天然特性,利用浏览器的能力按需加载模块

    • 依赖预构建,第一次启动的时候,会对依赖项进行预构建。通过 esbuild,将这些依赖转成高效的 es 模块格式。可以将 comonjs 模块、 umd 模块转成 esm 模块,从而更高效的使用

    • hmr 热模块替换,通过 vite 的模块加载机制,检测到模块变化的时候,通知浏览器更新指定的模块,无需刷新整个页面

  • vite 生产构建阶段

    • 使用 Rollup 打包,高效的树摇优化 和 支持 es 模块;vite 会将应用的所有模块和依赖项打包成一个或多个优化后的静态文件,可以直接部署到生产环境

    • vite 会自动进行代码拆分,根据路由或动态导入的方式生成不同的代码块(chunk),以便在生成环境中进行按需加载

    • 内置静态资源处理,css、图片、字体文件会被打包成优化的资源文件

  • vite 的核心优势

    • 快速冷启动,基于 esm 和预构建,开发环境下启动很快

    • 即时的热模块替换,基于 esm 的加载模式,无需全量更新

    • 按需加载,不需要全量打包,所以大型项目,vite 也能很快

    • Rollup 打包