bunchee 6.3.0 → 6.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -14,8 +14,11 @@
14
14
  </a>
15
15
  </p>
16
16
 
17
- **bunchee** is a zero configuration bundler makes bundling JS/TS library effortless. It's built on top of Rollup and SWC ⚡️, allowing you to focus on writing code and generating multiple bundles (CommonJS or ESModule) at the same time.
18
- It uses the standard exports configuration in `package.json` as the only source of truth, and uses entry file conventions to match your exports and build them into bundles.
17
+ ---
18
+
19
+ **bunchee** is a zero-configuration bundler designed to streamline package building by adhering to the `exports` field in your **package.json**. Powered by Rollup and SWC ⚡️, it generates output based on your config, supporting both CommonJS and ESModules.
20
+
21
+ By using the standard `exports` configuration as the single source of truth, **bunchee** automatically aligns entry file conventions with your exports, ensuring seamless and efficient builds.
19
22
 
20
23
  ## Quick Start
21
24
 
@@ -36,14 +39,14 @@ mkdir src && touch ./src/index.ts && touch package.json
36
39
 
37
40
  Add the exports in `package.json`.
38
41
 
39
- ```json
42
+ ```json5
40
43
  {
41
- "name": "coffee",
42
- "type": "module",
43
- "main": "./dist/index.js",
44
- "scripts": {
45
- "build": "bunchee"
46
- }
44
+ name: 'coffee',
45
+ type: 'module',
46
+ main: './dist/index.js',
47
+ scripts: {
48
+ build: 'bunchee',
49
+ },
47
50
  }
48
51
  ```
49
52
 
@@ -53,192 +56,118 @@ Add the exports in `package.json`.
53
56
  npm run build
54
57
  ```
55
58
 
56
- Then files in `src` folders will be treated as entry files and match the export names in package.json.
57
- Simply like Node.js module resolution, each export name will match the file in `src/` directory.
58
-
59
- For example:
60
-
61
- - `src/index.ts` will match the exports name `"."` or the only main export.
62
- - `src/lite.ts` will match the exports name `"./lite"`.
63
- - `src/react/index.ts` will match the exports name `"./react"`.
64
-
65
- Now just run `npm run build` (or `pnpm build` / `yarn build`) if you're using these package managers, `bunchee` will find the entry files and build them.
66
- The output format will based on the exports condition and also the file extension. Given an example:
67
-
68
- - It's CommonJS for `require` and ESM for `import` based on the exports condition.
69
- - It's CommonJS for `.js` and ESM for `.mjs` based on the extension regardless the exports condition. Then for export condition like "node" you could choose the format with your extension.
70
-
71
- > [!NOTE]
72
- > All the `dependencies` and `peerDependencies` will be marked as external automatically and not included in the bundle. If you want to include them in the bundle, you can use the `--no-external` option.
73
-
74
- #### Prepare Package
75
-
76
- ```sh
77
- # Use bunchee to prepare package.json configuration
78
- npm exec bunchee prepare
79
- # "If you're using other package manager such as pnpm"
80
- # pnpm bunchee prepare
59
+ ## Usage
81
60
 
82
- # "Or use with npx"
83
- # npx bunchee@latest prepare
84
- ```
61
+ ### Entry Files
85
62
 
86
- Or you can checkout the following cases to configure your package.json.
63
+ Then files in `src` folders will be treated as entry files and match the export names in package.json.
64
+ Simply like Node.js module resolution, each export name will match the file in `src/` directory.
87
65
 
88
- <details>
89
- <summary>JavaScript ESModule</summary>
66
+ Here's a example of entry files and exports configuration:
90
67
 
