2024-02-04 vite-学习-理解

2024-02-03  本文已影响0人  忙于未来的民工

vite 会将代码分为两部分,依赖和源码。依赖就是我们所引入的各种三方库(vue、react),源码就是我们自己写的代码(css、js、html),vite工作流程是 启动是进行将依赖进行预构建为一个es模块,vite以esm模块的形式为浏览器提供源码。esm就是直接给浏览器提供export、import这类模块化的代码。

执行流程:
本期起一个服务,浏览器解析 import, 发起http请求,本期的服务的中间件拦截请求,调用pluginContainer发起构建流程,最后将解析后的文件返回到浏览器。

在 pluginContainer 中会依次执行 resolveId、load、transform 三个方法,这三个方法会将所有插件的三个钩子全部执行一边。注意:是先执行所有插件的resolveId、再执行所有插件load、在执行所有插件的transform。

执行npm run dev流程:

一:执行 resolveConfig 方法,主要是将vite.config文件中的配置与默认配置合并,获取最终配置

 1:读取本地配置,这个过程中需要注意会用到esbuild编译配置文件得到本地配置对象,接着执行mergeConfig方法,将预先配置与本地配置进行合并。

2:对插件进行区分,依据插件执行的时机

    通过sortUserPlugins方法,对插件进行拆分,得到三个数组插件,分别是re、post、normal,这三个数组插件执行的顺序不同。

3:执行config钩子(主要是对config进行hooks)

    通过 runConfigHook 方法 执行每个插件的config钩子,最后返回一个config对象

4:接着处理config配置中的 resolve配置项(主要是将默认的配置与本地的配置进行merge)

5:利用 dotenv-expand 将env文件加载到 process.env 环境变量中

6:将本地配置的build与默认的build选项合并,得到最后最终的build

7:处理server和ssr配置,同上

8:接着是web work的一些配置

9:执行resolvePlugins,梳理所有插件以及插件的执行顺序。在这个方法添加的内置插件(很多)

    vite插件分为内置插件和用户插件,每种类型的插件有三个执行顺序。pre>normal(部分条件插件)>post

    aliasPlugin插件执行顺序最高,主要是处理别名。接着就是prePlugin。

    esbuildPlugin:三方库,编译文件

    importAnalysisPlugin:递归解析文件中的 import ,

    import 'foo' -> import '/@fs//project/node_modules/foo/dist/foo.js'

    import './style.css' ->  import './style.css.js'

二、新建一个connect服务,加入中间件进行拦截。这个文件的编译过程就是在中间件中调用pluginContainer进行的。

插件开发:
插件就是vite在打包的过程中,在不同的时期执行不同的回调钩子。钩子调用的时机大致分为vite加载配置时(config)、vite加载完配置后(configResolved)、vite解析模块路径时(resolveId)、vite加载源文件时(load)、vite对源码进行处理(transform)

对源码处理的方式:
1:将源码转成ast语法树
2:字符串直接切割

流程:
在resolveid 钩子中读取文件路径,在load钩子中读取文件,在Transform钩子中转换。当在文件中读取到新的import,接着重新走一边以上流程

钩子总结:

1:全局钩子

config:修改默认配置

configResolved:获取加载后的配置

2:局部钩子

resolveid:解析文件路径,返回给load使用。多个插件有resolveid钩子时,当某一个钩子返回了结果,后续resolveid钩子便不再执行。如果模块名称以/0开头,意思就是 resolveid钩子对该模块不做任何处理,交给后面的钩子处理。


resolveId(id, source) {

          // import jq from 'jquery' id

          // id就是jq,source是上面这段代码所在的文件

          console.log('----------------')

          console.log(id) // 模块名

          console.log(source) // 模块所在的文件

        },

load:根据resolveid钩子返回的路径加载文件,load可以加载磁盘文件、网络文件、虚拟文件。虚拟文件就是在磁盘上不存的,一般指我们在插件中直接返回的字符串

transform:根据需求对加载的源码进行处理(code)

ast语法树:

主要是有两个,acorn和babel/parser,babel是acorn的扩展。增加了类型和写等操作。vite内置了acorn。在处理import时使用了es-module-lexer

上一篇 下一篇

猜你喜欢

热点阅读