@utoo/pack 1.4.0-alpha.0 → 1.4.0-alpha.10

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/cjs/binding.d.ts CHANGED
@@ -81,6 +81,8 @@ export interface NapiProjectOptions {
81
81
  dev: boolean
82
82
  /** The build id. */
83
83
  buildId: string
84
+ /** Whether to enable default tracing logs. */
85
+ tracing: boolean
84
86
  packPath: string
85
87
  }
86
88
  /** [NapiProjectOptions] with all fields optional. */
@@ -117,6 +119,8 @@ export interface NapiTurboEngineOptions {
117
119
  memoryLimit?: number
118
120
  /** Track dependencies between tasks. If false, any change during build will error. */
119
121
  dependencyTracking?: boolean
122
+ /** Hint that this turbo-tasks instance is for a short-lived one-shot session. */
123
+ isShortSession?: boolean
120
124
  }
121
125
  export declare function projectNew(options: NapiProjectOptions, turboEngineOptions: NapiTurboEngineOptions, napiCallbacks: NapiTurbopackCallbacksJsObject): Promise<{ __napiType: "Project" }>
122
126
  export declare function projectUpdate(project: { __napiType: "Project" }, options: NapiPartialProjectOptions): Promise<void>
@@ -29,35 +29,41 @@ function build(options, projectPath, rootPath) {
29
29
  return buildInternal(bundleOptions, projectPath, rootPath);
30
30
  }
