quickbundle 0.15.0 → 1.0.0

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
@@ -12,11 +12,11 @@ Quickbundle allows you to bundle a library in a **quick**, **fast** and **easy**
12
12
 
13
13
  - Fast build and watch mode thanks to [esbuild](https://esbuild.github.io/)
14
14
  - Zero configuration: define the build artifacts in your `package.json` and you're all set!
15
- - JavaScript, TypeScript, JSX, CSS, JSON, Image and Text support following [esbuild support](https://esbuild.github.io/content-types/)
16
15
  - Support of multiple module formats including `cjs` & `esm`
16
+ - JavaScript, TypeScript, JSX, CSS, JSON, Image and Text support following [esbuild support](https://esbuild.github.io/content-types/)
17
+ - TypeScript declaration file (`.d.ts`) generation with bundling support
17
18
  - Bundling can be done for several platform targets including `browser` or `node`
18
- - Optimized build such as `peerDependencies` not bundled in the final output
19
- - Serve and live reload support for `html` entrypoint
19
+ - Optimized build with automatic dependency inclusion (`peerDependencies` and `dependencies` are not bundled in the final output whatever the defined platform target)
20
20
 
21
21
  <br>
22
22
 
@@ -25,8 +25,10 @@ Quickbundle allows you to bundle a library in a **quick**, **fast** and **easy**
25
25
  1️⃣ Install by running:
26
26
 
27
27
  ```bash
28
- # NPM
28
+ # Npm
29
29
  npm install quickbundle
30
+ # Pnpm
31
+ pnpm add quickbundle
30
32
  # Yarn
31
33
  yarn add quickbundle
32
34
  ```
@@ -37,16 +39,13 @@ yarn add quickbundle
37
39
  {
38
40
  "name": "lib", // Package name
39
41
  "source": "src/index.ts", // Source code entrypoint
40
- "main": "./dist/lib.cjs", // CommonJS output file
41
- "module": "./dist/lib.cjs.js", // ESM output file
42
- "types": "./dist/lib.d.ts", // Typing output file
42
+ "main": "./dist/index.cjs", // CommonJS output file
43
+ "module": "./dist/index.mjs", // ESM output file
44
+ "types": "./dist/index.d.ts", // Typing output file (if defined, can increase build time)
43
45
  "platform": "node", // Platform target (optional, by default "browser")
44
46
  "scripts": {
45
47
  "build": "quickbundle build", // Production mode (optimizes bundle)
46
48
  "watch": "quickbundle watch", // Development mode (watches each file change)
47
- "serve": "quickbundle watch --serve public/index.html", // Serve an html entrypoint with live reload capabilities (for more details, check examples folder)
48
- "build:fast": "quickbundle build --no-check", // Production mode with fast transpilation time. This mode disables TypeScript type checking (ie. not using `tsc`) and, consequently, the `types` asset is no more managed by the tool
49
- "watch:fast": "quickbundle watch --no-check" // Development mode with fast transpilation time
50
49
  }
51
50
  }
52
51
  ```
@@ -54,10 +53,12 @@ yarn add quickbundle
54
53
  3️⃣ Try it by running:
55
54
 
56
55
  ```bash
57
- # NPM
58
- npm run prod
56
+ # Npm
57
+ npm run build
58
+ # Pnpm
59
+ pnpm build
59
60
  # Yarn
60
- yarn prod
61
+ yarn build
61
62
  ```
62
63
 
63
64
  <br>
@@ -72,7 +73,7 @@ Contribution welcomed! 🤗
72
73
 
73
74
  ## 💙 Acknowledgements
74
75
 
75
- - The backend powered by [ESBuild](https://github.com/evanw/esbuild) to make blazing fast builds. A special shoutout to its author [Evan Wallace](https://github.com/evanw) and [all contributors](https://github.com/evanw/esbuild/graphs/contributors).
76
+ - The backend is powered by [ESBuild](https://github.com/evanw/esbuild) to make blazing-fast builds. A special shoutout to its author [Evan Wallace](https://github.com/evanw) and [all contributors](https://github.com/evanw/esbuild/graphs/contributors).
76
77
  - The zero-configuration approach was inspired by [microbundle](https://github.com/developit/microbundle). A special shoutout to its author [Jason Miller](https://github.com/developit) and [all contributors](https://github.com/developit/microbundle/graphs/contributors).
77
78
 
78
79
  <br>
@@ -1,8 +1,2 @@
1
- declare type BundleParameters = {
2
- isProduction: boolean;
3
- isFast: boolean;
4
- onWatch?: (error: Error | null) => void;
5
- serveEntryPoint?: string;
6
- };
7
- export declare const bundle: ({ isProduction, isFast, onWatch, serveEntryPoint, }: BundleParameters) => Promise<(string | null)[]>;
8
- export {};
1
+ export declare const build: () => Promise<any[]>;
2
+ export declare const watch: (onWatch: (type: "loading" | "result", error?: string) => void) => Promise<void>;
@@ -1,97 +1,88 @@
1
1
  "use strict";
2
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
- return new (P || (P = Promise))(function (resolve, reject) {
5
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
- step((generator = generator.apply(thisArg, _arguments || [])).next());
9
- });
10
- };
11
2
  Object.defineProperty(exports, "__esModule", { value: true });
12
- exports.bundle = void 0;
3
+ exports.watch = exports.build = void 0;
13
4
  const esbuild_1 = require("esbuild");
14
- const http_1 = require("http");
15
- const constants_1 = require("../constants");
5
+ const threads_1 = require("threads");
16
6
  const helpers_1 = require("../helpers");
17
- const package_1 = require("./package");
18
- const plugins_1 = require("./plugins");
19
- const typescript_1 = require("./typescript");
20
- const bundle = ({ isProduction, isFast, onWatch, serveEntryPoint, }) => __awaiter(void 0, void 0, void 0, function* () {
21
- const { destination, externalDependencies, hasModule, platform, source, types, } = (0, package_1.getPackageMetadata)();
22
- const isWatching = typeof onWatch === "function";
23
- const isLiveReloadable = serveEntryPoint && isWatching;
24
- const isTypingRequested = typeof types === "string" && !isFast;
25
- const tsConfig = yield (0, typescript_1.getTypeScriptConfiguration)();
26
- const getType = () => __awaiter(void 0, void 0, void 0, function* () {
27
- const outfile = types;
28
- if (!outfile)
29
- return null;
30
- yield (0, typescript_1.generateTypeScriptDeclaration)(outfile);
31
- return outfile;
7
+ const configs_1 = require("./configs");
8
+ const build = async () => {
9
+ const { pkg, typescript } = await (0, configs_1.getConfigs)({
10
+ isProduction: true,
32
11
  });
33
- const getJavaScript = (format) => __awaiter(void 0, void 0, void 0, function* () {
34
- const outfile = destination[format];
35
- if (!outfile)
36
- return null;
37
- yield (0, esbuild_1.build)(Object.assign(Object.assign({}, (isLiveReloadable && {
38
- banner: {
39
- js: `;new EventSource("http://0.0.0.0:${servePort}").onmessage = function() { location.reload(); }; console.log("Live reload ✅ (port: ${servePort})");`,
40
- },
41
- })), { absWorkingDir: constants_1.CWD, bundle: true, define: {
42
- "process.env.NODE_ENV": isProduction
43
- ? '"production"'
44
- : '"development"',
45
- }, entryPoints: [source], external: externalDependencies, format, loader: {
46
- ".jpg": "file",
47
- ".jpeg": "file",
48
- ".png": "file",
49
- ".gif": "file",
50
- ".svg": "file",
51
- ".webp": "file",
52
- }, logLevel: "silent", metafile: true, minify: isProduction, outfile, plugins: [(0, plugins_1.jsxPlugin)(tsConfig)], platform, sourcemap: true, target: (tsConfig === null || tsConfig === void 0 ? void 0 : tsConfig.target) || "esnext", treeShaking: true, watch: isWatching && {
53
- onRebuild(bundleError) {
54
- return __awaiter(this, void 0, void 0, function* () {
55
- let error = bundleError;
56
- if (isLiveReloadable) {
57
- clients.forEach((client) => {
58
- client.write("data: update\n\n");
12
+ const promises = [
13
+ buildJavaScript("cjs"),
14
+ ...(pkg.hasModule ? [buildJavaScript("esm")] : []),
15
+ ...(typescript.isEnabled
16
+ ? [
17
+ buildDts({
18
+ source: pkg.source,
19
+ destination: pkg.types,
20
+ }),
21
+ ]
22
+ : []),
23
+ ];
24
+ return Promise.all(promises);
25
+ };
26
+ exports.build = build;
27
+ const watch = async (onWatch) => {
28
+ const { esbuild, pkg, typescript } = await (0, configs_1.getConfigs)({
29
+ isProduction: false,
30
+ });
31
+ const ctx = await (0, esbuild_1.context)({
32
+ ...esbuild({ format: "cjs", outfile: pkg.destination["cjs"] }),
33
+ plugins: [
34
+ {
35
+ name: "onBuildEnd",
36
+ setup(build) {
37
+ build.onStart(() => {
38
+ onWatch("loading");
39
+ });
40
+ build.onEnd(async (result) => {
41
+ const error = (await (0, esbuild_1.formatMessages)(result.errors, {
42
+ kind: "error",
43
+ color: true,
44
+ terminalWidth: 100,
45
+ })).join("\n");
46
+ // If there's already a build error, no need to run
47
+ // a heavy typing generation process until the error is fixed
48
+ if (!error && typescript.isEnabled) {
49
+ buildDts({
50
+ source: pkg.source,
51
+ destination: pkg.types,
52
+ })
53
+ .then(() => {
54
+ onWatch("result");
55
+ })
56
+ .catch((err) => {
57
+ onWatch("result", err);
59
58
  });
60
- clients = [];
61
59
  }
62
- if (!error && isTypingRequested) {
63
- try {
64
- yield getType();
65
- }
66
- catch (typingError) {
67
- error = typingError;
68
- }
60
+ else {
61
+ onWatch("result", error);
69
62
  }
70
- onWatch(error);
71
63
  });
72
64
  },
73
- } }));
74
- return outfile;
65
+ },
66
+ ],
75
67
  });
76
- if (isLiveReloadable) {
77
- servePort = yield (0, helpers_1.getAvailablePortFrom)(servePort);
78
- (0, http_1.createServer)((_, res) => {
79
- clients.push(res.writeHead(200, {
80
- "Content-Type": "text/event-stream",
81
- "Cache-Control": "no-cache",
82
- "Access-Control-Allow-Origin": "*",
83
- }));
84
- }).listen(servePort);
85
- (0, helpers_1.openBrowser)(serveEntryPoint);
68
+ await ctx.watch();
69
+ };
70
+ exports.watch = watch;
71
+ const buildJavaScript = async (format) => {
72
+ const worker = await (0, threads_1.spawn)(new threads_1.Worker("./workers/esbuild"));
73
+ const outfile = await worker(format);
74
+ await threads_1.Thread.terminate(worker);
75
+ return outfile;
76
+ };
77
+ const buildDts = async ({ source, destination, }) => {
78
+ try {
79
+ const worker = await (0, threads_1.spawn)(new threads_1.Worker("./workers/dts"));
80
+ const dtsContent = await worker(source);
81
+ await (0, helpers_1.writeFile)(destination, dtsContent);
82
+ await threads_1.Thread.terminate(worker);
83
+ return destination;
86
84
  }
87
- const promises = [
88
- ...(isWatching
89
- ? [getJavaScript(hasModule ? "esm" : "cjs")]
90
- : [getJavaScript("cjs"), getJavaScript("esm")]),
91
- ...(isTypingRequested ? [getType()] : []),
92
- ];
93
- return Promise.all(promises);
94
- });
95
- exports.bundle = bundle;
96
- let clients = [];
97
- let servePort = 9000;
85
+ catch (error) {
86
+ throw new Error(`Type generation failed:\n${error}`);
87
+ }
88
+ };
@@ -0,0 +1,8 @@
1
+ import type { BuildOptions } from "esbuild";
2
+ import type { TSConfig } from "./typescript";
3
+ export interface EsbuildConfig extends Required<Pick<BuildOptions, "format" | "outfile" | "external" | "platform">> {
4
+ isProduction: boolean;
5
+ source: string;
6
+ tsConfig: TSConfig | null;
7
+ }
8
+ export declare const getEsbuildConfig: ({ external, format, isProduction, outfile, platform, source, tsConfig, }: EsbuildConfig) => BuildOptions;
@@ -0,0 +1,64 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getEsbuildConfig = void 0;
4
+ const helpers_1 = require("../../helpers");
5
+ const constants_1 = require("../../constants");
6
+ const getEsbuildConfig = ({ external, format, isProduction, outfile, platform, source, tsConfig, }) => ({
7
+ absWorkingDir: constants_1.CWD,
8
+ bundle: true,
9
+ color: true,
10
+ define: {
11
+ "process.env.NODE_ENV": isProduction ? '"production"' : '"development"',
12
+ },
13
+ entryPoints: [source],
14
+ external,
15
+ format,
16
+ loader: {
17
+ ".jpg": "file",
18
+ ".jpeg": "file",
19
+ ".png": "file",
20
+ ".gif": "file",
21
+ ".svg": "file",
22
+ ".webp": "file",
23
+ },
24
+ logLevel: "silent",
25
+ metafile: true,
26
+ minify: isProduction,
27
+ outfile,
28
+ plugins: [jsxPlugin(tsConfig)],
29
+ platform,
30
+ sourcemap: true,
31
+ target: tsConfig?.target || "esnext",
32
+ treeShaking: true,
33
+ });
34
+ exports.getEsbuildConfig = getEsbuildConfig;
35
+ /**
36
+ * Plugin to automatically inject React import for jsx management
37
+ * ESBuild doesn't support `jsx` tsconfig field: this plugin aims to add a tiny wrapper to support it
38
+ * We could use the `inject` ESBuild feature but it will break the tree shaking behavior since the React import will
39
+ * be imported on each file (even in .ts file) leading React being included in the bundle even if not needed
40
+ * @see: https://github.com/evanw/esbuild/issues/334
41
+ * @param tsConfig
42
+ * @returns Plugin
43
+ */
44
+ const jsxPlugin = (tsConfig) => ({
45
+ name: "jsx-runtime",
46
+ setup(build) {
47
+ build.onLoad({ filter: /\.(j|t)sx$/ }, async ({ path }) => {
48
+ // Enable plugin only if
49
+ // - `${module}/jsx-runtime` package is available (for js project, it's the only condition to check!)
50
+ // - if ts project: jsx compilerOption === "react-jsx" or "react-jsxdev"
51
+ if (!tsConfig || !tsConfig.hasJsxRuntime)
52
+ return;
53
+ const module = tsConfig.jsxImportSource || "react";
54
+ if (!(0, helpers_1.resolveModulePath)(`${module}/jsx-runtime`)) {
55
+ throw new Error("Unable to find the JSX runtime.\nPotential solutions:\n1. If you rely on a non React runtime, set a valid `jsxImportSource` in your tsconfig\n2. Make sure that you've installed your project dependencies");
56
+ }
57
+ const content = await (0, helpers_1.readFile)(path, "utf8");
58
+ return {
59
+ contents: `import * as React from "${module}";${content}`,
60
+ loader: "tsx",
61
+ };
62
+ });
63
+ },
64
+ });
@@ -0,0 +1,22 @@
1
+ import { BuildOptions } from "esbuild";
2
+ import { EsbuildConfig } from "./esbuild";
3
+ type ConfigOptions = {
4
+ isProduction: boolean;
5
+ };
6
+ export declare const getConfigs: ({ isProduction }: ConfigOptions) => Promise<{
7
+ esbuild: ({ format, outfile, }: Pick<EsbuildConfig, "format" | "outfile">) => BuildOptions;
8
+ pkg: {
9
+ destination: {
10
+ readonly esm?: string;
11
+ readonly cjs: string;
12
+ };
13
+ hasModule: boolean;
14
+ source: string;
15
+ types: string | undefined;
16
+ };
17
+ typescript: {
18
+ configuration: import("./typescript").TSConfig | null;
19
+ isEnabled: boolean;
20
+ };
21
+ }>;
22
+ export {};
@@ -0,0 +1,34 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getConfigs = void 0;
4
+ const esbuild_1 = require("./esbuild");
5
+ const package_1 = require("./package");
6
+ const typescript_1 = require("./typescript");
7
+ const getConfigs = async ({ isProduction }) => {
8
+ const { destination, externalDependencies, hasModule, platform, source, types, } = (0, package_1.getPkgConfig)();
9
+ const tsConfig = await (0, typescript_1.getTSConfig)();
10
+ const hasTyping = typeof types === "string" && Boolean(tsConfig);
11
+ const esbuild = ({ format, outfile, }) => (0, esbuild_1.getEsbuildConfig)({
12
+ external: externalDependencies,
13
+ format,
14
+ isProduction,
15
+ outfile,
16
+ platform,
17
+ source,
18
+ tsConfig,
19
+ });
20
+ return {
21
+ esbuild,
22
+ pkg: {
23
+ destination,
24
+ hasModule,
25
+ source,
26
+ types,
27
+ },
28
+ typescript: {
29
+ configuration: tsConfig,
30
+ isEnabled: hasTyping,
31
+ },
32
+ };
33
+ };
34
+ exports.getConfigs = getConfigs;
@@ -1,6 +1,6 @@
1
- export declare const getPackageMetadata: () => {
1
+ export declare const getPkgConfig: () => {
2
2
  readonly destination: {
3
- readonly esm?: string | undefined;
3
+ readonly esm?: string;
4
4
  readonly cjs: string;
5
5
  };
6
6
  readonly externalDependencies: string[];
@@ -1,24 +1,30 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getPackageMetadata = void 0;
3
+ exports.getPkgConfig = void 0;
4
+ /* eslint-disable @typescript-eslint/no-var-requires */
4
5
  const path_1 = require("path");
5
- const constants_1 = require("../constants");
6
- const helpers_1 = require("../helpers");
7
- const getPackageMetadata = () => {
6
+ const constants_1 = require("../../constants");
7
+ const helpers_1 = require("../../helpers");
8
+ const getPkgConfig = () => {
8
9
  const { devDependencies = {}, peerDependencies = {}, dependencies = {}, main, module, platform = "browser", source, types, } = require((0, path_1.resolve)(constants_1.CWD, "package.json"));
9
10
  (0, helpers_1.assert)(main, "A `main` field is required in `package.json`. Did you forget to add it?");
10
11
  (0, helpers_1.assert)(source, "A `source` field is required in `package.json`. Did you forget to add it?");
11
12
  (0, helpers_1.assert)(["browser", "node"].includes(platform), "The `platform` package field can only accept `browser` or `node` value.");
12
- const peerDependencyNames = Object.keys(peerDependencies);
13
+ const isomorphicExternalDependencies = [
14
+ ...Object.keys(peerDependencies),
15
+ ...Object.keys(dependencies),
16
+ ];
13
17
  const externalDependencies = platform === "browser"
14
- ? peerDependencyNames
18
+ ? isomorphicExternalDependencies
15
19
  : [
16
- ...peerDependencyNames,
17
- ...Object.keys(dependencies),
20
+ ...isomorphicExternalDependencies,
18
21
  ...Object.keys(devDependencies),
19
22
  ];
20
23
  return {
21
- destination: Object.assign({ cjs: main }, (module && { esm: module })),
24
+ destination: {
25
+ cjs: main,
26
+ ...(module && { esm: module }),
27
+ },
22
28
  externalDependencies,
23
29
  hasModule: Boolean(module),
24
30
  platform,
@@ -26,4 +32,4 @@ const getPackageMetadata = () => {
26
32
  types,
27
33
  };
28
34
  };
29
- exports.getPackageMetadata = getPackageMetadata;
35
+ exports.getPkgConfig = getPkgConfig;
@@ -0,0 +1,6 @@
1
+ export type TSConfig = {
2
+ target: string;
3
+ jsxImportSource: string | undefined;
4
+ hasJsxRuntime: boolean;
5
+ };
6
+ export declare const getTSConfig: () => Promise<TSConfig | null>;
@@ -0,0 +1,33 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.getTSConfig = void 0;
7
+ const path_1 = require("path");
8
+ const typescript_1 = __importDefault(require("typescript"));
9
+ const constants_1 = require("../../constants");
10
+ const TSCONFIG_PATH = (0, path_1.resolve)(constants_1.CWD, "tsconfig.json");
11
+ const getTSConfig = async () => {
12
+ try {
13
+ const { jsx, jsxImportSource, target } = typescript_1.default.parseJsonConfigFileContent(
14
+ // eslint-disable-next-line @typescript-eslint/no-var-requires
15
+ require(TSCONFIG_PATH), typescript_1.default.sys, constants_1.CWD).options;
16
+ // Convert ts target value to esbuild ones (latest value is not supported)
17
+ const esbuildTarget = !target ||
18
+ [typescript_1.default.ScriptTarget.ESNext, typescript_1.default.ScriptTarget.Latest].includes(target)
19
+ ? "esnext"
20
+ : typescript_1.default.ScriptTarget[target]?.toLowerCase();
21
+ const hasJsxRuntime = jsx !== undefined &&
22
+ [typescript_1.default.JsxEmit["ReactJSX"], typescript_1.default.JsxEmit["ReactJSXDev"]].includes(jsx);
23
+ return {
24
+ target: esbuildTarget,
25
+ jsxImportSource,
26
+ hasJsxRuntime,
27
+ };
28
+ }
29
+ catch (error) {
30
+ return null;
31
+ }
32
+ };
33
+ exports.getTSConfig = getTSConfig;
@@ -1 +1 @@
1
- export { bundle } from "./bundler";
1
+ export { build, watch } from "./bundler";
@@ -1,5 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.bundle = void 0;
3
+ exports.watch = exports.build = void 0;
4
4
  var bundler_1 = require("./bundler");
5
- Object.defineProperty(exports, "bundle", { enumerable: true, get: function () { return bundler_1.bundle; } });
5
+ Object.defineProperty(exports, "build", { enumerable: true, get: function () { return bundler_1.build; } });
6
+ Object.defineProperty(exports, "watch", { enumerable: true, get: function () { return bundler_1.watch; } });
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,25 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const dts_bundle_generator_1 = require("dts-bundle-generator");
4
+ const worker_1 = require("threads/worker");
5
+ (0, worker_1.expose)((source) => {
6
+ const errors = [];
7
+ // To prevent any UI glitch, catch any error by monkey patching
8
+ // the default error logger and forward them to the parent worker
9
+ console.error = (error) => {
10
+ errors.push(error);
11
+ };
12
+ try {
13
+ return (0, dts_bundle_generator_1.generateDtsBundle)([
14
+ {
15
+ filePath: source,
16
+ output: {
17
+ noBanner: true,
18
+ },
19
+ },
20
+ ])[0];
21
+ }
22
+ catch {
23
+ throw errors;
24
+ }
25
+ });
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,15 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const esbuild_1 = require("esbuild");
4
+ const worker_1 = require("threads/worker");
5
+ const configs_1 = require("../configs");
6
+ (0, worker_1.expose)(async (format) => {
7
+ const { esbuild, pkg } = await (0, configs_1.getConfigs)({
8
+ isProduction: true,
9
+ });
10
+ const outfile = pkg.destination[format];
11
+ if (!outfile)
12
+ return null;
13
+ await (0, esbuild_1.build)(esbuild({ format, outfile }));
14
+ return outfile;
15
+ });
package/bin/helpers.d.ts CHANGED
@@ -1,7 +1,6 @@
1
1
  /// <reference types="node" />
2
- import { readFile as fsReadFile } from "fs";
3
- export declare const readFile: typeof fsReadFile.__promisify__;
4
- export declare const resolveModulePath: (path: string) => boolean;
2
+ import fs from "node:fs/promises";
5
3
  export declare function assert(condition: unknown, message: string): asserts condition;
6
- export declare const getAvailablePortFrom: (port: number) => Promise<number>;
7
- export declare const openBrowser: (filename: string) => void;
4
+ export declare const readFile: typeof fs.readFile;
5
+ export declare const resolveModulePath: (path: string) => boolean;
6
+ export declare const writeFile: (filePath: string, content: string) => Promise<void>;
package/bin/helpers.js CHANGED
@@ -1,21 +1,22 @@
1
1
  "use strict";
2
- var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
- function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
- return new (P || (P = Promise))(function (resolve, reject) {
5
- function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
- function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
- function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
- step((generator = generator.apply(thisArg, _arguments || [])).next());
9
- });
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
10
4
  };
11
5
  Object.defineProperty(exports, "__esModule", { value: true });
12
- exports.openBrowser = exports.getAvailablePortFrom = exports.assert = exports.resolveModulePath = exports.readFile = void 0;
13
- const util_1 = require("util");
14
- const fs_1 = require("fs");
15
- const net_1 = require("net");
16
- const child_process_1 = require("child_process");
6
+ exports.writeFile = exports.resolveModulePath = exports.readFile = exports.assert = void 0;
7
+ const node_path_1 = require("node:path");
8
+ const promises_1 = __importDefault(require("node:fs/promises"));
9
+ const node_fs_1 = require("node:fs");
17
10
  const constants_1 = require("./constants");
18
- exports.readFile = (0, util_1.promisify)(fs_1.readFile);
11
+ // TS assertion not working properly with arrow function
12
+ // @see: https://github.com/microsoft/TypeScript/issues/34523
13
+ function assert(condition, message) {
14
+ if (!condition) {
15
+ throw new Error(message);
16
+ }
17
+ }
18
+ exports.assert = assert;
19
+ exports.readFile = promises_1.default.readFile;
19
20
  const resolveModulePath = (path) => {
20
21
  try {
21
22
  return Boolean(require.resolve(path, { paths: [constants_1.CWD] }));
@@ -25,35 +26,11 @@ const resolveModulePath = (path) => {
25
26
  }
26
27
  };
27
28
  exports.resolveModulePath = resolveModulePath;
28
- function assert(condition, message) {
29
- if (!condition) {
30
- throw new Error(message);
31
- }
32
- }
33
- exports.assert = assert;
34
- const getAvailablePortFrom = (port) => __awaiter(void 0, void 0, void 0, function* () {
35
- return new Promise((resolve) => {
36
- const server = (0, net_1.createServer)();
37
- server.listen(port);
38
- server.on("listening", () => server.close(() => resolve(port)));
39
- server.on("error", () => {
40
- server.listen(++port);
41
- });
42
- });
43
- });
44
- exports.getAvailablePortFrom = getAvailablePortFrom;
45
- const openBrowser = (filename) => {
46
- const bins = {
47
- darwin: "open",
48
- linux: "xdg-open",
49
- };
50
- const { platform } = process;
51
- if (platform !== "darwin" && platform !== "linux") {
52
- return;
53
- }
54
- if (!(0, fs_1.existsSync)(filename)) {
55
- throw new Error(`Unable to find ${filename}.\nPotential solutions:\n1. Create the missing file\n2. Edit the serve entrypoint to match an existing html file`);
29
+ const writeFile = async (filePath, content) => {
30
+ const dir = (0, node_path_1.dirname)(filePath);
31
+ if (!(0, node_fs_1.existsSync)(dir)) {
32
+ await promises_1.default.mkdir(dir, { recursive: true });
56
33
  }
57
- (0, child_process_1.spawn)(bins[platform], [filename]);
34
+ await promises_1.default.writeFile(filePath, content, "utf8");
58
35
  };
59
- exports.openBrowser = openBrowser;
36
+ exports.writeFile = writeFile;