一文学会 ts 构建工具 —— tsup

server/2024/10/19 15:24:59/

在这里插入图片描述

文章目录

  • 能打包什么?
  • 安装
  • 用法
    • 自定义配置文件
    • 条件配置
    • 在 package.json 中配置
    • 多入口打包
    • 生成类型声明文件
    • sourcemap
    • 生成格式
    • 自定义输出文件
    • 代码分割
    • 产物目标环境
    • 支持 es5
    • 编译的环境变量
    • 对开发命令行工具友好
    • 监听模式 watch
    • 提供成功构建的钩子 onSuccess
    • 压缩产物 minify
    • 自定义 loader
    • Tree shaking
    • 类型检查
    • 支持 CSS (实验性功能)
    • 元数据文件 metafile
    • 自定义 esbuild 插件和配置
    • 注入 cjs 和 esm shims (垫片)
    • 复制文件到输出目录
    • 在项目中使用 tsup
  • 常见问题
    • error: No matching export in "xxx.ts" for import "xxx"

tsup

Bundle your TypeScript library with no config, powered by esbuild.

tsup 号称不用配置文件,打包 ts 库。底层为 esbuild。tsup 这么宣传,说明它肯定做了很多预设封装,不需要太多配置,开箱即用。

rollup 已经是牛夫人了。

能打包什么?

node.js 支持的都能打包,.js, .json, .mjs.。加上 ts 相关的 .ts, .tsx。

安装

npm i tsup -D
# Or Yarn
yarn add tsup --dev
# Or pnpm
pnpm add tsup -D

用法

tsup [...files]

默认打包到 ./dist
能自动排除 node_modules 。
默认打包为 es5,CommonJS,

eg:

tsup src/index.ts src/cli.ts

生成 dist/index.js 和 dist/cli.js

自定义配置文件

可选的文件:

–config 配置项可指定配置文件。

typescript">import { defineConfig } from 'tsup'export default defineConfig({entry: ['src/index.ts'],splitting: false,sourcemap: true,clean: true,
})

条件配置

导出一个函数,tsup cli 会执行这个函数。

typescript">import { defineConfig } from 'tsup'export default defineConfig((options) => {return {minify: !options.watch,}
})

在 package.json 中配置

typescript">{"tsup": {"entry": ["src/index.ts"],"splitting": false,"sourcemap": true,"clean": true},"scripts": {"build": "tsup"}
}

多入口打包

typescript">export default defineConfig({// Outputs `dist/a.js` and `dist/b.js`.entry: ['src/a.ts', 'src/b.ts'],// Outputs `dist/foo.js` and `dist/bar.js`entry: {foo: 'src/a.ts',bar: 'src/b.ts',},
})

生成类型声明文件

typescript">tsup index.ts --dts

sourcemap

typescript">tsup index.ts --sourcemap

生成格式

支持 esm,cjs (默认) 和 iife。

tsup src/index.ts --format esm,cjs,iife
dist
├── index.mjs         # esm
├── index.global.js   # iife
└── index.js          # cjs

如果 package.json 的 type 字段为 module。命名会变成:

dist
├── index.js          # esm
├── index.global.js   # iife
└── index.cjs         # cjs

自定义输出文件

typescript">export default defineConfig({outExtension({ format }) {return {js: `.${format}.js`,}},
})

代码分割

默认支持 esm ,并且默认开启。CJS 需要 --splitting 手动开启。

产物目标环境

target 选项配置构建产物的目标环境,默认是 node16。

可支持:

  • chrome
  • edge
  • firefox
  • hermes
  • ie
  • ios
  • node
  • opera
  • rhino
  • safari

target 也可以指定 js 版本,比如 es2020,es5。

支持 es5

esbuild 是不支持 es5 的。tsup 是怎么做到的?

tsup 会先打包成 es2020,然后通过 SWC 转成 es5。

编译的环境变量

typescript">tsup src/index.ts --env.NODE_ENV production

对开发命令行工具友好

当入口文件如 src/cli.ts 包含 hashbang(即 #!/bin/env node)时,tsup 会自动使输出文件可执行,因此您无需运行 chmod +x dist/cli.js 来手动设置可执行权限。

监听模式 watch

typescript">tsup src/index.ts --watch

可选择忽视监听的文件:

typescript">tsup src src/index.ts --watch --ignore-watch folder1 --ignore-watch folder2

提供成功构建的钩子 onSuccess

这在监听模式下非常有用。

typescript">import { defineConfig } from 'tsup'export default defineConfig({async onSuccess() {// Start some long running task// Like a serverconst server = http.createServer((req, res) => {res.end('Hello World!')})server.listen(3000)return () => {server.close()}},
})

压缩产物 minify

typescript">tsup src/index.ts --minify

默认是用 esbuild 压缩,也可以用 terser 代替。前提必须安装 terser。

typescript">npm install -D tersertsup src/index.ts --minify terser

tsup.config.js 中,您可以传递 terserOptions,这些选项将原封不动地传递给 terser.minify。

自定义 loader

esbuild 提供这些 loader:

typescript">type Loader =| 'js'| 'jsx'| 'ts'| 'tsx'| 'css'| 'json'| 'text'| 'base64'| 'file'| 'dataurl'| 'binary'| 'copy'| 'default'

会发现上面没有图片的 loader,但我们可以指定 loader 去处理某些后缀的图片。

typescript">import { defineConfig } from 'tsup'export default defineConfig({loader: {'.jpg': 'base64', '.webp': 'file',},
})

Tree shaking

esbuild 默认开启了 tree shaking。但它的 tree shaking 可能有问题,所以 tsup 允许你选择 rollup 的 tree shaking 去替代 esbuild。