31
31
  async function buildInternal(bundleOptions, projectPath, rootPath) {
32
- var _a, _b, _c, _d, _e, _f, _g, _h;
32
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j;
33
33
  (0, common_1.blockStdout)();
34
34
  if (process.env.XCODE_PROFILE) {
35
35
  await (0, xcodeProfile_1.xcodeProfilingReady)();
36
36
  }
37
37
  const resolvedProjectPath = projectPath || process.cwd();
38
38
  const resolvedRootPath = rootPath || projectPath || process.cwd();
39
+ const persistentCaching = (_a = bundleOptions.config.persistentCaching) !== null && _a !== void 0 ? _a : false;
39
40
  (0, htmlEntry_1.processHtmlEntry)(bundleOptions.config, resolvedProjectPath);
40
41
  (0, validateEntry_1.validateEntryPaths)(bundleOptions.config, resolvedProjectPath);
41
42
  const createProject = (0, project_1.projectFactory)();
42
43
  const project = await createProject({
43
- processEnv: (_a = bundleOptions.processEnv) !== null && _a !== void 0 ? _a : {},
44
+ processEnv: (_b = bundleOptions.processEnv) !== null && _b !== void 0 ? _b : {},
44
45
  watch: {
45
46
  enable: false,
46
47
  },
47
- dev: (_b = bundleOptions.dev) !== null && _b !== void 0 ? _b : false,
48
+ dev: (_c = bundleOptions.dev) !== null && _c !== void 0 ? _c : false,
48
49
  buildId: bundleOptions.buildId || (0, nanoid_1.nanoid)(),
50
+ tracing: (_d = bundleOptions.tracing) !== null && _d !== void 0 ? _d : true,
49
51
  config: {
50
52
  ...bundleOptions.config,
51
53
  stats: Boolean(process.env.ANALYZE) ||
52
54
  bundleOptions.config.stats ||
53
55
  bundleOptions.config.entry.some((e) => !!e.html),
54
- pluginRuntimeStrategy: (_d = (_c = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _c === void 0 ? void 0 : _c.pluginRuntimeStrategy) !== null && _d !== void 0 ? _d : ((0, runtimePluginStratety_1.useWorkerThreads)() ? "workerThreads" : "childProcesses"),
56
+ pluginRuntimeStrategy: (_f = (_e = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _e === void 0 ? void 0 : _e.pluginRuntimeStrategy) !== null && _f !== void 0 ? _f : ((0, runtimePluginStratety_1.useWorkerThreads)() ? "workerThreads" : "childProcesses"),
55
57
  },
56
58
  projectPath: (0, normalize_path_1.normalizePath)(resolvedProjectPath),
57
59
  rootPath: resolvedRootPath,
58
60
  packPath: (0, common_1.getPackPath)(),
59
61
  }, {
60
- persistentCaching: (_e = bundleOptions.config.persistentCaching) !== null && _e !== void 0 ? _e : false,
62
+ persistentCaching,
63
+ // Build mode is a short-lived, one-shot compilation, so avoid paying
64
+ // dependency graph bookkeeping cost unless the persistent cache needs it.
65
+ dependencyTracking: persistentCaching,
66
+ isShortSession: true,
61
67
  });
62
68
  const entrypoints = await project.writeAllEntrypointsToDisk();
63
69
  (0, pack_shared_1.handleIssues)(entrypoints.issues);
@@ -73,20 +79,20 @@ async function buildInternal(bundleOptions, projectPath, rootPath) {
73
79
  ];
74
80
  if (htmlConfigs.length > 0) {
75
81
  const assets = { js: [], css: [] };
76
- const outputDir = ((_f = bundleOptions.config.output) === null || _f === void 0 ? void 0 : _f.path) || path_1.default.join(process.cwd(), "dist");
82
+ const outputDir = ((_g = bundleOptions.config.output) === null || _g === void 0 ? void 0 : _g.path) || path_1.default.join(process.cwd(), "dist");
77
83
  if (assets.js.length === 0 && assets.css.length === 0) {
78
84
  const discovered = (0, getInitialAssets_1.getInitialAssetsFromStats)(outputDir);
79
85
  assets.js.push(...discovered.js);
80
86
  assets.css.push(...discovered.css);
81
87
  }
82
- const publicPath = (_g = bundleOptions.config.output) === null || _g === void 0 ? void 0 : _g.publicPath;
88
+ const publicPath = (_h = bundleOptions.config.output) === null || _h === void 0 ? void 0 : _h.publicPath;
83
89
  for (const config of htmlConfigs) {
84
90
  const plugin = new HtmlPlugin_1.HtmlPlugin(config);
85
91
  await plugin.generate(outputDir, assets, publicPath);
86
92
  }
87
93
  }
88
94
  if (process.env.ANALYZE) {
89
- await analyzeBundle(((_h = bundleOptions.config.output) === null || _h === void 0 ? void 0 : _h.path) || "dist");
95
+ await analyzeBundle(((_j = bundleOptions.config.output) === null || _j === void 0 ? void 0 : _j.path) || "dist");
90
96
  }
91
97
  await project.shutdown();
92
98
  // TODO: Maybe run tasks in worker is a better way, see
package/cjs/core/hmr.js CHANGED
@@ -24,7 +24,7 @@ var pack_shared_2 = require("@utoo/pack-shared");
24
24
  Object.defineProperty(exports, "HMR_ACTIONS_SENT_TO_BROWSER", { enumerable: true, get: function () { return pack_shared_2.HMR_ACTIONS_SENT_TO_BROWSER; } });
25
25
  exports.FAST_REFRESH_RUNTIME_RELOAD = "Fast Refresh had to perform a full reload due to a runtime error.";
26
26
  async function createHotReloader(bundleOptions, projectPath, rootPath) {
27
- var _a, _b, _c, _d, _e, _f;
27
+ var _a, _b, _c, _d, _e, _f, _g;
28
28
  const resolvedProjectPath = projectPath || process.cwd();
29
29
  const resolvedRootPath = rootPath || projectPath || process.cwd();
30
30
  (0, htmlEntry_1.processHtmlEntry)(bundleOptions.config, resolvedProjectPath);
@@ -37,6 +37,7 @@ async function createHotReloader(bundleOptions, projectPath, rootPath) {
37
37
  },
38
38
  dev: true,
39
39
  buildId: bundleOptions.buildId || (0, nanoid_1.nanoid)(),
40
+ tracing: (_b = bundleOptions.tracing) !== null && _b !== void 0 ? _b : true,
40
41
  config: {
41
42
  ...bundleOptions.config,
42
43
  mode: "development",
@@ -48,14 +49,14 @@ async function createHotReloader(bundleOptions, projectPath, rootPath) {
48
49
  minify: false,
49
50
  moduleIds: "named",
50
51
  },
51
- persistentCaching: (_c = (_b = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _b === void 0 ? void 0 : _b.persistentCaching) !== null && _c !== void 0 ? _c : true,
52
- pluginRuntimeStrategy: (_e = (_d = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _d === void 0 ? void 0 : _d.pluginRuntimeStrategy) !== null && _e !== void 0 ? _e : ((0, runtimePluginStratety_1.useWorkerThreads)() ? "workerThreads" : "childProcesses"),
52
+ persistentCaching: (_d = (_c = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _c === void 0 ? void 0 : _c.persistentCaching) !== null && _d !== void 0 ? _d : true,
53
+ pluginRuntimeStrategy: (_f = (_e = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _e === void 0 ? void 0 : _e.pluginRuntimeStrategy) !== null && _f !== void 0 ? _f : ((0, runtimePluginStratety_1.useWorkerThreads)() ? "workerThreads" : "childProcesses"),
53
54
  },
54
55
  projectPath: (0, normalize_path_1.normalizePath)(resolvedProjectPath),
55
56
  rootPath: resolvedRootPath,
56
57
  packPath: (0, common_1.getPackPath)(),
57
58
  }, {
58
- persistentCaching: (_f = bundleOptions.config.persistentCaching) !== null && _f !== void 0 ? _f : false,
59
+ persistentCaching: (_g = bundleOptions.config.persistentCaching) !== null && _g !== void 0 ? _g : false,
59
60
  });
60
61
  const entrypointsSubscription = project.entrypointsSubscribe();
61
62
  let currentEntriesHandlingResolve;
@@ -64,6 +65,22 @@ async function createHotReloader(bundleOptions, projectPath, rootPath) {
64
65
  let hmrHash = 0;
65
66
  const clients = new Set();
66
67
  const clientStates = new WeakMap();
68
+ const backgroundWatchSubscriptions = new Set();
69
+ const htmlConfigs = [
70
+ ...(Array.isArray(bundleOptions.config.html)
71
+ ? bundleOptions.config.html
72
+ : bundleOptions.config.html
73
+ ? [bundleOptions.config.html]
74
+ : []),
75
+ ...bundleOptions.config.entry
76
+ .filter((e) => !!e.html)
77
+ .map((e) => e.html),
78
+ ];
79
+ let currentWatchedEntrypoints = [];
80
+ let backgroundWatchersStarted = false;
81
+ let backgroundWatchGeneration = 0;
82
+ const backgroundWriteTasks = new Map();
83
+ let closed = false;
67
84
  function sendToClient(client, payload) {
68
85
  client.send(JSON.stringify(payload));
69
86
  }
@@ -97,6 +114,103 @@ async function createHotReloader(bundleOptions, projectPath, rootPath) {
97
114
  hmrEventHappened = true;
98
115
  sendEnqueuedMessagesDebounce();
99
116
  }
117
+ async function regenerateHtml() {
118
+ var _a, _b;
119
+ if (htmlConfigs.length === 0) {
120
+ return;
121
+ }
122
+ const outputDir = ((_a = bundleOptions.config.output) === null || _a === void 0 ? void 0 : _a.path) || path_1.default.join(process.cwd(), "dist");
123
+ const publicPath = (_b = bundleOptions.config.output) === null || _b === void 0 ? void 0 : _b.publicPath;
124
+ const assets = (0, getInitialAssets_1.getInitialAssetsFromStats)(outputDir);
125
+ for (const config of htmlConfigs) {
126
+ const plugin = new HtmlPlugin_1.HtmlPlugin(config);
127
+ await plugin.generate(outputDir, assets, publicPath);
128
+ }
129
+ }
130
+ async function writeEntrypointToDisk(entrypoint) {
131
+ const result = await entrypoint.writeToDisk();
132
+ (0, common_1.processIssues)(result, true, true);
133
+ await regenerateHtml();
134
+ }
135
+ async function writeEntrypointsToDisk(entrypoints) {
136
+ await Promise.all(entrypoints.map((entrypoint) => writeEntrypointToDisk(entrypoint)));
137
+ }
138
+ async function disposeBackgroundWatchSubscriptions() {
139
+ const subscriptions = [...backgroundWatchSubscriptions];
140
+ backgroundWatchSubscriptions.clear();
141
+ backgroundWriteTasks.clear();
142
+ await Promise.all(subscriptions.map((subscription) => { var _a; return (_a = subscription.return) === null || _a === void 0 ? void 0 : _a.call(subscription); }));
143
+ }
144
+ function scheduleEntrypointWrite(entrypoint, generation) {
145
+ var _a;
146
+ if (!backgroundWatchersStarted ||
147
+ closed ||
148
+ generation !== backgroundWatchGeneration) {
149
+ return;
150
+ }
151
+ const previousTask = (_a = backgroundWriteTasks.get(entrypoint)) !== null && _a !== void 0 ? _a : Promise.resolve();
152
+ const task = previousTask
153
+ .catch(() => { })
154
+ .then(async () => {
155
+ await currentEntriesHandling;
156
+ if (closed || generation !== backgroundWatchGeneration) {
157
+ return;
158
+ }
159
+ await writeEntrypointToDisk(entrypoint);
160
+ hmrEventHappened = true;
161
+ })
162
+ .finally(() => {
163
+ if (backgroundWriteTasks.get(entrypoint) === task) {
164
+ backgroundWriteTasks.delete(entrypoint);
165
+ }
166
+ });
167
+ backgroundWriteTasks.set(entrypoint, task);
168
+ }
169
+ async function refreshBackgroundWatchers() {
170
+ const generation = ++backgroundWatchGeneration;
171
+ await disposeBackgroundWatchSubscriptions();
172
+ if (!backgroundWatchersStarted || closed) {
173
+ return;
174
+ }
175
+ await Promise.all(currentWatchedEntrypoints.map(async (entrypoint) => {
176
+ var _a, _b;
177
+ const [clientChanges, serverChanges] = await Promise.all([
178
+ entrypoint.clientChanged(),
179
+ entrypoint.serverChanged(true),
180
+ ]);
181
+ if (closed || generation !== backgroundWatchGeneration) {
182
+ await Promise.all([
183
+ (_a = clientChanges.return) === null || _a === void 0 ? void 0 : _a.call(clientChanges),
184
+ (_b = serverChanges.return) === null || _b === void 0 ? void 0 : _b.call(serverChanges),
185
+ ]);
186
+ return;
187
+ }
188
+ backgroundWatchSubscriptions.add(clientChanges);
189
+ backgroundWatchSubscriptions.add(serverChanges);
190
+ const watchChanges = async (subscription) => {
191
+ try {
192
+ for await (const data of subscription) {
193
+ if (closed || generation !== backgroundWatchGeneration) {
194
+ return;
195
+ }
196
+ (0, common_1.processIssues)(data, true, true);
197
+ scheduleEntrypointWrite(entrypoint, generation);
198
+ }
199
+ }
200
+ catch (error) {
201
+ if (!closed && generation === backgroundWatchGeneration) {
202
+ console.error(error);
203
+ process.exit(1);
204
+ }
205
+ }
206
+ finally {
207
+ backgroundWatchSubscriptions.delete(subscription);
208
+ }
209
+ };
210
+ void watchChanges(clientChanges);
211
+ void watchChanges(serverChanges);
212
+ }));
213
+ }
100
214
  async function subscribeToHmrEvents(client, id) {
101
215
  const state = clientStates.get(client);
102
216
  if (!state || state.subscriptions.has(id)) {
@@ -138,39 +252,19 @@ async function createHotReloader(bundleOptions, projectPath, rootPath) {
138
252
  subscription === null || subscription === void 0 ? void 0 : subscription.return();
139
253
  }
140
254
  async function handleEntrypointsSubscription() {
141
- var _a, _b;
142
255
  for await (const entrypoints of entrypointsSubscription) {
143
256
  if (!currentEntriesHandlingResolve) {
144
257
  currentEntriesHandling = new Promise(
145
258
  // eslint-disable-next-line no-loop-func
146
259
  (resolve) => (currentEntriesHandlingResolve = resolve));
147
260
  }
148
- const assets = { js: [], css: [] };
149
- await Promise.all([...entrypoints.apps, ...entrypoints.libraries].map((l) => l.writeToDisk().then((res) => {
150
- (0, common_1.processIssues)(res, true, true);
151
- })));
152
- const htmlConfigs = [
153
- ...(Array.isArray(bundleOptions.config.html)
154
- ? bundleOptions.config.html
155
- : bundleOptions.config.html
156
- ? [bundleOptions.config.html]
157
- : []),
158
- ...bundleOptions.config.entry
159
- .filter((e) => !!e.html)
160
- .map((e) => e.html),
261
+ currentWatchedEntrypoints = [
262
+ ...entrypoints.apps,
263
+ ...entrypoints.libraries,
161
264
  ];
162
- if (htmlConfigs.length > 0) {
163
- const outputDir = ((_a = bundleOptions.config.output) === null || _a === void 0 ? void 0 : _a.path) || path_1.default.join(process.cwd(), "dist");
164
- const publicPath = (_b = bundleOptions.config.output) === null || _b === void 0 ? void 0 : _b.publicPath;
165
- if (assets.js.length === 0 && assets.css.length === 0) {
166
- const discovered = (0, getInitialAssets_1.getInitialAssetsFromStats)(outputDir);
167
- assets.js.push(...discovered.js);
168
- assets.css.push(...discovered.css);
169
- }
170
- for (const config of htmlConfigs) {
171
- const plugin = new HtmlPlugin_1.HtmlPlugin(config);
172
- await plugin.generate(outputDir, assets, publicPath);
173
- }
265
+ await writeEntrypointsToDisk(currentWatchedEntrypoints);
266
+ if (backgroundWatchersStarted) {
267
+ await refreshBackgroundWatchers();
174
268
  }
175
269
  currentEntriesHandlingResolve();
176
270
  currentEntriesHandlingResolve = undefined;
@@ -338,11 +432,19 @@ async function createHotReloader(bundleOptions, projectPath, rootPath) {
338
432
  clearHmrServerError() {
339
433
  // Not implemented yet.
340
434
  },
341
- async start() { },
435
+ async start() {
436
+ if (backgroundWatchersStarted) {
437
+ return;
438
+ }
439
+ backgroundWatchersStarted = true;
440
+ await refreshBackgroundWatchers();
441
+ },
342
442
  async buildFallbackError() {
343
443
  // Not implemented yet.
344
444
  },
345
445
  close() {
446
+ closed = true;
447
+ void disposeBackgroundWatchSubscriptions();
346
448
  for (const wsClient of clients) {
347
449
  wsClient.close();
348
450
  }
@@ -1303,6 +1303,13 @@
1303
1303
  "null"
1304
1304
  ]
1305
1305
  },
1306
+ "absoluteSourceFilename": {
1307
+ "description": "Keep React dev source filenames as absolute disk paths for editor integrations",
1308
+ "type": [
1309
+ "boolean",
1310
+ "null"
1311
+ ]
1312
+ },
1306
1313
  "runtime": {
1307
1314
  "description": "JSX runtime to use (automatic or classic)",
1308
1315
  "type": [
@@ -1535,4 +1542,4 @@
1535
1542
  ]
1536
1543
  }
1537
1544
  }
1538
- }
1545
+ }
package/esm/binding.d.ts CHANGED
@@ -81,6 +81,8 @@ export interface NapiProjectOptions {
81
81
  dev: boolean
82
82
  /** The build id. */
83
83
  buildId: string
84
+ /** Whether to enable default tracing logs. */
85
+ tracing: boolean
84
86
  packPath: string
85
87
  }
86
88
  /** [NapiProjectOptions] with all fields optional. */
@@ -117,6 +119,8 @@ export interface NapiTurboEngineOptions {
117
119
  memoryLimit?: number
118
120
  /** Track dependencies between tasks. If false, any change during build will error. */
119
121
  dependencyTracking?: boolean
122
+ /** Hint that this turbo-tasks instance is for a short-lived one-shot session. */
123
+ isShortSession?: boolean
120
124
  }
121
125
  export declare function projectNew(options: NapiProjectOptions, turboEngineOptions: NapiTurboEngineOptions, napiCallbacks: NapiTurbopackCallbacksJsObject): Promise<{ __napiType: "Project" }>
122
126
  export declare function projectUpdate(project: { __napiType: "Project" }, options: NapiPartialProjectOptions): Promise<void>
@@ -23,35 +23,41 @@ export function build(options, projectPath, rootPath) {
23
23
  return buildInternal(bundleOptions, projectPath, rootPath);
24
24
  }
25
25
  async function buildInternal(bundleOptions, projectPath, rootPath) {
26
- var _a, _b, _c, _d, _e, _f, _g, _h;
26
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j;
27
27
  blockStdout();
28
28
  if (process.env.XCODE_PROFILE) {
29
29
  await xcodeProfilingReady();
30
30
  }
31
31
  const resolvedProjectPath = projectPath || process.cwd();
32
32
  const resolvedRootPath = rootPath || projectPath || process.cwd();
33
+ const persistentCaching = (_a = bundleOptions.config.persistentCaching) !== null && _a !== void 0 ? _a : false;
33
34
  processHtmlEntry(bundleOptions.config, resolvedProjectPath);
34
35
  validateEntryPaths(bundleOptions.config, resolvedProjectPath);
35
36
  const createProject = projectFactory();
36
37
  const project = await createProject({
37
- processEnv: (_a = bundleOptions.processEnv) !== null && _a !== void 0 ? _a : {},
38
+ processEnv: (_b = bundleOptions.processEnv) !== null && _b !== void 0 ? _b : {},
38
39
  watch: {
39
40
  enable: false,
40
41
  },
41
- dev: (_b = bundleOptions.dev) !== null && _b !== void 0 ? _b : false,
42
+ dev: (_c = bundleOptions.dev) !== null && _c !== void 0 ? _c : false,
42
43
  buildId: bundleOptions.buildId || nanoid(),
44
+ tracing: (_d = bundleOptions.tracing) !== null && _d !== void 0 ? _d : true,
43
45
  config: {
44
46
  ...bundleOptions.config,
45
47
  stats: Boolean(process.env.ANALYZE) ||
46
48
  bundleOptions.config.stats ||
47
49
  bundleOptions.config.entry.some((e) => !!e.html),
48
- pluginRuntimeStrategy: (_d = (_c = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _c === void 0 ? void 0 : _c.pluginRuntimeStrategy) !== null && _d !== void 0 ? _d : (useWorkerThreads() ? "workerThreads" : "childProcesses"),
50
+ pluginRuntimeStrategy: (_f = (_e = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _e === void 0 ? void 0 : _e.pluginRuntimeStrategy) !== null && _f !== void 0 ? _f : (useWorkerThreads() ? "workerThreads" : "childProcesses"),
49
51
  },
50
52
  projectPath: normalizePath(resolvedProjectPath),
51
53
  rootPath: resolvedRootPath,
52
54
  packPath: getPackPath(),
53
55
  }, {
54
- persistentCaching: (_e = bundleOptions.config.persistentCaching) !== null && _e !== void 0 ? _e : false,
56
+ persistentCaching,
57
+ // Build mode is a short-lived, one-shot compilation, so avoid paying
58
+ // dependency graph bookkeeping cost unless the persistent cache needs it.
59
+ dependencyTracking: persistentCaching,
60
+ isShortSession: true,
55
61
  });
56
62
  const entrypoints = await project.writeAllEntrypointsToDisk();
57
63
  handleIssues(entrypoints.issues);
@@ -67,20 +73,20 @@ async function buildInternal(bundleOptions, projectPath, rootPath) {
67
73
  ];
68
74
  if (htmlConfigs.length > 0) {
69
75
  const assets = { js: [], css: [] };
70
- const outputDir = ((_f = bundleOptions.config.output) === null || _f === void 0 ? void 0 : _f.path) || path.join(process.cwd(), "dist");
76
+ const outputDir = ((_g = bundleOptions.config.output) === null || _g === void 0 ? void 0 : _g.path) || path.join(process.cwd(), "dist");
71
77
  if (assets.js.length === 0 && assets.css.length === 0) {
72
78
  const discovered = getInitialAssetsFromStats(outputDir);
73
79
  assets.js.push(...discovered.js);
74
80
  assets.css.push(...discovered.css);
75
81
  }
76
- const publicPath = (_g = bundleOptions.config.output) === null || _g === void 0 ? void 0 : _g.publicPath;
82
+ const publicPath = (_h = bundleOptions.config.output) === null || _h === void 0 ? void 0 : _h.publicPath;
77
83
  for (const config of htmlConfigs) {
78
84
  const plugin = new HtmlPlugin(config);
79
85
  await plugin.generate(outputDir, assets, publicPath);
80
86
  }
81
87
  }
82
88
  if (process.env.ANALYZE) {
83
- await analyzeBundle(((_h = bundleOptions.config.output) === null || _h === void 0 ? void 0 : _h.path) || "dist");
89
+ await analyzeBundle(((_j = bundleOptions.config.output) === null || _j === void 0 ? void 0 : _j.path) || "dist");
84
90
  }
85
91
  await project.shutdown();
86
92
  // TODO: Maybe run tasks in worker is a better way, see
package/esm/core/hmr.js CHANGED
@@ -16,7 +16,7 @@ const sessionId = Math.floor(Number.MAX_SAFE_INTEGER * Math.random());
16
16
  export { HMR_ACTIONS_SENT_TO_BROWSER, } from "@utoo/pack-shared";
17
17
  export const FAST_REFRESH_RUNTIME_RELOAD = "Fast Refresh had to perform a full reload due to a runtime error.";
18
18
  export async function createHotReloader(bundleOptions, projectPath, rootPath) {
19
- var _a, _b, _c, _d, _e, _f;
19
+ var _a, _b, _c, _d, _e, _f, _g;
20
20
  const resolvedProjectPath = projectPath || process.cwd();
21
21
  const resolvedRootPath = rootPath || projectPath || process.cwd();
22
22
  processHtmlEntry(bundleOptions.config, resolvedProjectPath);
@@ -29,6 +29,7 @@ export async function createHotReloader(bundleOptions, projectPath, rootPath) {
29
29
  },
30
30
  dev: true,
31
31
  buildId: bundleOptions.buildId || nanoid(),
32
+ tracing: (_b = bundleOptions.tracing) !== null && _b !== void 0 ? _b : true,
32
33
  config: {
33
34
  ...bundleOptions.config,
34
35
  mode: "development",
@@ -40,14 +41,14 @@ export async function createHotReloader(bundleOptions, projectPath, rootPath) {
40
41
  minify: false,
41
42
  moduleIds: "named",
42
43
  },
43
- persistentCaching: (_c = (_b = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _b === void 0 ? void 0 : _b.persistentCaching) !== null && _c !== void 0 ? _c : true,
44
- pluginRuntimeStrategy: (_e = (_d = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _d === void 0 ? void 0 : _d.pluginRuntimeStrategy) !== null && _e !== void 0 ? _e : (useWorkerThreads() ? "workerThreads" : "childProcesses"),
44
+ persistentCaching: (_d = (_c = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _c === void 0 ? void 0 : _c.persistentCaching) !== null && _d !== void 0 ? _d : true,
45
+ pluginRuntimeStrategy: (_f = (_e = bundleOptions === null || bundleOptions === void 0 ? void 0 : bundleOptions.config) === null || _e === void 0 ? void 0 : _e.pluginRuntimeStrategy) !== null && _f !== void 0 ? _f : (useWorkerThreads() ? "workerThreads" : "childProcesses"),
45
46
  },
46
47
  projectPath: normalizePath(resolvedProjectPath),
47
48
  rootPath: resolvedRootPath,
48
49
  packPath: getPackPath(),
49
50
  }, {
50
- persistentCaching: (_f = bundleOptions.config.persistentCaching) !== null && _f !== void 0 ? _f : false,
51
+ persistentCaching: (_g = bundleOptions.config.persistentCaching) !== null && _g !== void 0 ? _g : false,
51
52
  });
52
53
  const entrypointsSubscription = project.entrypointsSubscribe();
53
54
  let currentEntriesHandlingResolve;
@@ -56,6 +57,22 @@ export async function createHotReloader(bundleOptions, projectPath, rootPath) {
56
57
  let hmrHash = 0;
57
58
  const clients = new Set();
58
59
  const clientStates = new WeakMap();
60
+ const backgroundWatchSubscriptions = new Set();
61
+ const htmlConfigs = [
62
+ ...(Array.isArray(bundleOptions.config.html)
63
+ ? bundleOptions.config.html
64
+ : bundleOptions.config.html
65
+ ? [bundleOptions.config.html]
66
+ : []),
67
+ ...bundleOptions.config.entry
68
+ .filter((e) => !!e.html)
69
+ .map((e) => e.html),
70
+ ];
71
+ let currentWatchedEntrypoints = [];
72
+ let backgroundWatchersStarted = false;
73
+ let backgroundWatchGeneration = 0;
74
+ const backgroundWriteTasks = new Map();
75
+ let closed = false;
59
76
  function sendToClient(client, payload) {
60
77
  client.send(JSON.stringify(payload));
61
78
  }
@@ -89,6 +106,103 @@ export async function createHotReloader(bundleOptions, projectPath, rootPath) {
89
106
  hmrEventHappened = true;
90
107
  sendEnqueuedMessagesDebounce();
91
108
  }
109
+ async function regenerateHtml() {
110
+ var _a, _b;
111
+ if (htmlConfigs.length === 0) {
112
+ return;
113
+ }
114
+ const outputDir = ((_a = bundleOptions.config.output) === null || _a === void 0 ? void 0 : _a.path) || path.join(process.cwd(), "dist");
115
+ const publicPath = (_b = bundleOptions.config.output) === null || _b === void 0 ? void 0 : _b.publicPath;
116
+ const assets = getInitialAssetsFromStats(outputDir);
117
+ for (const config of htmlConfigs) {
118
+ const plugin = new HtmlPlugin(config);
119
+ await plugin.generate(outputDir, assets, publicPath);
120
+ }
121
+ }
122
+ async function writeEntrypointToDisk(entrypoint) {
123
+ const result = await entrypoint.writeToDisk();
124
+ processIssues(result, true, true);
125
+ await regenerateHtml();
126
+ }
127
+ async function writeEntrypointsToDisk(entrypoints) {
128
+ await Promise.all(entrypoints.map((entrypoint) => writeEntrypointToDisk(entrypoint)));
129
+ }
130
+ async function disposeBackgroundWatchSubscriptions() {
131
+ const subscriptions = [...backgroundWatchSubscriptions];
132
+ backgroundWatchSubscriptions.clear();
133
+ backgroundWriteTasks.clear();
134
+ await Promise.all(subscriptions.map((subscription) => { var _a; return (_a = subscription.return) === null || _a === void 0 ? void 0 : _a.call(subscription); }));
135
+ }
136
+ function scheduleEntrypointWrite(entrypoint, generation) {
137
+ var _a;
138
+ if (!backgroundWatchersStarted ||
139
+ closed ||
140
+ generation !== backgroundWatchGeneration) {
141
+ return;
142
+ }
143
+ const previousTask = (_a = backgroundWriteTasks.get(entrypoint)) !== null && _a !== void 0 ? _a : Promise.resolve();
144
+ const task = previousTask
145
+ .catch(() => { })
146
+ .then(async () => {
147
+ await currentEntriesHandling;
148
+ if (closed || generation !== backgroundWatchGeneration) {
149
+ return;
150
+ }
151
+ await writeEntrypointToDisk(entrypoint);
152
+ hmrEventHappened = true;
153
+ })
154
+ .finally(() => {
155
+ if (backgroundWriteTasks.get(entrypoint) === task) {
156
+ backgroundWriteTasks.delete(entrypoint);
157
+ }
158
+ });
159
+ backgroundWriteTasks.set(entrypoint, task);
160
+ }
161
+ async function refreshBackgroundWatchers() {
162
+ const generation = ++backgroundWatchGeneration;
163
+ await disposeBackgroundWatchSubscriptions();
164
+ if (!backgroundWatchersStarted || closed) {
165
+ return;
166
+ }
167
+ await Promise.all(currentWatchedEntrypoints.map(async (entrypoint) => {
168
+ var _a, _b;
169
+ const [clientChanges, serverChanges] = await Promise.all([
170
+ entrypoint.clientChanged(),
171
+ entrypoint.serverChanged(true),
172
+ ]);
173
+ if (closed || generation !== backgroundWatchGeneration) {
174
+ await Promise.all([
175
+ (_a = clientChanges.return) === null || _a === void 0 ? void 0 : _a.call(clientChanges),
176
+ (_b = serverChanges.return) === null || _b === void 0 ? void 0 : _b.call(serverChanges),
177
+ ]);
178
+ return;
179
+ }
180
+ backgroundWatchSubscriptions.add(clientChanges);
181
+ backgroundWatchSubscriptions.add(serverChanges);
182
+ const watchChanges = async (subscription) => {
183
+ try {
184
+ for await (const data of subscription) {
185
+ if (closed || generation !== backgroundWatchGeneration) {
186
+ return;
187
+ }
188
+ processIssues(data, true, true);
189
+ scheduleEntrypointWrite(entrypoint, generation);
190
+ }
191
+ }
192
+ catch (error) {
193
+ if (!closed && generation === backgroundWatchGeneration) {
194
+ console.error(error);
195
+ process.exit(1);
196
+ }
197
+ }
198
+ finally {
199
+ backgroundWatchSubscriptions.delete(subscription);
200
+ }
201
+ };
202
+ void watchChanges(clientChanges);
203
+ void watchChanges(serverChanges);
204
+ }));
205
+ }
92
206
  async function subscribeToHmrEvents(client, id) {
93
207
  const state = clientStates.get(client);
94
208
  if (!state || state.subscriptions.has(id)) {
@@ -130,39 +244,19 @@ export async function createHotReloader(bundleOptions, projectPath, rootPath) {
130
244
  subscription === null || subscription === void 0 ? void 0 : subscription.return();
131
245
  }
132
246
  async function handleEntrypointsSubscription() {
133
- var _a, _b;
134
247
  for await (const entrypoints of entrypointsSubscription) {
135
248
  if (!currentEntriesHandlingResolve) {
136
249
  currentEntriesHandling = new Promise(
137
250
  // eslint-disable-next-line no-loop-func
138
251
  (resolve) => (currentEntriesHandlingResolve = resolve));
139
252
  }
140
- const assets = { js: [], css: [] };
141
- await Promise.all([...entrypoints.apps, ...entrypoints.libraries].map((l) => l.writeToDisk().then((res) => {
142
- processIssues(res, true, true);
143
- })));
144
- const htmlConfigs = [
145
- ...(Array.isArray(bundleOptions.config.html)
146
- ? bundleOptions.config.html
147
- : bundleOptions.config.html
148
- ? [bundleOptions.config.html]
149
- : []),
150
- ...bundleOptions.config.entry
151
- .filter((e) => !!e.html)
152
- .map((e) => e.html),
253
+ currentWatchedEntrypoints = [
254
+ ...entrypoints.apps,
255
+ ...entrypoints.libraries,
153
256
  ];
154
- if (htmlConfigs.length > 0) {
155
- const outputDir = ((_a = bundleOptions.config.output) === null || _a === void 0 ? void 0 : _a.path) || path.join(process.cwd(), "dist");
156
- const publicPath = (_b = bundleOptions.config.output) === null || _b === void 0 ? void 0 : _b.publicPath;
157
- if (assets.js.length === 0 && assets.css.length === 0) {
158
- const discovered = getInitialAssetsFromStats(outputDir);
159
- assets.js.push(...discovered.js);
160
- assets.css.push(...discovered.css);
161
- }
162
- for (const config of htmlConfigs) {
163
- const plugin = new HtmlPlugin(config);
164
- await plugin.generate(outputDir, assets, publicPath);
165
- }
257
+ await writeEntrypointsToDisk(currentWatchedEntrypoints);
258
+ if (backgroundWatchersStarted) {
259
+ await refreshBackgroundWatchers();
166
260
  }
167
261
  currentEntriesHandlingResolve();
168
262
  currentEntriesHandlingResolve = undefined;
@@ -330,11 +424,19 @@ export async function createHotReloader(bundleOptions, projectPath, rootPath) {
330
424
  clearHmrServerError() {
331
425
  // Not implemented yet.
332
426
  },
333
- async start() { },
427
+ async start() {
428
+ if (backgroundWatchersStarted) {
429
+ return;
430
+ }
431
+ backgroundWatchersStarted = true;
432
+ await refreshBackgroundWatchers();
433
+ },
334
434
  async buildFallbackError() {
335
435
  // Not implemented yet.
336
436
  },
337
437
  close() {
438
+ closed = true;
439
+ void disposeBackgroundWatchSubscriptions();
338
440
  for (const wsClient of clients) {
339
441
  wsClient.close();
340
442
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@utoo/pack",
3
- "version": "1.4.0-alpha.0",
3
+ "version": "1.4.0-alpha.10",
4
4
  "main": "cjs/index.js",
5
5
  "module": "esm/index.js",
6
6
  "types": "esm/index.d.ts",
@@ -41,7 +41,7 @@
41
41
  "@hono/node-server": "^1.19.11",
42
42
  "@hono/node-ws": "^1.3.0",
43
43
  "@swc/helpers": "0.5.15",
44
- "@utoo/pack-shared": "1.4.0-alpha.0",
44
+ "@utoo/pack-shared": "1.4.0-alpha.10",
45
45
  "domparser-rs": "^0.0.7",
46
46
  "find-up": "4.1.0",
47
47
  "get-port": "5.1.1",
@@ -92,12 +92,12 @@
92
92
  },
93
93
  "repository": "git@github.com:utooland/utoo.git",
94
94
  "optionalDependencies": {
95
- "@utoo/pack-darwin-arm64": "1.4.0-alpha.0",
96
- "@utoo/pack-darwin-x64": "1.4.0-alpha.0",
97
- "@utoo/pack-linux-arm64-gnu": "1.4.0-alpha.0",
98
- "@utoo/pack-linux-arm64-musl": "1.4.0-alpha.0",
99
- "@utoo/pack-linux-x64-gnu": "1.4.0-alpha.0",
100
- "@utoo/pack-linux-x64-musl": "1.4.0-alpha.0",
101
- "@utoo/pack-win32-x64-msvc": "1.4.0-alpha.0"
95
+ "@utoo/pack-darwin-arm64": "1.4.0-alpha.10",
96
+ "@utoo/pack-darwin-x64": "1.4.0-alpha.10",
97
+ "@utoo/pack-linux-arm64-gnu": "1.4.0-alpha.10",
98
+ "@utoo/pack-linux-arm64-musl": "1.4.0-alpha.10",
99
+ "@utoo/pack-linux-x64-gnu": "1.4.0-alpha.10",
100
+ "@utoo/pack-linux-x64-musl": "1.4.0-alpha.10",
101
+ "@utoo/pack-win32-x64-msvc": "1.4.0-alpha.10"
102
102
  }
103
103
  }