91
- Then use use the [exports field in package.json](https://nodejs.org/api/packages.html#exports-sugar) to configure different conditions and leverage the same functionality as other bundlers, such as webpack. The exports field allows you to define multiple conditions.
68
+ | **File** | **Exports Name** |
69
+ | -------------------- | ---------------------- |
70
+ | `src/index.ts` | `"."` (default export) |
71
+ | `src/lite.ts` | `"./lite"` |
72
+ | `src/react/index.ts` | `"./react"` |
92
73
 
93
- ```json
74
+ ```json5
94
75
  {
95
- "files": ["dist"],
96
- "type": "module",
97
- "exports": {
98
- ".": "./dist/es/index.js",
99
- "./react": "./dist/es/react.js"
76
+ name: 'coffee',
77
+ scripts: {
78
+ build: 'bunchee',
100
79
  },
101
- "scripts": {
102
- "build": "bunchee"
103
- }
104
- }
105
- ```
106
-
107
- </details>
108
-
109
- <details>
110
- <summary>TypeScript</summary>
111
-
112
- If you're build a TypeScript library, separate the types from the main entry file and specify the types path in package.json. Types exports need to stay on the top of each export with `types` condition, and you can use `default` condition for the JS bundle file.
113
-
114
- ```json
115
- {
116
- "files": ["dist"],
117
- "type": "module",
118
- "main": "./dist/index.js",
119
- "exports": {
120
- ".": {
121
- "types": "./dist/index.d.ts",
122
- "default": "./dist/index.js"
80
+ type: 'module',
81
+ exports: {
82
+ // entry: ./src/index.ts
83
+ '.': {
84
+ import: './dist/index.js',
85
+ require: './dist/index.cjs',
123
86
  },
124
- "./react": {
125
- "types": "./dist/react/index.d.ts",
126
- "default": "./dist/react/index.js"
127
- }
128
- },
129
- "scripts": {
130
- "build": "bunchee"
131
- }
132
- }
133
- ```
134
-
135
- </details>
136
87
 
137
- <details>
138
- <summary>Hybrid (CJS & ESM) Module Resolution with TypeScript</summary>
139
- If you're using TypeScript with Node 10 and Node 16 module resolution, you can use the `types` field in package.json to specify the types path. Then `bunchee` will generate the types file with the same extension as the main entry file.
88
+ // entry: ./src/lite.ts
89
+ './lite': './dist/lite.js',
140
90
 
141
- _NOTE_: When you're using `.mjs` or `.cjs` extensions with TypeScript and modern module resolution (above node16), TypeScript will require specific type declaration files like `.d.mts` or `.d.cts` to match the extension. `bunchee` can automatically generate them to match the types to match the condition and extensions.
142
-
143
- ```json
144
- {
145
- "files": ["dist"],
146
- "type": "module",
147
- "main": "./dist/index.js",
148
- "module": "./dist/index.js",
149
- "types": "./dist/index.d.ts",
150
- "exports": {
151
- "import": {
152
- "types": "./dist/index.d.ts",
153
- "default": "./dist/index.js"
154
- },
155
- "require": {
156
- "types": "./dist/index.d.cts",
157
- "default": "./dist/index.cjs"
158
- }
91
+ // entry: ./src/react/index.ts
92
+ './react': './dist/react.js',
159
93
  },
160
- "scripts": {
161
- "build": "bunchee"
162
- }
163
94
  }
164
95
  ```
165
96
 
166
- </details>
97
+ ### Output Formats
167
98
 
168
- #### Lint Package
99
+ **bunchee** detects the format of each entry-point based on export condition type or the file extension. It supports the following output formats:
169
100
 
170
- `lint` command will check the package.json configuration is valid or not, it can valid few things like:
101
+ | `package.json` Field | Output format |
102
+ | -------------------- | -------------------------------- |
103
+ | `main` | Default |
104
+ | `types` | TypeScript declaration |
105
+ | `exports` | Default |
106
+ | `exports.require` | CommonJS |
107
+ | `exports.import` | Default |
108
+ | `exports.types` | TypeScript declaration of export |
109
+ | `bin` | Default |
110
+ | `bin.<name>` | Default |
171
111
 
172
- - if the entry files are matched with the exports conditions.
173
- - if the entry files are matched with the exports paths.
112
+ The **Default** output format is determined by the file extension:
174
113
 
175
- ```sh
176
- # Use bunchee to lint if the package.json configuration is valid
177
- npm exec bunchee lint
178
- ```
114
+ | File Extension | Output format |
115
+ | -------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
116
+ | `.js` | Determined by `package.json#type`, CommonJS by default |
117
+ | `.cjs` | [CommonJS](https://nodejs.org/api/packages.html#:~:text=Files%20ending%20with%20.cjs%20are%20always%20loaded%20as%20CommonJS%20regardless%20of%20the%20nearest%20parent%20package.json) |
118
+ | `.mjs` | [ECMAScript Modules](https://nodejs.org/api/modules.html#the-mjs-extension) |
179
119
 
180
- ## Usage
120
+ ### External Dependencies
181
121
 
182
- ### File Conventions
122
+ The `dependencies` and `peerDependencies` will be marked as externalized and wont be included in the bundle. If you want to include them in the bundle, you can use the `--no-external` option. Or you can import the `devDependencies` in your source code to bundle them.
183
123
 
184
- While `exports` field is becoming the standard of exporting in node.js, bunchee also supports to build multiple exports all in one command.
124
+ ```json5
125
+ {
126
+ // Externalized
127
+ dependencies: {
128
+ /* ... */
129
+ },
130
+ peerDependencies: {
131
+ /* ... */
132
+ },
185
133
 
186
- Provide entry files with the name (`[name].[ext]`) that matches the exported name from exports field in package.json. For instance:
134
+ // Bundled
135
+ devDependencies: {
136
+ /* ... */
137
+ },
138
+ }
139
+ ```
187
140
 
188
- - `<cwd>/src/index.ts` will match `"."` export name or the if there's only one main export.
189
- - `<cwd>/src/lite.ts` will match `"./lite"` export name.
141
+ ### Multiple Runtime
190
142
 
191
- The build script can be just `bunchee` without configure any input sources for each exports. Of course you can still specify other arguments as you need.
192
- Briefly, the entry files from `src/` folder will do matching with `exports` conditions from `package.json` and build them into bundles.
143
+ For exports condition like `react-native`, `react-server` and `edge-light` as they're special platforms, they could have different exports or different code conditions. In this case bunchee provides an override input source file convention if you want to build them as different code bundle.
193
144
 
194
- Assuming you have default export package as `"."` and subpath export `"./lite"` with different exports condition listed in package.json
145
+ For instance:
195
146
 
196
- ```json
147
+ ```json5
197
148
  {
198
- "name": "example",
199
- "scripts": {
200
- "build": "bunchee"
149
+ exports: {
150
+ 'react-server': './dist/react-server.mjs',
151
+ 'edge-light': './dist/edge-light.mjs',
152
+ import: './dist/index.mjs',
201
153
  },
202
- "type": "module",
203
- "exports": {
204
- "./lite": "./dist/lite.js",
205
- ".": {
206
- "import": "./dist/index.js",
207
- "require": "./dist/index.cjs"
208
- }
209
- }
210
154
  }
211
155
  ```
212
156
 
213
- Then you need to add two entry files `index.ts` and `lite.ts` in project root directory to match the export name `"."` and `"./lite"`, bunchee will associate these entry files with export names then use them as input source and output paths information.
214
-
215
- ```
216
- - my-lib/
217
- |- src/
218
- |- lite.ts
219
- |- index.ts
220
- |- package.json
221
- ```
222
-
223
- It will also look up for `index.<ext>` file under the directory having the name of the export path. For example, if you have `"./lite": "./dist/lite.js"` in exports field, then it will look up for `./lite/index.js` as the entry file as well.
224
-
225
- ### Multiple Runtime
226
-
227
- For exports condition like `react-native`, `react-server` and `edge-light` as they're special platforms, they could have different exports or different code conditions. In this case bunchee provides an override input source file convention if you want to build them as different code bundle.
157
+ ### Path Alias
228
158
 
229
- For instance:
159
+ `bunchee` supports both TypeScript `paths` config and Node.js [`imports field`](https://nodejs.org/api/packages.html#subpath-imports) in `package.json` for path aliasing. It will resolve the path alias to the correct file path. If you're using modern TypeScript versions, you can also directly configure the `imports` field in `package.json` and it will work as a charm.
230
160
 
231
- ```json
161
+ ```json5
162
+ // package.json
232
163
  {
233
- "exports": {
234
- "react-server": "./dist/react-server.mjs",
235
- "edge-light": "./dist/edge-light.mjs",
236
- "import": "./dist/index.mjs"
237
- }
164
+ imports: {
165
+ '#util': './src/utils.ts',
166
+ },
238
167
  }
239
168
  ```
240
169
 
241
- ### Executables
170
+ ### Binary CLI
242
171
 
243
172
  To build executable files with the `bin` field in package.json, `bunchee` requires you to create the `bin` directory under `src` directory. The source file matching will be same as the entry files convention.
244
173
 
@@ -252,45 +181,49 @@ For example:
252
181
 
253
182
  This will match the `bin` field in package.json as:
254
183
 
255
- ```json
184
+ ```json5
256
185
  {
257
- "bin": "./dist/bin.js"
186
+ bin: './dist/bin.js',
258
187
  }
259
188
  ```
260
189
 
261
- For multiple executable files, you can create multiple files under the `bin` directory.
190
+ If you have multiple binaries, you can create multiple files under the `bin` directory. Check the below example for more details.
191
+
192
+ <details>
193
+ <summary>Multiple Binaries</summary>
194
+
195
+ For named executable files, you can create multiple files under the `bin` directory.
262
196
 
263
197
  ```bash
264
198
  |- src/
265
199
  |- bin/
266
- |- foo.ts
267
- |- bar.ts
200
+
268
201
  ```
269
202
 
270
203
  This will match the `bin` field in package.json as:
271
204
 
272
- ```json
205
+ ```json5
273
206
  {
274
- "bin": {
275
- "foo": "./dist/bin/a.js",
276
- "bar": "./dist/bin/b.js"
277
- }
207
+ bin: {
208
+ foo: './dist/bin/a.js',
209
+ bar: './dist/bin/b.js',
210
+ },
278
211
  }
279
212
  ```
280
213
 
214
+ </details>
215
+
281
216
  > Note: For multiple `bin` files, the filename should match the key name in the `bin` field.
282
217
 
283
218
  ### Server Components
284
219
 
285
- `bunchee` supports to build server components and server actions with library directives like `"use client"` or `"use server"`. It will generate the corresponding chunks for client and server that scope the client and server boundaries properly.
286
- Then when the library is integrated to an app such as Next.js, app bundler can transform the client components and server actions correctly and maximum the benefits.
287
-
288
- If you're using `"use client"` or `"use server"` in entry file, then it will be preserved on top and the dist file of that entry will become a client component.
289
- If you're using `"use client"` or `"use server"` in a file that used as a dependency for an entry, then that file containing directives be split into a separate chunk and hoist the directives to the top of the chunk.
220
+ **bunchee** supports building React Server Components and Server Actions with directives like `"use client"` or `"use server"`. It generates separate chunks for the server or client boundaries. When integrated to framework like Next.js, it can correctly handles the boundaries with the split chunks.
290
221
 
291
222
  ### Shared Modules
292
223
 
293
- In some cases, you may need to share code across multiple bundles without promoting them to separate entries or exports. These modules should be bundled into shared chunks that can be reused by various bundles. By convention, files or directories **prefixed with an underscore** (`_<name>.<ext>` or `_<name>/**`) are treated as **shared modules**. They're private and not exposed publicly as entry points or exports. Testing, mocking related files are ignored. e.g. `_foo/a.test.ts` will not be treated as shared module.
224
+ Sometimes, you may want to share a chunk across multiple bundles without promoting it to separate entries or exports, such as single instance of React context module, shared utils, etc. In these cases, **shared modules** will help you achieve the goal. Files or directories **prefixed with an underscore** (`_<name>.<ext>` or `_<name>/**`) will be treated as **shared modules**.
225
+
226
+ These conventions are kept private and are not going to be treat as shared modules or entry points. For example, test or mock files like `_foo/a.test.ts` will be ignored and not included as shared modules.
294
227
 
295
228
  <details>
296
229
  <summary>Shared Utils Example</summary>
@@ -351,38 +284,23 @@ This convention keeps shared modules private while enabling efficient bundling a
351
284
 
352
285
  #### CLI Options
353
286
 
354
- `bunchee` CLI provides few options to create different bundles or generating types.
355
-
356
- - Output (`-o <file>`): Specify output filename.
357
- - Format (`-f <format>`): Set output format (default: `'esm'`).
358
- - External (`--external <dep,>`): Specifying extra external dependencies, by default it is the list of `dependencies` and `peerDependencies` from `package.json`. Values are separate by comma.
359
- - Target (`--target <target>`): Set ECMAScript target (default: `'es2015'`).
360
- - Runtime (`--runtime <runtime>`): Set build runtime (default: `'browser'`).
361
- - Environment (`--env <env,>`): Define environment variables. (default: `[]`, separate by comma)
362
- - Working Directory (`--cwd <cwd>`): Set current working directory where containing `package.json`.
363
- - Minify (`-m`): Compress output.
364
- - Watch (`-w`): Watch for source file changes.
365
- - No Clean(`--no-clean`): Do not clean the dist folder before building. (default: `false`)
366
- - TSConfig (`--tsconfig <path>`): Specify the path to the TypeScript configuration file. (default: `tsconfig.json`)
367
- - Bundle Types (`--dts-bundle`): Bundle type declaration files. (default: `false`)
287
+ `bunchee` CLI provides few options to create different bundles or generating types. Call `bunchee --help` to see the help information in the terminal.
288
+
289
+ Here are the available options for the CLI:
368
290
 
369
291
  ```sh
370
292
  cd <project-root-dir>
371
293
 
372
- # specifying input, output and format
294
+ # Build based on the package.json configuration
295
+ bunchee --runtime node -o ./dist/bundle.js
296
+ bunchee -f esm -o --target es2022 ./dist/bundle.esm.js
373
297
 
374
- bunchee ./src/index.js -f cjs -o ./dist/bundle.js
375
- bunchee ./src/index.js -f esm -o ./dist/bundle.esm.js
376
-
377
- # build node.js library, or change target to es2019
378
- bunchee ./src/index.js --runtime node --target es2019
298
+ # Specify the input source file
299
+ bunchee ./src/foo.ts -o ./dist/foo.js
379
300
  ```
380
301
 
381
302
  #### Specifying extra external dependencies
382
303
 
383
- By default, `bunchee` will mark all the `dependencies` and `peerDependencies` as externals so you don't need to pass them as CLI args.
384
- But if there's any dependency that used but not in the dependency list and you want to mark as external, you can use the `--external` option to specify them.
385
-
386
304
  ```sh
387
305
  bunchee --external=dep1,dep2,dep3
388
306
  ```
@@ -399,6 +317,112 @@ bunchee --no-external
399
317
 
400
318
  This will include all dependencies within your output bundle.
401
319
 
320
+ #### Prepare Package
321
+
322
+ ```sh
323
+ # Use bunchee to prepare package.json configuration
324
+ npm exec bunchee prepare
325
+ # "If you're using other package manager such as pnpm"
326
+ # pnpm bunchee prepare
327
+
328
+ # "Or use with npx"
329
+ # npx bunchee@latest prepare
330
+ ```
331
+
332
+ Or you can checkout the following cases to configure your package.json.
333
+
334
+ <details>
335
+ <summary>JavaScript ESModule</summary>
336
+
337
+ Then use use the [exports field in package.json](https://nodejs.org/api/packages.html#exports-sugar) to configure different conditions and leverage the same functionality as other bundlers, such as webpack. The exports field allows you to define multiple conditions.
338
+
339
+ ```json5
340
+ {
341
+ files: ['dist'],
342
+ type: 'module',
343
+ exports: {
344
+ '.': './dist/es/index.js',
345
+ './react': './dist/es/react.js',
346
+ },
347
+ scripts: {
348
+ build: 'bunchee',
349
+ },
350
+ }
351
+ ```
352
+
353
+ </details>
354
+
355
+ <details>
356
+ <summary>TypeScript</summary>
357
+
358
+ If you're build a TypeScript library, separate the types from the main entry file and specify the types path in package.json. Types exports need to stay on the top of each export with `types` condition, and you can use `default` condition for the JS bundle file.
359
+
360
+ ```json5
361
+ {
362
+ files: ['dist'],
363
+ type: 'module',
364
+ main: './dist/index.js',
365
+ exports: {
366
+ '.': {
367
+ types: './dist/index.d.ts',
368
+ default: './dist/index.js',
369
+ },
370
+ './react': {
371
+ types: './dist/react/index.d.ts',
372
+ default: './dist/react/index.js',
373
+ },
374
+ },
375
+ scripts: {
376
+ build: 'bunchee',
377
+ },
378
+ }
379
+ ```
380
+
381
+ </details>
382
+
383
+ <details>
384
+ <summary>Hybrid (CJS & ESM) Module Resolution with TypeScript</summary>
385
+ If you're using TypeScript with Node 10 and Node 16 module resolution, you can use the `types` field in package.json to specify the types path. Then `bunchee` will generate the types file with the same extension as the main entry file.
386
+
387
+ _NOTE_: When you're using `.mjs` or `.cjs` extensions with TypeScript and modern module resolution (above node16), TypeScript will require specific type declaration files like `.d.mts` or `.d.cts` to match the extension. `bunchee` can automatically generate them to match the types to match the condition and extensions.
388
+
389
+ ```json5
390
+ {
391
+ files: ['dist'],
392
+ type: 'module',
393
+ main: './dist/index.js',
394
+ module: './dist/index.js',
395
+ types: './dist/index.d.ts',
396
+ exports: {
397
+ import: {
398
+ types: './dist/index.d.ts',
399
+ default: './dist/index.js',
400
+ },
401
+ require: {
402
+ types: './dist/index.d.cts',
403
+ default: './dist/index.cjs',
404
+ },
405
+ },
406
+ scripts: {
407
+ build: 'bunchee',
408
+ },
409
+ }
410
+ ```
411
+
412
+ </details>
413
+
414
+ #### Lint Package
415
+
416
+ `lint` command will check the package.json configuration is valid or not, it can valid few things like:
417
+
418
+ - if the entry files are matched with the exports conditions.
419
+ - if the entry files are matched with the exports paths.
420
+
421
+ ```sh
422
+ # Use bunchee to lint if the package.json configuration is valid
423
+ npm exec bunchee lint
424
+ ```
425
+
402
426
  ### Environment Variables
403
427
 
404
428
  To pass environment variables to your bundled code, use the --env option followed by a comma-separated list of environment variable names:
@@ -424,12 +448,12 @@ This will match the export name `"react-server"` and `"edge-light"` then use the
424
448
 
425
449
  `process.env.NODE_ENV` is injected by default if present that you don't need to manually inject yourself. If you need to separate the development build and production build, `bunchee` provides different export conditions for development and production mode with `development` and `production` export conditions.
426
450
 
427
- ```json
451
+ ```json5
428
452
  {
429
- "exports": {
430
- "development": "./dist/index.development.js",
431
- "production": "./dist/index.production.js"
432
- }
453
+ exports: {
454
+ development: './dist/index.development.js',
455
+ production: './dist/index.production.js',
456
+ },
433
457
  }
434
458
  ```
435
459
 
@@ -512,14 +536,14 @@ To target a range of browsers, you can use the `browserslist` field in `package.
512
536
 
513
537
  For example:
514
538
 
515
- ```json
539
+ ```json5
516
540
  {
517
- "browserslist": [
518
- "last 1 version",
519
- "> 1%",
520
- "maintained node versions",
521
- "not dead"
522
- ]
541
+ browserslist: [
542
+ 'last 1 version',
543
+ '> 1%',
544
+ 'maintained node versions',
545
+ 'not dead',
546
+ ],
523
547
  }
524
548
  ```
525
549
 
package/dist/bin/cli.js CHANGED
@@ -69,9 +69,13 @@ const tsExtensions = new Set([
69
69
  ]);
70
70
  const DEFAULT_TS_CONFIG = {
71
71
  compilerOptions: {
72
+ target: 'ES2022',
72
73
  module: 'ESNext',
73
74
  moduleResolution: 'bundler'
74
- }
75
+ },
76
+ include: [
77
+ 'src'
78
+ ]
75
79
  };
76
80
  const BINARY_TAG = '$binary';
77
81
  const PRIVATE_GLOB_PATTERN = '**/_*/**';
@@ -642,7 +646,7 @@ function lint$1(pkg) {
642
646
  }
643
647
  }
644
648
 
645
- var version = "6.3.0";
649
+ var version = "6.3.1";
646
650
 
647
651
  async function writeDefaultTsconfig(tsConfigPath) {
648
652
  await fs.promises.writeFile(tsConfigPath, JSON.stringify(DEFAULT_TS_CONFIG, null, 2), 'utf-8');
@@ -1198,11 +1202,11 @@ async function run(args) {
1198
1202
  cwd,
1199
1203
  target,
1200
1204
  runtime,
1201
- external: args.external === null ? null : ((_args_external = args.external) == null ? void 0 : _args_external.split(',')) || [],
1205
+ external: args.external === null ? null : ((_args_external = args.external) == null ? undefined : _args_external.split(',')) || [],
1202
1206
  watch: !!watch,
1203
1207
  minify: !!minify,
1204
1208
  sourcemap: sourcemap === false ? false : true,
1205
- env: (env == null ? void 0 : env.split(',')) || [],
1209
+ env: (env == null ? undefined : env.split(',')) || [],
1206
1210
  clean,
1207
1211
  tsconfig
1208
1212
  };
@@ -1256,7 +1260,7 @@ async function run(args) {
1256
1260
  if (assetJobs.length === 0) {
1257
1261
  logger.warn('The "src" directory does not contain any entry files. ' + 'For proper usage, please refer to the following link: ' + 'https://github.com/huozhi/bunchee#usage');
1258
1262
  }
1259
- const outputState = initialBuildContext == null ? void 0 : initialBuildContext.pluginContext.outputState;
1263
+ const outputState = initialBuildContext == null ? undefined : initialBuildContext.pluginContext.outputState;
1260
1264
  if (outputState) {
1261
1265
  logOutputState(outputState.getSizeStats());
1262
1266
  }
@@ -1268,7 +1272,7 @@ async function run(args) {
1268
1272
  onBuildEnd
1269
1273
  };
1270
1274
  if (watch) {
1271
- logger.log(`Watching project ${cwd}...`);
1275
+ logger.log(`Watching changes in the project directory...`);
1272
1276
  }
1273
1277
  try {
1274
1278
  await index_js.bundle(cliEntry, bundleConfig);
@@ -1279,7 +1283,7 @@ async function run(args) {
1279
1283
  error: err
1280
1284
  };
1281
1285
  }
1282
- if ((buildError == null ? void 0 : buildError.digest) === 'bunchee:not-existed') {
1286
+ if ((buildError == null ? undefined : buildError.digest) === 'bunchee:not-existed') {
1283
1287
  help();
1284
1288
  } else {
1285
1289
  if (watch) {
package/dist/index.js CHANGED
@@ -249,9 +249,13 @@ const tsExtensions = new Set([
249
249
  ]);
250
250
  const DEFAULT_TS_CONFIG = {
251
251
  compilerOptions: {
252
+ target: 'ES2022',
252
253
  module: 'ESNext',
253
254
  moduleResolution: 'bundler'
254
- }
255
+ },
256
+ include: [
257
+ 'src'
258
+ ]
255
259
  };
256
260
  const BINARY_TAG = '$binary';
257
261
  const PRIVATE_GLOB_PATTERN = '**/_*/**';
@@ -1003,7 +1007,7 @@ function createOutputState({ entries }) {
1003
1007
  };
1004
1008
  }
1005
1009
 
1006
- const memoize = (fn, cacheKey, cacheArg)=>{
1010
+ const createMemoize = (fn, cacheKey, cacheArg)=>{
1007
1011
  const cache = cacheArg || new Map();
1008
1012
  return (...args)=>{
1009
1013
  const key = cacheKey ? typeof cacheKey === 'function' ? cacheKey(...args) : cacheKey : JSON.stringify({
@@ -1020,8 +1024,9 @@ const memoize = (fn, cacheKey, cacheArg)=>{
1020
1024
  };
1021
1025
  const memoizeByKey = (fn)=>{
1022
1026
  const cache = new Map();
1023
- return (cacheKey)=>memoize(fn, cacheKey, cache);
1027
+ return (cacheKey)=>createMemoize(fn, cacheKey, cache);
1024
1028
  };
1029
+ const memoize = (fn)=>createMemoize(fn);
1025
1030
 
1026
1031
  let hasLoggedTsWarning = false;
1027
1032
  function resolveTypescript(cwd) {
@@ -1049,11 +1054,14 @@ function resolveTypescript(cwd) {
1049
1054
  }
1050
1055
  return ts;
1051
1056
  }
1052
- function resolveTsConfigHandler(cwd, tsconfig = 'tsconfig.json') {
1053
- let tsCompilerOptions = {};
1057
+ const resolveTsConfigPath = memoize((cwd, tsconfigFileName = 'tsconfig.json')=>{
1054
1058
  let tsConfigPath;
1055
- tsConfigPath = path.resolve(cwd, tsconfig);
1056
- if (fileExists(tsConfigPath)) {
1059
+ tsConfigPath = path.resolve(cwd, tsconfigFileName);
1060
+ return fileExists(tsConfigPath) ? tsConfigPath : undefined;
1061
+ });
1062
+ function resolveTsConfigHandler(cwd, tsConfigPath) {
1063
+ let tsCompilerOptions = {};
1064
+ if (tsConfigPath) {
1057
1065
  // Use the original ts handler to avoid memory leak
1058
1066
  const ts = resolveTypescript(cwd);
1059
1067
  const basePath = tsConfigPath ? path.dirname(tsConfigPath) : cwd;
@@ -1067,7 +1075,7 @@ function resolveTsConfigHandler(cwd, tsconfig = 'tsconfig.json') {
1067
1075
  tsConfigPath
1068
1076
  };
1069
1077
  }
1070
- const resolveTsConfig = memoizeByKey(resolveTsConfigHandler)();
1078
+ const resolveTsConfig = memoize(resolveTsConfigHandler);
1071
1079
  async function convertCompilerOptions(cwd, json) {
1072
1080
  // Use the original ts handler to avoid memory leak
1073
1081
  const ts = resolveTypescript(cwd);
@@ -1345,7 +1353,7 @@ function aliasEntries({ entry: sourceFilePath, conditionNames, entries, format,
1345
1353
  if (dts) {
1346
1354
  var _exportMapEntries_find;
1347
1355
  // Find the type with format condition first
1348
- matchedBundlePath = (_exportMapEntries_find = exportMapEntries.find(findTypesFileCallback)) == null ? void 0 : _exportMapEntries_find.bundlePath;
1356
+ matchedBundlePath = (_exportMapEntries_find = exportMapEntries.find(findTypesFileCallback)) == null ? undefined : _exportMapEntries_find.bundlePath;
1349
1357
  // If theres no format specific types such as import.types or require.types,
1350
1358
  // fallback to the general types file.
1351
1359
  if (!matchedBundlePath) {
@@ -1355,13 +1363,13 @@ function aliasEntries({ entry: sourceFilePath, conditionNames, entries, format,
1355
1363
  ...item,
1356
1364
  format: undefined
1357
1365
  });
1358
- })) == null ? void 0 : _exportMapEntries_find1.bundlePath;
1366
+ })) == null ? undefined : _exportMapEntries_find1.bundlePath;
1359
1367
  }
1360
1368
  } else {
1361
1369
  var _exportMapEntries_find2;
1362
1370
  matchedBundlePath = (_exportMapEntries_find2 = exportMapEntries.find((item)=>{
1363
1371
  return findJsBundlePathCallback(item, specialCondition);
1364
- })) == null ? void 0 : _exportMapEntries_find2.bundlePath;
1372
+ })) == null ? undefined : _exportMapEntries_find2.bundlePath;
1365
1373
  }
1366
1374
  if (matchedBundlePath) {
1367
1375
  if (!sourceToRelativeBundleMap.has(exportCondition.source)) sourceToRelativeBundleMap.set(exportCondition.source, matchedBundlePath);
@@ -1519,7 +1527,7 @@ async function buildInputConfig(entry, bundleConfig, exportCondition, buildConte
1519
1527
  const sizePlugin = pluginContext.outputState.plugin(cwd);
1520
1528
  // common plugins for both dts and ts assets that need to be processed
1521
1529
  // If it's a .d.ts file under non-ESM package or .d.cts file, use cjs types alias.
1522
- const aliasFormat = dts ? ((_bundleConfig_file = bundleConfig.file) == null ? void 0 : _bundleConfig_file.endsWith('.d.cts')) || ((_bundleConfig_file1 = bundleConfig.file) == null ? void 0 : _bundleConfig_file1.endsWith('.d.ts')) && !isESModulePackage(pkg.type) ? 'cjs' : 'esm' : bundleConfig.format;
1530
+ const aliasFormat = dts ? ((_bundleConfig_file = bundleConfig.file) == null ? undefined : _bundleConfig_file.endsWith('.d.cts')) || ((_bundleConfig_file1 = bundleConfig.file) == null ? undefined : _bundleConfig_file1.endsWith('.d.ts')) && !isESModulePackage(pkg.type) ? 'cjs' : 'esm' : bundleConfig.format;
1523
1531
  const currentConditionNames = Object.keys(exportCondition.export)[0];
1524
1532
  const aliasPlugin = aliasEntries({
1525
1533
  entry,
@@ -1685,7 +1693,7 @@ async function buildOutputConfigs(bundleConfig, exportCondition, buildContext, d
1685
1693
  const { format } = bundleConfig;
1686
1694
  const { entries, pkg, cwd, tsOptions: { tsCompilerOptions }, pluginContext } = buildContext;
1687
1695
  // Add esm mark and interop helper if esm export is detected
1688
- const useEsModuleMark = tsCompilerOptions == null ? void 0 : tsCompilerOptions.esModuleInterop;
1696
+ const useEsModuleMark = tsCompilerOptions == null ? undefined : tsCompilerOptions.esModuleInterop;
1689
1697
  const absoluteOutputFile = path.resolve(cwd, bundleConfig.file);
1690
1698
  const isEsmPkg = isESModulePackage(pkg.type);
1691
1699
  const name = filePathWithoutExtension(absoluteOutputFile);
@@ -1893,11 +1901,12 @@ async function bundle(cliEntryPath, { cwd: _cwd, ...options } = {}) {
1893
1901
  // Original input file path, client path might change later
1894
1902
  const inputFile = cliEntryPath;
1895
1903
  const isFromCli = Boolean(cliEntryPath);
1896
- let tsConfig = resolveTsConfig(cwd, options.tsconfig);
1897
- let hasTsConfig = Boolean(tsConfig == null ? void 0 : tsConfig.tsConfigPath);
1904
+ const tsConfigPath = resolveTsConfigPath(cwd, options.tsconfig);
1905
+ let tsConfig = resolveTsConfig(cwd, tsConfigPath);
1906
+ let hasTsConfig = Boolean(tsConfig == null ? undefined : tsConfig.tsConfigPath);
1898
1907
  const defaultTsOptions = {
1899
- tsConfigPath: tsConfig == null ? void 0 : tsConfig.tsConfigPath,
1900
- tsCompilerOptions: (tsConfig == null ? void 0 : tsConfig.tsCompilerOptions) || {}
1908
+ tsConfigPath: tsConfig == null ? undefined : tsConfig.tsConfigPath,
1909
+ tsCompilerOptions: (tsConfig == null ? undefined : tsConfig.tsCompilerOptions) || {}
1901
1910
  };
1902
1911
  // Handle single entry file
1903
1912
  if (!isMultiEntries) {
@@ -1947,10 +1956,16 @@ async function bundle(cliEntryPath, { cwd: _cwd, ...options } = {}) {
1947
1956
  }
1948
1957
  const entries = await collectEntriesFromParsedExports(cwd, parsedExportsInfo, pkg, inputFile);
1949
1958
  const hasTypeScriptFiles = Object.values(entries).some((entry)=>isTypescriptFile(entry.source));
1959
+ // If there's no tsconfig, create one.
1950
1960
  if (hasTypeScriptFiles && !hasTsConfig) {
1951
- const tsConfigPath = path.resolve(cwd, 'tsconfig.json');
1952
- defaultTsOptions.tsConfigPath = tsConfigPath;
1953
- await writeDefaultTsconfig(tsConfigPath);
1961
+ // Check if tsconfig.json exists in the project first.
1962
+ // If not, create one with default settings.
1963
+ // Otherwise, use the existing one.
1964
+ const defaultTsConfigPath = path.resolve(cwd, 'tsconfig.json');
1965
+ if (!fileExists(defaultTsConfigPath)) {
1966
+ await writeDefaultTsconfig(defaultTsConfigPath);
1967
+ }
1968
+ defaultTsOptions.tsConfigPath = defaultTsConfigPath;
1954
1969
  hasTsConfig = true;
1955
1970
  }
1956
1971
  let browserslistConfig;
@@ -1972,14 +1987,14 @@ async function bundle(cliEntryPath, { cwd: _cwd, ...options } = {}) {
1972
1987
  moduleDirectiveLayerMap: new Map()
1973
1988
  }
1974
1989
  };
1975
- (_options__callbacks = options._callbacks) == null ? void 0 : (_options__callbacks_onBuildStart = _options__callbacks.onBuildStart) == null ? void 0 : _options__callbacks_onBuildStart.call(_options__callbacks, buildContext);
1990
+ (_options__callbacks = options._callbacks) == null ? undefined : (_options__callbacks_onBuildStart = _options__callbacks.onBuildStart) == null ? undefined : _options__callbacks_onBuildStart.call(_options__callbacks, buildContext);
1976
1991
  const generateTypes = hasTsConfig && options.dts !== false;
1977
1992
  const rollupJobsOptions = {
1978
1993
  isFromCli,
1979
1994
  generateTypes
1980
1995
  };
1981
1996
  const assetJobs = await createAssetRollupJobs(options, buildContext, rollupJobsOptions);
1982
- (_options__callbacks1 = options._callbacks) == null ? void 0 : (_options__callbacks_onBuildEnd = _options__callbacks1.onBuildEnd) == null ? void 0 : _options__callbacks_onBuildEnd.call(_options__callbacks1, assetJobs);
1997
+ (_options__callbacks1 = options._callbacks) == null ? undefined : (_options__callbacks_onBuildEnd = _options__callbacks1.onBuildEnd) == null ? undefined : _options__callbacks_onBuildEnd.call(_options__callbacks1, assetJobs);
1983
1998
  }
1984
1999
 
1985
2000
  exports.bundle = bundle;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "bunchee",
3
- "version": "6.3.0",
3
+ "version": "6.3.1",
4
4
  "description": "zero config bundler for js/ts/jsx libraries",
5
5
  "bin": "./dist/bin/cli.js",
6
6
  "main": "./dist/index.js",
@@ -24,7 +24,8 @@
24
24
  ],
25
25
  "prettier": {
26
26
  "semi": false,
27
- "singleQuote": true
27
+ "singleQuote": true,
28
+ "trailingComma": "all"
28
29
  },
29
30
  "engines": {
30
31
  "node": ">= 18.0.0"
@@ -36,25 +37,25 @@
36
37
  },
37
38
  "license": "MIT",
38
39
  "dependencies": {
39
- "@rollup/plugin-commonjs": "^28.0.1",
40
+ "@rollup/plugin-commonjs": "^28.0.2",
40
41
  "@rollup/plugin-json": "^6.1.0",
41
- "@rollup/plugin-node-resolve": "^15.3.0",
42
- "@rollup/plugin-replace": "^6.0.1",
42
+ "@rollup/plugin-node-resolve": "^16.0.0",
43
+ "@rollup/plugin-replace": "^6.0.2",
43
44
  "@rollup/plugin-wasm": "^6.2.2",
44
45
  "@rollup/pluginutils": "^5.1.3",
45
- "@swc/core": "^1.9.3",
46
+ "@swc/core": "^1.10.7",
46
47
  "@swc/helpers": "^0.5.11",
47
48
  "clean-css": "^5.3.3",
48
49
  "glob": "^11.0.0",
49
- "magic-string": "^0.30.14",
50
+ "magic-string": "^0.30.17",
50
51
  "ora": "^8.0.1",
51
52
  "picomatch": "^4.0.2",
52
53
  "pretty-bytes": "^5.6.0",
53
- "rollup": "^4.27.4",
54
+ "rollup": "^4.30.1",
54
55
  "rollup-plugin-dts": "^6.1.1",
55
56
  "rollup-plugin-swc3": "^0.11.1",
56
57
  "rollup-preserve-directives": "^1.1.3",
57
- "tslib": "^2.7.0",
58
+ "tslib": "^2.8.1",
58
59
  "yargs": "^17.7.2"
59
60
  },
60
61
  "peerDependencies": {
@@ -71,8 +72,8 @@
71
72
  "devDependencies": {
72
73
  "@huozhi/testing-package": "1.0.0",
73
74
  "@swc-node/register": "^1.10.9",
74
- "@swc/jest": "^0.2.31",
75
- "@swc/types": "^0.1.9",
75
+ "@swc/jest": "^0.2.37",
76
+ "@swc/types": "^0.1.17",
76
77
  "@types/clean-css": "^4.2.11",
77
78
  "@types/jest": "29.0.0",
78
79
  "@types/node": "^22.9.3",
@@ -82,11 +83,11 @@
82
83
  "bunchee": "link:./",
83
84
  "cross-env": "^7.0.3",
84
85
  "husky": "^9.0.11",
85
- "jest": "29.0.1",
86
+ "jest": "29.7.0",
86
87
  "lint-staged": "^15.2.2",
87
88
  "next": "^15.0.4",
88
89
  "picocolors": "^1.0.0",
89
- "prettier": "^3.0.0",
90
+ "prettier": "2.8.8",
90
91
  "react": "^19.0.0",
91
92
  "react-dom": "^19.0.0",
92
93
  "typescript": "^5.7.2"