typescript">import { defineConfig } from 'tsup'export default defineConfig({treeshake: true, // 使用 rollup tree shaking
}

类型检查

esbuild 之所以快,就是因为它不会执行 ts 类型检查。你应该依靠 IDE 在完成类型检查。
如果你就想在构建时,执行类型检查,可以开启 --dts。
它会生成类型声明文件,自然也会进行类型检查。

支持 CSS (实验性功能)

元数据文件 metafile

传递 --metafile 标志,告诉 esbuild 以 JSON 格式生成一些关于构建的元数据。您可以将输出文件提供给像 bundle buddy 这样的分析工具,以可视化您的包中的模块以及每个模块占用多少空间。

生成的文件格式为:metafile-{format}.json。eg:metafile-cjs.json

自定义 esbuild 插件和配置

typescript">import { defineConfig } from 'tsup'export default defineConfig({esbuildPlugins: [YourPlugin],esbuildOptions(options, context) {options.define.foo = '"bar"'},
})

注入 cjs 和 esm shims (垫片)

shims 本意为垫片,类似于补丁的意思

启用此选项将在构建 esm/cjs 项目时填充一些代码以使其工作。

例如 __dirname 仅在 cjs 模块中可用,而 import.meta.url 仅在 esm 模块中可用。打完补丁后,esm 中就也能用 __dirname 了。

typescript">import { defineConfig } from 'tsup'export default defineConfig({shims: true,
})

打的补丁具体是什么样的?

CJS 项目会添加如下代码:

typescript">// import.meta.url:
(import.meta.url as typeof document) === "undefined"? new URL("file:" + __filename).href: (document.currentScript && document.currentScript.src) || new URL("main.js", document.baseURI).href;

esm 项目会添加如下代码:

typescript">// __dirname
path.dirname(fileURLToPath(import.meta.url))

vite 早期配置中就得使用这段代码。现在可以直接使用 __diranme 了。看来也是把这段代码作为了补丁,默认提供。

复制文件到输出目录

使用 --publicDir 将 ./public 文件夹内的文件复制到输出目录。
您还可以使用 --publicDir [dir] 来选择一个自定义目录。

tsup_347">在项目中使用 tsup

tsup 提供了 js API,可以在 js 中使用。

typescript">import { build } from 'tsup'await build({entry: ['src/index.ts'],sourcemap: true,dts: true,
})

常见问题

error: No matching export in “xxx.ts” for import “xxx”

当您在 tsconfig 中启用了emitDecoratorMetadata时,通常会发生这种情况。
在这种模式下,我们使用 SWC 将装饰器转换为 JavaScript,因此导出的类型将被消除,这就是为什么 esbuild 无法找到相应的导出。
您可以通过将 import 语句从 import {SomeType}更改为import {type SomeType}import type {SomeType}来修复此问题。


http://www.ppmy.cn/server/6090.html

相关文章

Rust常用特型之AsRef和AsMut特型

在Rust标准库中&#xff0c;存在很多常用的工具类特型&#xff0c;它们能帮助我们写出更具有Rust风格的代码。 今天我们要学习的AsRef和AsMut&#xff0c;和前面学习的Deref和DerefMut有那么一点混淆的地方。 当一个类型U实现了AsRef<T>&#xff0c;那么我们可以高效的从…

DevOps(六)Git特点和命令详解

Git 是一个分布式版本控制系统&#xff0c;用于跟踪软件开发过程中对文件的修改&#xff0c;使得团队成员可以在不同的地方工作&#xff0c;同时保持代码的一致性和完整性。它由 Linus Torvalds 于 2005 年开发&#xff0c;主要用于 Linux 内核的开发&#xff0c;后来被广泛应用…

HTML不常用的文本标签

1.标签如下&#xff1a; 代码及相关内容 <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>不常用的文…

算法课程笔记——STL键值对map

map当下标无限的数组 重点是对应关系&#xff0c;一般不修改compare 类比set 没有lowerbound&#xff0c;因为遍历是无序的 ; map不能用sort函数排序 但可用vector转化为map使用 std::set<std::pair<TKEY, mutable TVAL> > ≈ std::map<TKEY, TVAL>

vue3使用阿里oss上传资源(上传图片、视频、文件、pdf等等),删除oss资源。获取STS token的接口

vue3使用阿里oss上传资源 全部oss.ts代码如下&#xff1a; import OSS from "ali-oss";// 获取STS token export const getSTSToken async () > {const STS_TOKEN_URL "....."; // 获取STS token的接口&#xff0c;后端提供// fetch方式可按需更换成…

IDEA Tomcat localhost 日志和 catalina日志乱码(解决)

只需要修改 Tomcat 的 logging.properties D:\work\apache-tomcat-8.5.70-windows-x64\apache-tomcat-8.5.70\conf

短视频流媒体平台的系统设计

1. 功能需求: 我们的系统有两类参与者 内容创作者 •上传任何类型的视频&#xff08;格式编解码器&#xff09;•视频可以被删除•视频元数据•必填项: 标题&#xff0c;作者&#xff0c;描述•选填项: 分类/标签列表•可以随时更新•当视频对观众可用时&#xff0c;向内容创作…

nginx容器化方案预研

一、概述 目前 nginx迁移升级不方便,且生产环境没有编译环境,导致生产环境nginx版本过旧、目前存在安全漏洞无法升级。运维建议容器化nginx,因此预研了此容器方案 二、镜像制作 基础镜像 cloudservice-alpine-base-v1.tar 2.1 加载基础镜像 docker load -i cloudservic…