如何使 Vite 将不同类型的文件输出到不同目录下

在咱使用 Vite 的过程中,会发现所有不管是 CSS,JS 还是其他资源文件,都在 dist 中乱成一堆,不便于管理。

Webpack 可以通过简单的配置输出文件的 plugin 来实现文件类型分离,而 Vite 在生产模式下,也应该由输出文件的东西来控制,不过 Vite 不用 plugin,而是 rollup 配置项。

1. 对文件类型初步判断

首先,通过查阅文档可知 Vite 提供了三种输出的文件类型的路径参数,分别是:

  • 资源文件:assetFileNames
  • 生成的 chunk:chunkFileNames
  • 入口文件:entryFileNames

所以直接把它们搬到 output 里边:

rollupOptions: {
   output: {
      assetFileNames: 'static/assets/[name].[hash][extname]',
      chunkFileNames: 'static/js/[name].[hash].js',
      entryFileNames: 'static/js/[name].[hash].js',
   }
}

注:xxxFileNames 不是单纯的文件名,而实际上是文件的路径。

2. 对资源类型的判断

由于 chunk 和 entry 都是 Javascript 文件,所以可以直接输出到 js 文件夹呐。

然而 asset 资源除了 CSS 之外,可能还有各种图片、字体等等,故需要分门别类地将对应的类型的资源,放在对应文件夹下。

现在咱先脱离 Vite 环境,如果已知资源的文件名,如何通过 Javascript 判断它的类型呢?

咱很容易地可以想出以下的步骤✓

  • 1. 获取文件名为字符串,以 “.” 为界分割成两个或多个字符串。
  • 2. 检测这些字符串中是否包含指定的文件扩展名。
  • 3. 按照不同的扩展名进行分类并 return

接下来以这些代码就可以很简单地实现:

let getType = fileName => {
   if(/\.(woff2|woff|ttf)(\?.*)?$/i.test(fileName)){
      return "字体";
   }
   elseif(/\.(jpe?g|webp|png|svg)(\?.*)?$/i.test(fileName)){
      return "图片";
   }
   elseif(/\.(css)(\?.*)?$/i.test(fileName)){
      return "样式表";
   }
}

let a = getType("iconfont.woff2"); // 字体
let b = getType("banner.jpg"); // 图片
let c = getType("index.css"); // 样式表

3. 资源处理的实践

接下来的步骤,就是将第二步中的函数搬进 rollup 的配置项中,其实到这一步已经简单了。

rollup 对 1 中所提到的这三个 fileNames,实际上不仅可以是固定的值,也可以是返回字符串的函数。而这个函数,只要你写需要传一个参数,不管参数叫什么名,逐个打包文件时 rollup 都会传一个关于这个文件的对象。而我们所需要的文件名字,就是它的 name 属性。

也就是说,下面这段代码中的 asset.name 就相当于咱在 2 中写的 fileName 参数呐↓

rollupOptions: {
   output: {
      assetFileNames: asset => {
         // 这里的 asset.name 即为 2 中的 fileName
      }
   }
}

而接下来就是将它们分门别类地放进各个文件夹,有了咱上面的铺垫,这个问题解决起来已经比较容易了 (*´︶`*)

咱目前需要处理的,就是以下的小问题啦

  • 1. 通过文件扩展名判断文件类型
  • 2. 将文件放到对应文件夹中
rollupOptions: {
   output: {
      assetFileNames: asset => {
         if(/\.(woff2|woff|ttf)(\?.*)?$/i.test(asset.name)){
            let extType = "fonts";
         }
         elseif(/\.(jpe?g|webp|png|svg)(\?.*)?$/i.test(asset.name)){
            let extType = "images";
         }
         elseif(/\.(css)(\?.*)?$/i.test(asset.name)){
            let extType = "css";
         }

          // 2. 将文件放到对应位置
         return `static/${extType}/[name].[hash][extname]`;
      },

      chunkFileNames: 'static/js/[name].[hash].js',
      entryFileNames: 'static/js/[name].[hash].js',
   }
}

主要代码分两大板块,分别以独立的思想去解决问题,接着再将它们拼接起来,完成!

4. 浅谈 Rollup 和 Vite 的关系

你也许会好奇,为什么 Vite 中会出现 Rollup 的配置项呢?

Vite 由于自己研制了一套推翻 Webpack 的完全基于 ESModule 的 HMR 热更新系统,所以开发模式就跟 Rollup 没啥关系了。

然而在生产模式下,由于 Rollup 使用 ES2015 的模块化语法,相对于 Webpack 等所使用的 CommonJS,技术更新,效率更高,编写更简洁,生成的包体积更小,所以 Vite 选择使用了它。

总而言之,简单(但可能不准确地)来说,Rollup 是生产模式下 Vite 的打包内核。

除特殊声明转载之外,本文由博主 云萧只会咕咕咕 原创,依据 CC BY-NC-SA 4.0 许可协议授权,转载请注明出处。(*◦˙▽˙◦)
暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