bunup 0.14.19 → 0.14.21

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
@@ -60,7 +60,7 @@ Spin up a modern, ready-to-publish TypeScript or React component library (or a b
60
60
  bunx @bunup/cli@latest create
61
61
  ```
62
62
 
63
- See more in [Scaffold with Bunup](./docs/scaffold-with-bunup.md).
63
+ See more in [Scaffold with Bunup](https://bunup.dev/docs/scaffold-with-bunup).
64
64
 
65
65
  ## Features
66
66
 
package/dist/cli/index.js CHANGED
@@ -4,7 +4,7 @@ import {
4
4
  build,
5
5
  processLoadedConfigs,
6
6
  resolveBuildOptions
7
- } from "../shared/bunup-5jz4dbz1.js";
7
+ } from "../shared/bunup-3cppvv1c.js";
8
8
  import {
9
9
  BunupCLIError,
10
10
  BunupWatchError,
@@ -20,13 +20,13 @@ import {
20
20
  logTime,
21
21
  logger,
22
22
  parseErrorMessage
23
- } from "../shared/bunup-8meww5p0.js";
23
+ } from "../shared/bunup-b5xfnqft.js";
24
24
 
25
25
  // packages/bunup/src/cli/index.ts
26
26
  import { loadConfig } from "coffi";
27
27
  import pc4 from "picocolors";
28
28
  // packages/bunup/package.json
29
- var version = "0.14.19";
29
+ var version = "0.14.21";
30
30
 
31
31
  // packages/bunup/src/printer/print-build-report.ts
32
32
  import { promisify } from "util";
@@ -39,13 +39,13 @@ async function printBuildReport(buildOutput) {
39
39
  const showCompression = gzip || brotli;
40
40
  const files = await Promise.all(buildOutput.files.map(async (file) => {
41
41
  const pathRelative = file.pathRelativeToOutdir;
42
- const bunFile = Bun.file(file.fullPath);
43
- const size = bunFile.size;
42
+ const size = file.size;
44
43
  const isDts = file.dts && file.kind === "entry-point";
45
44
  const isJs = isTypeScriptFile(file.fullPath) || isJavascriptFile(file.fullPath);
46
45
  let gzipSize;
47
46
  let brotliSize;
48
47
  if (showCompression) {
48
+ const bunFile = Bun.file(file.fullPath);
49
49
  const uint8 = new Uint8Array(await bunFile.arrayBuffer());
50
50
  const [gzipResult, brotliResult] = await Promise.all([
51
51
  gzip ? Promise.resolve(Bun.gzipSync(uint8)) : Promise.resolve(null),
@@ -208,7 +208,8 @@ async function watch(userOptions, rootDir, configFilePath) {
208
208
  watcher.on("change", (changedPath) => {
209
209
  if (configFilePath && changedPath === configFilePath) {
210
210
  console.log(pc2.yellow(`
211
- Please restart watch mode to apply configuration changes.`));
211
+ Please restart watch mode to apply configuration changes.
212
+ `));
212
213
  cleanup();
213
214
  return;
214
215
  }
