为什么我应该捆绑一个库(使用 Rollup 或 Webpack)而不是使用 Babel 进行转译?

rfe*_*tag 5 javascript rollup npm webpack

如果我用 Javascript 编写一个库,与 Rollup 或 Webpack 之类的东西捆绑比仅使用 Babel 进行转译有什么优势?我唯一能想到的是,如果我只是进行转译,那么也许我的所有依赖项实际上都可能是对等依赖项(尽管我不能 100% 确定这是否属实)。但是,如果我正在做一个相对普通的 React 组件(或者我正在构建一个更大的库(例如material-ui)),我可能希望它们成为对等依赖项,所以如果我依赖的话,这才应该是一个问题无论如何,我的消费者不太可能安装多个较小的库。此外,如果我只是进行转译,理论上消费者可以更轻松地导入他们想要的部分(因为每个文件都将被转译并可导入),而不是在捆绑器中使用复杂的配置来输出多个包。

我错过了什么吗?捆绑程序是否为我做了一些工作,作为库开发人员,我想要的不仅仅是确保代码在旧版浏览器中更直接可用,而旧版浏览器可能无法实现我想要使用的现代语言功能?

Phi*_*ang 3

免责声明:此答案假设您使用ECMAScript 模块语法编写代码,这是目前的行业标准。

捆绑还是不捆绑?首先,认识到捆绑器做了两件事:

  1. 他们将多个源文件合并为一个
  2. 他们可以生成多种模块格式的代码(ESM、CommonJS、UMD)

捆绑的优点

提供单个文件

提供单个文件有其好处。即使在当今时代,有些人也喜欢将单个文件拖放*.js到他们的项目中。这包括不知道如何使用捆绑器的初学者。

此外,可以轻松地从 CDN(例如unpkgJSDelivr )导入单个文件,这些 CDN 允许在 NPM 包中热链接文件。作为多个文件分发的库将花费多个网络请求,这会增加初始加载时间。

支持旧浏览器和运行时

您可以选择捆绑或不独立于转译和聚合填充。因此,您需要一个捆绑程序来支持旧浏览器,这种说法通常是不正确的。

然而,不支持 ES 模块的旧浏览器是一个例外——您确实需要考虑对它们进行捆绑。(请阅读下面的反驳)

还有少数非 Node.js JavaScript 运行时(例如Mozilla Rhino)不支持 ES 模块。

限制 API 表面

从理论上讲,消费者更容易进口他们想要的零件

如果您的用户尝试深入了解您的包并导入单个文件,这可能会适得其反:

import {someFunc} from 'amazing-lib/dist/some/file.js'

someFunc() // Accessing an internal feature!
Run Code Online (Sandbox Code Playgroud)

这允许他们以您意想不到的方式访问您的库的内部结构,可能会导致意想不到的副作用。此外,如果您稍后决定修改实现,人们会抱怨您突然通过补丁版本升级破坏了他们的应用程序。

捆绑通常使得访问代码的内部变得不可能。这使您可以放心地更改您的库,而不会违反您和用户之间的相互合同。

请注意,现在我们有了包入口点,这就不再是一个问题了。来自文档:

引入该"exports"字段的现有包将阻止包的使用者使用任何未定义的入口点

捆绑的缺点

更多的工作

显然您需要安装并配置您的捆绑器。这不仅很乏味(尽管工具有了巨大的改进),而且会使您的部署速度变慢。哦,你的意志node_modules会更胖。

无论如何,谁不捆绑?

任何热衷于现代网络开发的人都可能会在他们的项目中使用捆绑器。尤其是那些必须针对没有 ESM 支持的浏览器的可怜的灵魂,将需要一个捆绑器,因为越来越多的库作者不愿意提供 CJS 或 UMD 捆绑包。捆绑你的库有利于一小部分用户。