@@ -250,7 +251,7 @@ var program = cli().name("bunup").version(version).description("A blazing-fast b
250
251
  resolve: z.union(z.boolean().describe("Resolve types from dependencies"), z.array(z.string()).describe("Names or patterns of packages from which to resolve types")).optional(),
251
252
  splitting: z.boolean().describe("Enable declaration file splitting").optional(),
252
253
  minify: z.boolean().describe("Minify generated declaration files").optional()
253
- })).default(true)).option("preferred-tsconfig-path", z.string().describe("Path to preferred tsconfig.json for declaration generation").example("./tsconfig.build.json").optional()).option("sourcemap", z.union(z.boolean().describe("Generate a sourcemap (uses the inline type by default)"), z.string().choices(["none", "linked", "inline", "external"]).describe("Generate a sourcemap with a specific type")).optional()).option("define", z.object(z.string()).describe("Define global constants replaced at build time").example(`--define.PACKAGE_VERSION='"1.0.0"'`).optional()).option("env", z.union(z.string().choices(["inline", "disable"]).describe("inline: inject all, disable: inject none"), z.string().regex(/\*$/, "Environment prefix must end with *").describe("Inject env vars with this prefix").example("MYAPP_*").transform((val) => val), z.object(z.string()).describe("Explicit env var mapping").example('--env.NODE_ENV="production" --env.API_URL="https://api.example.com"')).optional()).option("banner", z.string().describe("Banner text added to the top of bundle files").optional()).option("footer", z.string().describe("Footer text added to the bottom of bundle files").optional()).option("drop", z.array(z.string()).describe("Remove function calls from bundle").example("--drop console,debugger").optional()).option("loader", z.object(z.string().choices([
254
+ })).default(true)).option("preferred-tsconfig", z.string().describe("Path to a custom tsconfig.json file used for path resolution during both bundling and TypeScript declaration generation.").example("./tsconfig.build.json").optional()).option("sourcemap", z.union(z.boolean().describe("Generate a sourcemap (uses the inline type by default)"), z.string().choices(["none", "linked", "inline", "external"]).describe("Generate a sourcemap with a specific type")).optional()).option("define", z.object(z.string()).describe("Define global constants replaced at build time").example(`--define.PACKAGE_VERSION='"1.0.0"'`).optional()).option("env", z.union(z.string().choices(["inline", "disable"]).describe("inline: inject all, disable: inject none"), z.string().regex(/\*$/, "Environment prefix must end with *").describe("Inject env vars with this prefix").example("MYAPP_*").transform((val) => val), z.object(z.string()).describe("Explicit env var mapping").example('--env.NODE_ENV="production" --env.API_URL="https://api.example.com"')).optional()).option("banner", z.string().describe("Banner text added to the top of bundle files").optional()).option("footer", z.string().describe("Footer text added to the bottom of bundle files").optional()).option("drop", z.array(z.string()).describe("Remove function calls from bundle").example("--drop console,debugger").optional()).option("loader", z.object(z.string().choices([
254
255
  "js",
255
256
  "jsx",
256
257
  "ts",
package/dist/index.d.ts CHANGED
@@ -1,5 +1,5 @@
1
- import { Arrayable, BuildContext, BuildMeta, BuildOptions, BuildOutput, BuildOutputFile, BunupPlugin, DefineConfigItem, DefineWorkspaceItem, WithOptional } from "./shared/bunup-zqdmwaar";
1
+ import { BuildContext, BuildMeta, BuildOptions, BuildOutput, BuildOutputFile, BunupPlugin, DefineConfigItem, DefineWorkspaceItem, WithOptional, WithRequired } from "./shared/bunup-9dy62rzf";
2
2
  declare function build(userOptions: Partial<BuildOptions>, rootDir?: string): Promise<BuildOutput>;
3
- declare function defineConfig(options: Arrayable<DefineConfigItem>): Arrayable<DefineConfigItem>;
3
+ declare function defineConfig(options: DefineConfigItem | WithRequired<DefineConfigItem, "name">[]): DefineConfigItem | WithRequired<DefineConfigItem, "name">[];
4
4
  declare function defineWorkspace(options: WithOptional<DefineWorkspaceItem, "config">[], sharedOptions?: Partial<DefineConfigItem>): DefineWorkspaceItem[];
5
5
  export { defineWorkspace, defineConfig, build, DefineWorkspaceItem, DefineConfigItem, BunupPlugin, BuildOutputFile, BuildOutput, BuildOptions, BuildMeta, BuildContext };
package/dist/index.js CHANGED
@@ -1,8 +1,8 @@
1
1
  // @bun
2
2
  import {
3
3
  build
4
- } from "./shared/bunup-5jz4dbz1.js";
5
- import"./shared/bunup-8meww5p0.js";
4
+ } from "./shared/bunup-3cppvv1c.js";
5
+ import"./shared/bunup-b5xfnqft.js";
6
6
  // packages/bunup/src/define.ts
7
7
  function defineConfig(options) {
8
8
  return options;
package/dist/plugins.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { BuildOptions, BunupPlugin, BunupPluginHooks, exports, injectStyles, unused } from "./shared/bunup-zqdmwaar";
1
+ import { BuildOptions, BunupPlugin, BunupPluginHooks, exports, injectStyles, unused } from "./shared/bunup-9dy62rzf";
2
2
  type CopyOptions = {
3
3
  /** Whether to follow symbolic links when copying files. */
4
4
  followSymlinks?: boolean;
package/dist/plugins.js CHANGED
@@ -7,7 +7,7 @@ import {
7
7
  logger,
8
8
  shims,
9
9
  unused
10
- } from "./shared/bunup-8meww5p0.js";
10
+ } from "./shared/bunup-b5xfnqft.js";
11
11
 
12
12
  // packages/bunup/src/plugins/copy.ts
13
13
  import { basename, extname, join } from "path";
@@ -8,28 +8,25 @@ import {
8
8
  ensureArray,
9
9
  ensureObject,
10
10
  exports,
11
+ formatBunBuildError,
12
+ formatInvalidEntryPointsError,
11
13
  formatListWithAnd,
12
- getDefaultDtsOutputExtention,
13
- getDefaultJsOutputExtension,
14
+ formatNoEntryPointsFoundError,
14
15
  getFilesFromGlobs,
15
- getPackageDeps,
16
16
  getShortFilePath,
17
17
  injectStyles,
18
- invalidEntryPointsError,
19
18
  isJavascriptFile,
20
19
  logger,
21
- noEntryPointsFoundError,
22
20
  parseErrorMessage,
23
- replaceExtension,
24
21
  shims,
25
22
  unused
26
- } from "./bunup-8meww5p0.js";
23
+ } from "./bunup-b5xfnqft.js";
27
24
 
28
25
  // packages/bunup/src/loaders.ts
29
26
  import path from "path";
30
27
  import { loadConfig } from "coffi";
31
28
  async function processLoadedConfigs(config, cwd, filter) {
32
- return Array.isArray(config) && "root" in config[0] ? config.filter((c) => filter ? filter.includes(c.name) : true).map((c) => ({
29
+ return Array.isArray(config) && config[0] && "root" in config[0] ? config.filter((c) => filter ? filter.includes(c.name) : true).map((c) => ({
33
30
  rootDir: path.resolve(cwd, c.root),
34
31
  options: setOrSuffixField(c.config ?? {}, "name", c.name)
35
32
  })) : [
@@ -157,6 +154,19 @@ export default classes;
157
154
  };
158
155
  }
159
156
 
157
+ // packages/bunup/src/plugins/internal/external-option.ts
158
+ import { isBuiltin } from "module";
159
+
160
+ // packages/bunup/src/utils/package.ts
161
+ function getPackageDeps(packageJson) {
162
+ if (!packageJson)
163
+ return [];
164
+ return Array.from(new Set([
165
+ ...Object.keys(packageJson.dependencies || {}),
166
+ ...Object.keys(packageJson.peerDependencies || {})
167
+ ]));
168
+ }
169
+
160
170
  // packages/bunup/src/helpers/external.ts
161
171
  function getPackageDepsPatterns(packageJson) {
162
172
  return getPackageDeps(packageJson).map((dep) => new RegExp(`^${dep}($|\\/|\\\\)`));
@@ -164,7 +174,7 @@ function getPackageDepsPatterns(packageJson) {
164
174
  function matchesPattern(path2, pattern) {
165
175
  return typeof pattern === "string" ? pattern === path2 : pattern.test(path2);
166
176
  }
167
- function isExternal(path2, options, packageJson) {
177
+ function isExternalFromPackageJson(path2, options, packageJson) {
168
178
  const packageDepsPatterns = getPackageDepsPatterns(packageJson);
169
179
  const matchesExternalPattern = packageDepsPatterns.some((pattern) => pattern.test(path2)) || options.external?.some((pattern) => matchesPattern(path2, pattern));
170
180
  const isExcludedFromExternal = options.noExternal?.some((pattern) => matchesPattern(path2, pattern));
@@ -178,7 +188,7 @@ function externalOptionPlugin(options, packageJson) {
178
188
  setup(build) {
179
189
  build.onResolve({ filter: /.*/ }, (args) => {
180
190
  const importPath = args.path;
181
- if (isExternal(importPath, options, packageJson)) {
191
+ if (isBuiltin(importPath) || isExternalFromPackageJson(importPath, options, packageJson)) {
182
192
  return {
183
193
  path: importPath,
184
194
  external: true
@@ -336,6 +346,48 @@ async function runPluginBuildDoneHooks(bunupPlugins, options, output, meta) {
336
346
  }
337
347
  }
338
348
 
349
+ // packages/bunup/src/utils/extension.ts
350
+ function getDefaultJsOutputExtension(format, packageType) {
351
+ switch (format) {
352
+ case "esm":
353
+ return isModulePackage(packageType) ? ".js" : ".mjs";
354
+ case "cjs":
355
+ return isModulePackage(packageType) ? ".cjs" : ".js";
356
+ case "iife":
357
+ return ".global.js";
358
+ }
359
+ }
360
+ function getDefaultDtsOutputExtention(format, packageType, kind) {
361
+ if (kind === "chunk")
362
+ return ".d.ts";
363
+ switch (format) {
364
+ case "esm":
365
+ return isModulePackage(packageType) ? ".d.ts" : ".d.mts";
366
+ case "cjs":
367
+ return isModulePackage(packageType) ? ".d.cts" : ".d.ts";
368
+ case "iife":
369
+ return ".global.d.ts";
370
+ }
371
+ }
372
+ function isModulePackage(packageType) {
373
+ return packageType === "module";
374
+ }
375
+ function replaceExtension(filePath, newExtension) {
376
+ if (!filePath) {
377
+ return filePath;
378
+ }
379
+ const normalizedExtension = newExtension.startsWith(".") ? newExtension : `.${newExtension}`;
380
+ const lastSlashIndex = Math.max(filePath.lastIndexOf("/"), filePath.lastIndexOf("\\"));
381
+ const directory = lastSlashIndex >= 0 ? filePath.substring(0, lastSlashIndex + 1) : "";
382
+ const filename = lastSlashIndex >= 0 ? filePath.substring(lastSlashIndex + 1) : filePath;
383
+ const lastDotIndex = filename.lastIndexOf(".");
384
+ if (lastDotIndex === -1) {
385
+ return directory + filename + normalizedExtension;
386
+ }
387
+ const nameWithoutExtension = filename.substring(0, lastDotIndex);
388
+ return directory + nameWithoutExtension + normalizedExtension;
389
+ }
390
+
339
391
  // packages/bunup/src/build.ts
340
392
  var ac = null;
341
393
  async function build(userOptions, rootDir = process.cwd()) {
@@ -372,9 +424,9 @@ async function build(userOptions, rootDir = process.cwd()) {
372
424
  const entrypoints = getFilesFromGlobs(entryArray, rootDir);
373
425
  if (!entrypoints.length) {
374
426
  if (!ensureArray(userOptions.entry).length) {
375
- throw new BunupBuildError(noEntryPointsFoundError(DEFAULT_ENTYPOINTS));
427
+ throw new BunupBuildError(formatNoEntryPointsFoundError(DEFAULT_ENTYPOINTS));
376
428
  }
377
- throw new BunupBuildError(invalidEntryPointsError(entryArray));
429
+ throw new BunupBuildError(formatInvalidEntryPointsError(entryArray));
378
430
  }
379
431
  logger.info(`entry: ${formatListWithAnd(entrypoints)}`, {
380
432
  identifier: options.name,
@@ -411,14 +463,17 @@ async function build(userOptions, rootDir = process.cwd()) {
411
463
  emitDCEAnnotations: options.emitDCEAnnotations,
412
464
  jsx: options.jsx,
413
465
  throw: false,
414
- plugins: bunPlugins
466
+ plugins: bunPlugins,
467
+ tsconfig: options.preferredTsconfig ? path2.resolve(rootDir, options.preferredTsconfig) : undefined
415
468
  });
416
469
  for (const log of result.logs) {
417
470
  if (log.level === "error") {
418
- throw new BunupBuildError(log.message);
471
+ throw new BunupBuildError(formatBunBuildError(log));
419
472
  }
420
473
  if (log.level === "warning")
421
474
  logger.warn(log.message);
475
+ if (log.level === "verbose")
476
+ logger.log(log.message);
422
477
  else if (log.level === "info")
423
478
  logger.info(log.message);
424
479
  }
@@ -437,7 +492,8 @@ async function build(userOptions, rootDir = process.cwd()) {
437
492
  dts: false,
438
493
  format: fmt,
439
494
  kind: file.kind,
440
- entrypoint: file.kind === "entry-point" ? cleanPath(entrypoints[entrypointIndex]) : undefined
495
+ entrypoint: file.kind === "entry-point" ? cleanPath(entrypoints[entrypointIndex] ?? "") : undefined,
496
+ size: file.size
441
497
  });
442
498
  if (file.kind === "entry-point") {
443
499
  entrypointIndex++;
@@ -451,7 +507,7 @@ async function build(userOptions, rootDir = process.cwd()) {
451
507
  const { entry, splitting, ...dtsOptions } = typeof options.dts === "object" ? options.dts : {};
452
508
  const dtsResult = await generateDts(ensureArray(entry ?? entrypoints), {
453
509
  cwd: rootDir,
454
- preferredTsConfigPath: options.preferredTsconfigPath,
510
+ preferredTsconfig: options.preferredTsconfig,
455
511
  splitting: getResolvedDtsSplitting(options.splitting, splitting),
456
512
  naming: {
457
513
  chunk: getDefaultChunkNaming(options.name)
@@ -475,7 +531,8 @@ async function build(userOptions, rootDir = process.cwd()) {
475
531
  dts: true,
476
532
  format: fmt,
477
533
  kind: file.kind,
478
- entrypoint: file.entrypoint ? cleanPath(file.entrypoint) : undefined
534
+ entrypoint: file.entrypoint ? cleanPath(file.entrypoint) : undefined,
535
+ size: file.dts.length
479
536
  });
480
537
  }
481
538
  }
@@ -34,6 +34,8 @@ type BuildOutputFile = {
34
34
  dts: boolean;
35
35
  /** The format of the output file */
36
36
  format: Format;
37
+ /** The size of the file in bytes */
38
+ size: number;
37
39
  };
38
40
  /**
39
41
  * Represents the output of a build operation
@@ -370,16 +372,15 @@ interface BuildOptions {
370
372
  entry?: string | string[];
371
373
  });
372
374
  /**
373
- * Path to a preferred tsconfig.json file to use for declaration generation
375
+ * Path to a custom tsconfig.json file used for path resolution during
376
+ * both bundling and TypeScript declaration generation.
374
377
  *
375
- * If not specified, the tsconfig.json in the project root will be used.
376
- * This option allows you to use a different TypeScript configuration
377
- * specifically for declaration file generation.
378
+ * If not specified, the nearest tsconfig.json will be used.
378
379
  *
379
380
  * @example
380
- * preferredTsconfigPath: './tsconfig.build.json'
381
+ * preferredTsconfig: './tsconfig.build.json'
381
382
  */
382
- preferredTsconfigPath?: string;
383
+ preferredTsconfig?: string;
383
384
  /**
384
385
  * External packages that should not be bundled
385
386
  * Useful for dependencies that should be kept as external imports
@@ -632,11 +633,14 @@ type WithOptional<
632
633
  T,
633
634
  K extends keyof T
634
635
  > = Omit<T, K> & Partial<Pick<T, K>>;
635
- type Arrayable<T> = T | T[];
636
+ type WithRequired<
637
+ T,
638
+ K extends keyof T
639
+ > = Omit<T, K> & Required<Pick<T, K>>;
636
640
  type DefineConfigItem = WithOptional<BuildOptions, "outDir" | "format" | "entry">;
637
641
  type DefineWorkspaceItem = {
638
642
  name: string;
639
643
  root: string;
640
- config?: DefineConfigItem | DefineConfigItem[];
644
+ config?: DefineConfigItem | WithRequired<DefineConfigItem, "name">[];
641
645
  };
642
- export { WithOptional, Arrayable, DefineConfigItem, DefineWorkspaceItem, BuildMeta, BuildOutputFile, BuildOutput, BuildContext, BunupPluginHooks, BunupPlugin, exports, injectStyles, unused, BuildOptions };
646
+ export { WithOptional, WithRequired, DefineConfigItem, DefineWorkspaceItem, BuildMeta, BuildOutputFile, BuildOutput, BuildContext, BunupPluginHooks, BunupPlugin, exports, injectStyles, unused, BuildOptions };
@@ -67,12 +67,14 @@ class Logger {
67
67
  identifier,
68
68
  muted = false,
69
69
  tick = false,
70
- type = "info"
70
+ type = "info",
71
+ noIcon = false
71
72
  } = options;
72
- const icon = options.icon ?? this.getIcon(type, tick);
73
+ const icon = noIcon ? "" : options.icon ?? this.getIcon(type, tick);
73
74
  const styledMessage = muted ? pc.dim(message) : type === "error" ? pc.red(message) : type === "warn" ? pc.yellow(message) : message;
74
75
  const identifierPart = this.formatIdentifier(identifier);
75
- return `${icon} ${styledMessage}${identifierPart}`;
76
+ const iconPart = icon ? `${icon} ` : "";
77
+ return `${iconPart}${styledMessage}${identifierPart}`;
76
78
  }
77
79
  output(message, options = {}, logFn = console.log) {
78
80
  if (this.silent || !this.shouldLog(options)) {
@@ -136,6 +138,20 @@ class Logger {
136
138
  }).join(`
137
139
  `);
138
140
  }
141
+ highlight(code) {
142
+ const keywords = /\b(const|let|var|function|return|if|else|for|while|class|import|export|from|async|await|new|try|catch|throw|typeof|interface|type|enum)\b/g;
143
+ const strings = /(["'`])(?:(?=(\\?))\2.)*?\1/g;
144
+ const comments = /(\/\/.*$|\/\*[\s\S]*?\*\/)/gm;
145
+ const numbers = /\b(\d+\.?\d*)\b/g;
146
+ const functions = /\b([a-zA-Z_$][a-zA-Z0-9_$]*)\s*(?=\()/g;
147
+ let result = code;
148
+ result = result.replace(comments, (match) => pc.dim(match));
149
+ result = result.replace(strings, (match) => pc.green(match));
150
+ result = result.replace(keywords, (match) => pc.magenta(match));
151
+ result = result.replace(numbers, (match) => pc.yellow(match));
152
+ result = result.replace(functions, (match) => pc.cyan(match));
153
+ return result;
154
+ }
139
155
  }
140
156
  function logTime(ms) {
141
157
  return ms >= 1000 ? pc.green(`${(ms / 1000).toFixed(2)}s`) : pc.green(`${Math.round(ms)}ms`);
@@ -148,8 +164,42 @@ function link(url, label) {
148
164
  }
149
165
  var logger = Logger.getInstance();
150
166
 
167
+ // packages/bunup/src/utils/path.ts
168
+ import { normalize } from "path";
169
+ function getShortFilePath(filePath, maxLength = 3) {
170
+ const fileParts = filePath.split("/");
171
+ const shortPath = fileParts.slice(-maxLength).join("/");
172
+ return shortPath;
173
+ }
174
+ function cleanPath(path) {
175
+ return normalize(path).replace(/\\/g, "/").replace(/^[a-zA-Z]:\//, "").replace(/^\/+/, "").replace(/\/+/g, "/");
176
+ }
177
+
151
178
  // packages/bunup/src/errors.ts
152
179
  import pc2 from "picocolors";
180
+
181
+ // packages/bunup/src/utils/format.ts
182
+ function formatFileSize(bytes) {
183
+ if (bytes === 0)
184
+ return "0 B";
185
+ const units = ["B", "KB", "MB", "GB"];
186
+ const i = Math.floor(Math.log(bytes) / Math.log(1024));
187
+ if (i === 0)
188
+ return `${bytes} ${units[i]}`;
189
+ return `${(bytes / 1024 ** i).toFixed(2)} ${units[i]}`;
190
+ }
191
+ var listFormatter = new Intl.ListFormat("en", {
192
+ style: "long",
193
+ type: "conjunction"
194
+ });
195
+ function formatListWithAnd(arr) {
196
+ return listFormatter.format(arr);
197
+ }
198
+ function stripAnsiSafe(text) {
199
+ return Bun.stripANSI ? Bun.stripANSI(text) : text;
200
+ }
201
+
202
+ // packages/bunup/src/errors.ts
153
203
  class BunupError extends Error {
154
204
  constructor(message) {
155
205
  super(message);
@@ -242,36 +292,34 @@ var handleError = (error, context) => {
242
292
  }
243
293
  const knownError = KNOWN_ERRORS.find((error2) => error2.pattern.test(errorMessage) && (error2.errorType === errorType || !error2.errorType));
244
294
  if (!knownError) {
245
- console.error(`
295
+ logger.error(`
246
296
  ${pc2.bgRed(` ${errorType} `)}
247
297
 
248
298
  ${contextPrefix}${errorMessage}`.split(`
249
- `).map((line) => ` ${line}`).join(`
250
- `));
299
+ `).map((line) => pc2.white(` ${line}`)).join(`
300
+ `), { noIcon: true });
251
301
  }
252
302
  if (knownError) {
253
- console.log(`
254
- `);
303
+ logger.space();
255
304
  knownError.logSolution(errorMessage);
256
- console.log(`
257
- `);
305
+ logger.space();
258
306
  } else {
259
307
  const issueUrl = new URL("https://github.com/bunup/bunup/issues/new");
260
- issueUrl.searchParams.set("title", `[${errorType}] Error encountered`);
308
+ issueUrl.searchParams.set("title", `[${errorType}] [give a descriptive title]`);
261
309
  issueUrl.searchParams.set("body", `## Error Details
262
310
 
263
311
  **Error Type:** ${errorType}
264
- **Error Message:** ${errorMessage}
312
+ **Error Message:** ${stripAnsiSafe(errorMessage)}
265
313
 
266
314
  ## Additional Context
267
315
 
268
316
  <!-- Please provide any additional context about what you were trying to do when the error occurred -->`);
269
- console.error(pc2.white(`
317
+ logger.log(pc2.white(`
270
318
  If you think this is a bug, please `) + link(issueUrl.toString(), "open an issue") + ` with details about this error
271
319
  `);
272
320
  }
273
321
  };
274
- var noEntryPointsFoundError = (defaultEntrypoints) => {
322
+ var formatNoEntryPointsFoundError = (defaultEntrypoints) => {
275
323
  return `${pc2.red(pc2.bold("No entry points found"))}
276
324
 
277
325
  ` + `Looked for these default entry points:
@@ -280,7 +328,7 @@ var noEntryPointsFoundError = (defaultEntrypoints) => {
280
328
 
281
329
  You can specify entry points via CLI like ${pc2.green("bunup lib/main.ts")}, ` + `use multiple entries like ${pc2.green("bunup components/button.tsx utils/format.ts")}, or add the entry option in your bunup config.`;
282
330
  };
283
- var invalidEntryPointsError = (userEntrypoints) => {
331
+ var formatInvalidEntryPointsError = (userEntrypoints) => {
284
332
  const entryPointsFormatted = logger.list(userEntrypoints, { dim: true });
285
333
  const isMultiple = userEntrypoints.length > 1;
286
334
  return `${pc2.red(pc2.bold(`Entry ${isMultiple ? "points do not exist" : "point does not exist"}`))}
@@ -289,14 +337,27 @@ ${entryPointsFormatted}
289
337
 
290
338
  Please check that ${isMultiple ? "these paths exist and point" : "this path exists and points"} to ${isMultiple ? "valid files" : "a valid file"}.`;
291
339
  };
340
+ function formatBunBuildError(error) {
341
+ const pos = error.position;
342
+ if (!pos) {
343
+ return error.message;
344
+ }
345
+ const lineNum = String(pos.line);
346
+ const padding = " ".repeat(lineNum.length);
347
+ const caretPos = pos.column;
348
+ return `${pc2.dim(`${lineNum} |`)} ${logger.highlight(pos.lineText)}
349
+ ${pc2.dim(`${padding} |`)} ${" ".repeat(caretPos)}${pc2.red("^")}
350
+
351
+ ${pc2.bold(error.message)}
352
+ ${pc2.dim("at")} ${pc2.cyan(getShortFilePath(pos.file))}${pc2.dim(":")}${pc2.yellow(lineNum)}${pc2.dim(":")}${pc2.yellow(String(pos.column))}`;
353
+ }
292
354
  var handleErrorAndExit = (error, context) => {
293
355
  handleError(error, context);
294
356
  process.exit(1);
295
357
  };
296
358
 
297
- // packages/bunup/src/utils.ts
298
- import fs from "fs/promises";
299
- import path, { normalize } from "path";
359
+ // packages/bunup/src/plugins/exports.ts
360
+ import path2 from "path";
300
361
 
301
362
  // packages/bunup/src/constants/re.ts
302
363
  var JS_RE = /\.(js|jsx|cjs|mjs)$/;
@@ -306,60 +367,9 @@ var JS_TS_RE = new RegExp(`${JS_RE.source}|${TS_RE.source}`);
306
367
  var JS_DTS_RE = new RegExp(`${JS_RE.source}|${DTS_RE.source}`);
307
368
  var CSS_RE = /\.(css)$/;
308
369
 
309
- // packages/bunup/src/utils.ts
310
- function ensureArray(value) {
311
- return Array.isArray(value) ? value : [value].filter(Boolean);
312
- }
313
- function ensureObject(value) {
314
- return typeof value === "object" && value !== null ? value : {};
315
- }
316
- function getDefaultJsOutputExtension(format, packageType) {
317
- switch (format) {
318
- case "esm":
319
- return isModulePackage(packageType) ? ".js" : ".mjs";
320
- case "cjs":
321
- return isModulePackage(packageType) ? ".cjs" : ".js";
322
- case "iife":
323
- return ".global.js";
324
- }
325
- }
326
- function getDefaultDtsOutputExtention(format, packageType, kind) {
327
- if (kind === "chunk")
328
- return ".d.ts";
329
- switch (format) {
330
- case "esm":
331
- return isModulePackage(packageType) ? ".d.ts" : ".d.mts";
332
- case "cjs":
333
- return isModulePackage(packageType) ? ".d.cts" : ".d.ts";
334
- case "iife":
335
- return ".global.d.ts";
336
- }
337
- }
338
- function isModulePackage(packageType) {
339
- return packageType === "module";
340
- }
341
- function getPackageDeps(packageJson) {
342
- if (!packageJson)
343
- return [];
344
- return Array.from(new Set([
345
- ...Object.keys(packageJson.dependencies || {}),
346
- ...Object.keys(packageJson.peerDependencies || {})
347
- ]));
348
- }
349
- function formatFileSize(bytes) {
350
- if (bytes === 0)
351
- return "0 B";
352
- const units = ["B", "KB", "MB", "GB"];
353
- const i = Math.floor(Math.log(bytes) / Math.log(1024));
354
- if (i === 0)
355
- return `${bytes} ${units[i]}`;
356
- return `${(bytes / 1024 ** i).toFixed(2)} ${units[i]}`;
357
- }
358
- function getShortFilePath(filePath, maxLength = 3) {
359
- const fileParts = filePath.split("/");
360
- const shortPath = fileParts.slice(-maxLength).join("/");
361
- return shortPath;
362
- }
370
+ // packages/bunup/src/utils/file.ts
371
+ import fs from "fs/promises";
372
+ import path from "path";
363
373
  async function cleanOutDir(rootDir, outDir) {
364
374
  const normalizedOutDir = path.normalize(outDir);
365
375
  if (["/", ".", "..", "~"].includes(normalizedOutDir) || normalizedOutDir.startsWith("/") || normalizedOutDir.startsWith("~")) {
@@ -376,16 +386,6 @@ async function cleanOutDir(rootDir, outDir) {
376
386
  throw new BunupBuildError(`Failed to manage output directory: ${error}`);
377
387
  }
378
388
  }
379
- function cleanPath(path2) {
380
- return normalize(path2).replace(/\\/g, "/").replace(/^[a-zA-Z]:\//, "").replace(/^\/+/, "").replace(/\/+/g, "/");
381
- }
382
- var listFormatter = new Intl.ListFormat("en", {
383
- style: "long",
384
- type: "conjunction"
385
- });
386
- function formatListWithAnd(arr) {
387
- return listFormatter.format(arr);
388
- }
389
389
  function getFilesFromGlobs(patterns, cwd) {
390
390
  const includePatterns = patterns.filter((p) => !p.startsWith("!"));
391
391
  const excludePatterns = patterns.filter((p) => p.startsWith("!")).map((p) => p.slice(1));
@@ -416,20 +416,8 @@ function isJavascriptFile(path2) {
416
416
  return false;
417
417
  return JS_RE.test(path2);
418
418
  }
419
- function replaceExtension(filePath, newExtension) {
420
- if (!filePath) {
421
- return filePath;
422
- }
423
- const normalizedExtension = newExtension.startsWith(".") ? newExtension : `.${newExtension}`;
424
- const lastSlashIndex = Math.max(filePath.lastIndexOf("/"), filePath.lastIndexOf("\\"));
425
- const directory = lastSlashIndex >= 0 ? filePath.substring(0, lastSlashIndex + 1) : "";
426
- const filename = lastSlashIndex >= 0 ? filePath.substring(lastSlashIndex + 1) : filePath;
427
- const lastDotIndex = filename.lastIndexOf(".");
428
- if (lastDotIndex === -1) {
429
- return directory + filename + normalizedExtension;
430
- }
431
- const nameWithoutExtension = filename.substring(0, lastDotIndex);
432
- return directory + nameWithoutExtension + normalizedExtension;
419
+ function isGlobPattern(pattern) {
420
+ return /[*?[\]{}]/.test(pattern);
433
421
  }
434
422
  async function detectFileFormatting(filePath) {
435
423
  try {
@@ -442,10 +430,10 @@ async function detectFileFormatting(filePath) {
442
430
  const match = line.match(/^(\s+)/);
443
431
  if (match) {
444
432
  const indent = match[1];
445
- if (indent.startsWith("\t")) {
433
+ if (indent?.startsWith("\t")) {
446
434
  return { indentation: "\t", hasTrailingNewline };
447
435
  }
448
- return { indentation: indent, hasTrailingNewline };
436
+ return { indentation: indent ?? " ", hasTrailingNewline };
449
437
  }
450
438
  }
451
439
  return { indentation: " ", hasTrailingNewline };
@@ -453,12 +441,8 @@ async function detectFileFormatting(filePath) {
453
441
  return { indentation: " ", hasTrailingNewline: true };
454
442
  }
455
443
  }
456
- function isGlobPattern(pattern) {
457
- return /[*?[\]{}]/.test(pattern);
458
- }
459
444
 
460
445
  // packages/bunup/src/plugins/exports.ts
461
- import path2 from "path";
462
446
  function exports(options = {}) {
463
447
  return {
464
448
  name: "exports",
@@ -678,7 +662,7 @@ function isExcluded(entrypoint, exclude, ctx) {
678
662
  }
679
663
  function getExportKey(pathRelativeToOutdir) {
680
664
  const pathSegments = cleanPath(removeExtension(pathRelativeToOutdir)).split("/");
681
- if (pathSegments.length === 1 && pathSegments[0].startsWith("index")) {
665
+ if (pathSegments.length === 1 && pathSegments[0]?.startsWith("index")) {
682
666
  return ".";
683
667
  }
684
668
  return `./${pathSegments.filter((segment) => !segment.startsWith("index")).join("/")}`;
@@ -859,7 +843,7 @@ function unused(options = {}) {
859
843
  const transpiler = new Bun.Transpiler({
860
844
  loader: "js"
861
845
  });
862
- const jsFiles = output.files.filter((file) => file.fullPath.endsWith(".js"));
846
+ const jsFiles = output.files.filter((file) => isJavascriptFile(file.fullPath));
863
847
  const packageDependencies = typeof meta.packageJson.data?.dependencies === "object" ? meta.packageJson.data.dependencies : {};
864
848
  const externals = [
865
849
  ...buildOptions.external ?? [],
@@ -892,7 +876,8 @@ function unused(options = {}) {
892
876
  const message = [
893
877
  `
894
878
  Your project${buildOptions.name ? ` ${buildOptions.name}` : ""} has ${count} unused ${depText}: ${coloredDeps}.`,
895
- `You can remove ${count === 1 ? "it" : "them"} with ${removeCommand}`
879
+ `You can remove ${count === 1 ? "it" : "them"} with ${removeCommand}`,
880
+ `or move to devDependencies if you are using ${count === 1 ? "it" : "them"} only for types.`
896
881
  ].join(" ");
897
882
  if (level === "error") {
898
883
  logger.log(pc3.red(message));
@@ -906,4 +891,12 @@ function unused(options = {}) {
906
891
  };
907
892
  }
908
893
 
909
- export { __toESM, __require, logTime, logger, BunupBuildError, BunupDTSBuildError, BunupCLIError, BunupWatchError, BunupVersionError, parseErrorMessage, handleError, noEntryPointsFoundError, invalidEntryPointsError, handleErrorAndExit, ensureArray, ensureObject, getDefaultJsOutputExtension, getDefaultDtsOutputExtention, getPackageDeps, formatFileSize, getShortFilePath, cleanOutDir, cleanPath, formatListWithAnd, getFilesFromGlobs, isTypeScriptFile, isJavascriptFile, replaceExtension, isGlobPattern, exports, injectStyles, shims, unused };
894
+ // packages/bunup/src/utils/common.ts
895
+ function ensureArray(value) {
896
+ return Array.isArray(value) ? value : [value].filter(Boolean);
897
+ }
898
+ function ensureObject(value) {
899
+ return typeof value === "object" && value !== null ? value : {};
900
+ }
901
+
902
+ export { __toESM, __require, logTime, logger, formatFileSize, formatListWithAnd, getShortFilePath, cleanPath, BunupBuildError, BunupDTSBuildError, BunupCLIError, BunupWatchError, BunupVersionError, parseErrorMessage, handleError, formatNoEntryPointsFoundError, formatInvalidEntryPointsError, formatBunBuildError, handleErrorAndExit, cleanOutDir, getFilesFromGlobs, isTypeScriptFile, isJavascriptFile, isGlobPattern, exports, injectStyles, shims, unused, ensureArray, ensureObject };
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "bunup",
3
3
  "description": "⚡ A blazing-fast build tool for your libraries built with Bun.",
4
- "version": "0.14.19",
4
+ "version": "0.14.21",
5
5
  "type": "module",
6
6
  "files": [
7
7
  "dist"
@@ -46,8 +46,11 @@
46
46
  "bin": {
47
47
  "bunup": "dist/cli/index.js"
48
48
  },
49
+ "scripts": {
50
+ "type-check": "tsc --noEmit"
51
+ },
49
52
  "dependencies": {
50
- "@bunup/dts": "0.14.19",
53
+ "@bunup/dts": "0.14.20",
51
54
  "chokidar": "^4.0.3",
52
55
  "coffi": "^0.1.37",
53
56
  "lightningcss": "^1.30.2",
@@ -55,7 +58,7 @@
55
58
  "tinyexec": "^1.0.1",
56
59
  "tree-kill": "^1.2.2",
57
60
  "zlye": "^0.4.4",
58
- "@bunup/shared": "0.14.19"
61
+ "@bunup/shared": "0.14.20"
59
62
  },
60
63
  "peerDependencies": {
61
64
  "typescript": "latest"