@wolfstar/cli 2.2.0 → 2.3.0-next-20261004142621

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.
Files changed (90) hide show
  1. package/LICENSE +201 -201
  2. package/README.md +465 -304
  3. package/dist/{_shared-DJrpalNQ.js → _shared-BIQK0Bhm.js} +2 -2
  4. package/dist/_shared-BIQK0Bhm.js.map +1 -0
  5. package/dist/bridge-BvkmlAOZ.js +410 -0
  6. package/dist/bridge-BvkmlAOZ.js.map +1 -0
  7. package/dist/{build-CluOR8dJ.js → build-DJcc95Yq.js} +5 -5
  8. package/dist/build-DJcc95Yq.js.map +1 -0
  9. package/dist/cli.js +1 -1
  10. package/dist/cli.js.map +1 -1
  11. package/dist/{codegen-D6V1i_fa.js → codegen-aJSyPz-J.js} +4 -4
  12. package/dist/codegen-aJSyPz-J.js.map +1 -0
  13. package/dist/command-diff-BK912Hjc.js +78 -0
  14. package/dist/command-diff-BK912Hjc.js.map +1 -0
  15. package/dist/commands-CIPWQtF0.js +3 -0
  16. package/dist/commands-Clpbqq3K.js +15 -0
  17. package/dist/commands-Clpbqq3K.js.map +1 -0
  18. package/dist/{commands-BJ589_AC.js → commands-DVC7ky6f.js} +259 -9
  19. package/dist/commands-DVC7ky6f.js.map +1 -0
  20. package/dist/completions-D2KYtrrv.js +161 -0
  21. package/dist/completions-D2KYtrrv.js.map +1 -0
  22. package/dist/{dev-DJJZN4NJ.js → dev-oPPVR7d_.js} +434 -28
  23. package/dist/dev-oPPVR7d_.js.map +1 -0
  24. package/dist/{diagnostics-3JRAy8Xj.js → diagnostics-BysbNnPD.js} +22 -1
  25. package/dist/diagnostics-BysbNnPD.js.map +1 -0
  26. package/dist/doctor-DkVUwgDd.js +334 -0
  27. package/dist/doctor-DkVUwgDd.js.map +1 -0
  28. package/dist/errors-COFWKKKw.js.map +1 -1
  29. package/dist/external-CxFKxwi3.js.map +1 -1
  30. package/dist/framework-auto-imports-Gu_PXSyr.js.map +1 -1
  31. package/dist/{hooks-BfDFM38k.js → hooks-Cy6F2bhH.js} +20 -4
  32. package/dist/hooks-Cy6F2bhH.js.map +1 -0
  33. package/dist/index.d.ts +53 -0
  34. package/dist/index.d.ts.map +1 -1
  35. package/dist/index.js +3 -3
  36. package/dist/{info-C1Kx_4Og.js → info-CKJVMWIT.js} +15 -4
  37. package/dist/info-CKJVMWIT.js.map +1 -0
  38. package/dist/{locales-BzOLRBVg.js → locales-BJAP4HYf.js} +5 -5
  39. package/dist/locales-BJAP4HYf.js.map +1 -0
  40. package/dist/log-view-B7uJEnMR.js +342 -0
  41. package/dist/log-view-B7uJEnMR.js.map +1 -0
  42. package/dist/{nitro-yjqZBh5L.js → nitro-B8u1iVgf.js} +2 -2
  43. package/dist/nitro-B8u1iVgf.js.map +1 -0
  44. package/dist/none-uC_wi_l4.js.map +1 -1
  45. package/dist/output-mode-Bp7Da8vJ.js.map +1 -1
  46. package/dist/{plain-B6z85uQP.js → plain-DG7cy0Kk.js} +7 -2
  47. package/dist/plain-DG7cy0Kk.js.map +1 -0
  48. package/dist/{prepare-Cb45Z4re.js → prepare-BM93i3Rm.js} +4 -4
  49. package/dist/prepare-BM93i3Rm.js.map +1 -0
  50. package/dist/{project-D-8VIcyF.js → project-zlQStwsf.js} +2 -2
  51. package/dist/project-zlQStwsf.js.map +1 -0
  52. package/dist/{run-BiLZqib3.js → run-DMM2YlP3.js} +2 -12
  53. package/dist/run-DMM2YlP3.js.map +1 -0
  54. package/dist/{theme-3Fc_LI-2.js → theme-yS2h5dd_.js} +25 -1
  55. package/dist/theme-yS2h5dd_.js.map +1 -0
  56. package/dist/tsc-C5l5TQGC.js +3 -0
  57. package/dist/{tsc-DEBcwIO0.js → tsc-puVAcwmo.js} +24 -5
  58. package/dist/tsc-puVAcwmo.js.map +1 -0
  59. package/dist/{tsdown-DrWXld54.js → tsdown-Dwt3JhPw.js} +2 -2
  60. package/dist/tsdown-Dwt3JhPw.js.map +1 -0
  61. package/dist/{tui-BRddrLQP.js → tui-nldGSD4c.js} +913 -141
  62. package/dist/tui-nldGSD4c.js.map +1 -0
  63. package/dist/version-BzclCE19.js.map +1 -1
  64. package/dist/{vite-Bf7nrJx7.js → vite-YZUtv2Hk.js} +2 -2
  65. package/dist/vite-YZUtv2Hk.js.map +1 -0
  66. package/package.json +5 -5
  67. package/dist/_shared-DJrpalNQ.js.map +0 -1
  68. package/dist/build-CluOR8dJ.js.map +0 -1
  69. package/dist/codegen-D6V1i_fa.js.map +0 -1
  70. package/dist/commands-BJ589_AC.js.map +0 -1
  71. package/dist/dev-DJJZN4NJ.js.map +0 -1
  72. package/dist/diagnostics-3JRAy8Xj.js.map +0 -1
  73. package/dist/hooks-BfDFM38k.js.map +0 -1
  74. package/dist/info-C1Kx_4Og.js.map +0 -1
  75. package/dist/locales-BzOLRBVg.js.map +0 -1
  76. package/dist/log-buffer-CY82aqnb.js +0 -72
  77. package/dist/log-buffer-CY82aqnb.js.map +0 -1
  78. package/dist/nitro-yjqZBh5L.js.map +0 -1
  79. package/dist/plain-B6z85uQP.js.map +0 -1
  80. package/dist/prepare-Cb45Z4re.js.map +0 -1
  81. package/dist/project-D-8VIcyF.js.map +0 -1
  82. package/dist/run-BiLZqib3.js.map +0 -1
  83. package/dist/theme-3Fc_LI-2.js.map +0 -1
  84. package/dist/tsc-B931Ezh7.js +0 -3
  85. package/dist/tsc-DEBcwIO0.js.map +0 -1
  86. package/dist/tsdown-DrWXld54.js.map +0 -1
  87. package/dist/tui-BRddrLQP.js.map +0 -1
  88. package/dist/tunnel-DHSxOZKr.js +0 -175
  89. package/dist/tunnel-DHSxOZKr.js.map +0 -1
  90. package/dist/vite-Bf7nrJx7.js.map +0 -1
@@ -22,6 +22,10 @@ const THEMES = {
22
22
  success: "#4ade80",
23
23
  warning: "#facc15",
24
24
  error: "#f87171",
25
+ info: "#4ade80",
26
+ debug: "#60a5fa",
27
+ trace: "#c084fc",
28
+ accent: "#fbbf24",
25
29
  text: void 0,
26
30
  onBright: "#000000",
27
31
  onError: "#000000"
@@ -34,6 +38,10 @@ const THEMES = {
34
38
  success: "#15803d",
35
39
  warning: "#a16207",
36
40
  error: "#b91c1c",
41
+ info: "#15803d",
42
+ debug: "#1d4ed8",
43
+ trace: "#7e22ce",
44
+ accent: "#b45309",
37
45
  text: void 0,
38
46
  onBright: "#ffffff",
39
47
  onError: "#ffffff"
@@ -46,6 +54,10 @@ const THEMES = {
46
54
  success: "#56b4e9",
47
55
  warning: "#e69f00",
48
56
  error: "#ff8a3d",
57
+ info: "#56b4e9",
58
+ debug: "#0072b2",
59
+ trace: "#cc79a7",
60
+ accent: "#f0e442",
49
61
  text: void 0,
50
62
  onBright: "#000000",
51
63
  onError: "#000000"
@@ -58,6 +70,10 @@ const THEMES = {
58
70
  success: "#0072b2",
59
71
  warning: "#8a6500",
60
72
  error: "#b84a00",
73
+ info: "#0072b2",
74
+ debug: "#004c7a",
75
+ trace: "#8e3b76",
76
+ accent: "#8a6500",
61
77
  text: void 0,
62
78
  onBright: "#ffffff",
63
79
  onError: "#ffffff"
@@ -70,6 +86,10 @@ const THEMES = {
70
86
  success: "greenBright",
71
87
  warning: "yellowBright",
72
88
  error: "redBright",
89
+ info: "greenBright",
90
+ debug: "blueBright",
91
+ trace: "magentaBright",
92
+ accent: "yellowBright",
73
93
  text: void 0,
74
94
  onBright: "black",
75
95
  onError: "black"
@@ -82,6 +102,10 @@ const THEMES = {
82
102
  success: "green",
83
103
  warning: "yellow",
84
104
  error: "red",
105
+ info: "green",
106
+ debug: "blue",
107
+ trace: "magenta",
108
+ accent: "yellow",
85
109
  text: void 0,
86
110
  onBright: "white",
87
111
  onError: "white"
@@ -148,4 +172,4 @@ function saveTheme(setting, env = process.env) {
148
172
 
149
173
  //#endregion
150
174
  export { readSavedTheme as a, saveTheme as c, isThemeSetting as i, THEME_SETTINGS as n, resolveTheme as o, detectTerminalBackground as r, resolveThemeSetting as s, THEMES as t };
151
- //# sourceMappingURL=theme-3Fc_LI-2.js.map
175
+ //# sourceMappingURL=theme-yS2h5dd_.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"theme-yS2h5dd_.js","names":[],"sources":["../src/utils/theme.ts"],"sourcesContent":["import { mkdirSync, readFileSync, writeFileSync } from 'node:fs';\nimport { homedir } from 'node:os';\nimport { dirname, join } from 'node:path';\n\n/** Every theme a user can pick, in the order the picker lists them. `auto` follows the terminal background. */\nexport const THEME_SETTINGS = ['auto', 'dark', 'light', 'dark-daltonized', 'light-daltonized', 'dark-ansi', 'light-ansi'] as const;\nexport type ThemeSetting = (typeof THEME_SETTINGS)[number];\nexport type ThemeName = Exclude<ThemeSetting, 'auto'>;\n\n/**\n * Semantic colour roles the TUI paints with, instead of hardcoded colour names. `undefined` leaves the terminal's own\n * foreground colour, which is the only legible choice for body text on both dark and light backgrounds.\n */\nexport interface Theme {\n\t/** The wordmark, progress bar and selection marker. */\n\tbrand: string;\n\turl: string;\n\ttunnel: string;\n\t/** Something is still building or starting. */\n\tbusy: string;\n\tsuccess: string;\n\twarning: string;\n\terror: string;\n\t/** The `info`, `debug` and `trace` level badges of the dashboard's log stream. */\n\tinfo: string;\n\tdebug: string;\n\ttrace: string;\n\t/** Names worth finding in a log line: a command, a piece, a channel that is switched on. */\n\taccent: string;\n\ttext: string | undefined;\n\t/** Foreground of a badge painted on `success`, `warning` or `busy`. */\n\tonBright: string;\n\t/** Foreground of a badge painted on `error`. */\n\tonError: string;\n}\n\nexport type ThemeToken = keyof Theme;\n\nexport const THEMES: Readonly<Record<ThemeName, Theme>> = {\n\tdark: {\n\t\tbrand: '#4ade80',\n\t\turl: '#22d3ee',\n\t\ttunnel: '#e879f9',\n\t\tbusy: '#facc15',\n\t\tsuccess: '#4ade80',\n\t\twarning: '#facc15',\n\t\terror: '#f87171',\n\t\tinfo: '#4ade80',\n\t\tdebug: '#60a5fa',\n\t\ttrace: '#c084fc',\n\t\taccent: '#fbbf24',\n\t\ttext: undefined,\n\t\tonBright: '#000000',\n\t\tonError: '#000000'\n\t},\n\tlight: {\n\t\tbrand: '#15803d',\n\t\turl: '#0e7490',\n\t\ttunnel: '#a21caf',\n\t\tbusy: '#a16207',\n\t\tsuccess: '#15803d',\n\t\twarning: '#a16207',\n\t\terror: '#b91c1c',\n\t\tinfo: '#15803d',\n\t\tdebug: '#1d4ed8',\n\t\ttrace: '#7e22ce',\n\t\taccent: '#b45309',\n\t\ttext: undefined,\n\t\tonBright: '#ffffff',\n\t\tonError: '#ffffff'\n\t},\n\t// Okabe-Ito palette: blue/orange carry the good/bad distinction instead of green/red.\n\t'dark-daltonized': {\n\t\tbrand: '#56b4e9',\n\t\turl: '#56b4e9',\n\t\ttunnel: '#cc79a7',\n\t\tbusy: '#f0e442',\n\t\tsuccess: '#56b4e9',\n\t\twarning: '#e69f00',\n\t\terror: '#ff8a3d',\n\t\tinfo: '#56b4e9',\n\t\tdebug: '#0072b2',\n\t\ttrace: '#cc79a7',\n\t\taccent: '#f0e442',\n\t\ttext: undefined,\n\t\tonBright: '#000000',\n\t\tonError: '#000000'\n\t},\n\t'light-daltonized': {\n\t\tbrand: '#0072b2',\n\t\turl: '#0072b2',\n\t\ttunnel: '#8e3b76',\n\t\tbusy: '#8a6500',\n\t\tsuccess: '#0072b2',\n\t\twarning: '#8a6500',\n\t\terror: '#b84a00',\n\t\tinfo: '#0072b2',\n\t\tdebug: '#004c7a',\n\t\ttrace: '#8e3b76',\n\t\taccent: '#8a6500',\n\t\ttext: undefined,\n\t\tonBright: '#ffffff',\n\t\tonError: '#ffffff'\n\t},\n\t// The 16 ANSI colours only, so the terminal's own palette decides what they look like.\n\t'dark-ansi': {\n\t\tbrand: 'greenBright',\n\t\turl: 'cyanBright',\n\t\ttunnel: 'magentaBright',\n\t\tbusy: 'yellowBright',\n\t\tsuccess: 'greenBright',\n\t\twarning: 'yellowBright',\n\t\terror: 'redBright',\n\t\tinfo: 'greenBright',\n\t\tdebug: 'blueBright',\n\t\ttrace: 'magentaBright',\n\t\taccent: 'yellowBright',\n\t\ttext: undefined,\n\t\tonBright: 'black',\n\t\tonError: 'black'\n\t},\n\t'light-ansi': {\n\t\tbrand: 'green',\n\t\turl: 'cyan',\n\t\ttunnel: 'magenta',\n\t\tbusy: 'yellow',\n\t\tsuccess: 'green',\n\t\twarning: 'yellow',\n\t\terror: 'red',\n\t\tinfo: 'green',\n\t\tdebug: 'blue',\n\t\ttrace: 'magenta',\n\t\taccent: 'yellow',\n\t\ttext: undefined,\n\t\tonBright: 'white',\n\t\tonError: 'white'\n\t}\n};\n\nexport function isThemeSetting(value: unknown): value is ThemeSetting {\n\treturn typeof value === 'string' && (THEME_SETTINGS as readonly string[]).includes(value);\n}\n\n/**\n * Guesses whether the terminal background is light from `COLORFGBG` (`foreground;background`, set by rxvt, Konsole and\n * others). Without it the terminal is assumed dark, which matches most developer setups.\n */\nexport function detectTerminalBackground(env: NodeJS.ProcessEnv = process.env): 'dark' | 'light' {\n\tconst background = env.COLORFGBG?.split(';').at(-1);\n\tif (background === undefined || !/^\\d+$/.test(background)) return 'dark';\n\tconst index = Number(background);\n\treturn index === 7 || index === 15 ? 'light' : 'dark';\n}\n\nexport function resolveTheme(setting: ThemeSetting, env: NodeJS.ProcessEnv = process.env): ThemeName {\n\treturn setting === 'auto' ? detectTerminalBackground(env) : setting;\n}\n\nexport interface ThemeSettingSources {\n\t/** `--theme`. */\n\tflag?: string;\n\tenv?: NodeJS.ProcessEnv;\n\t/** The theme saved by the picker. */\n\tsaved?: ThemeSetting;\n}\n\n/**\n * Precedence: `--theme` › `STARS_THEME` › the saved preference › `auto`. An unknown `STARS_THEME` is ignored, since an\n * environment variable should not stop the dev server; an unknown `--theme` is the caller's to reject.\n */\nexport function resolveThemeSetting({ flag, env = process.env, saved }: ThemeSettingSources): ThemeSetting {\n\tif (isThemeSetting(flag)) return flag;\n\tconst fromEnv = env.STARS_THEME?.trim().toLowerCase();\n\tif (isThemeSetting(fromEnv)) return fromEnv;\n\treturn saved ?? 'auto';\n}\n\n/** Where preferences live: `$STARS_CONFIG_DIR`, else `$XDG_CONFIG_HOME/stars`, `%APPDATA%\\stars` or `~/.config/stars`. */\nexport function preferencesPath(env: NodeJS.ProcessEnv = process.env): string {\n\tconst directory =\n\t\tenv.STARS_CONFIG_DIR ??\n\t\tjoin((env.XDG_CONFIG_HOME || (process.platform === 'win32' ? env.APPDATA : undefined)) ?? join(homedir(), '.config'), 'stars');\n\treturn join(directory, 'preferences.json');\n}\n\nexport function readSavedTheme(env: NodeJS.ProcessEnv = process.env): ThemeSetting | undefined {\n\ttry {\n\t\tconst { theme } = JSON.parse(readFileSync(preferencesPath(env), 'utf8')) as { theme?: unknown };\n\t\treturn isThemeSetting(theme) ? theme : undefined;\n\t} catch {\n\t\treturn undefined;\n\t}\n}\n\n/** Persists the theme, keeping any other preference in the file. Returns whether it could be written. */\nexport function saveTheme(setting: ThemeSetting, env: NodeJS.ProcessEnv = process.env): boolean {\n\tconst path = preferencesPath(env);\n\ttry {\n\t\tlet existing: Record<string, unknown> = {};\n\t\ttry {\n\t\t\tconst parsed: unknown = JSON.parse(readFileSync(path, 'utf8'));\n\t\t\tif (parsed && typeof parsed === 'object' && !Array.isArray(parsed)) existing = parsed as Record<string, unknown>;\n\t\t} catch {\n\t\t\t// No file yet, or a corrupt one: start over.\n\t\t}\n\t\tmkdirSync(dirname(path), { recursive: true });\n\t\twriteFileSync(path, `${JSON.stringify({ ...existing, theme: setting }, null, '\\t')}\\n`);\n\t\treturn true;\n\t} catch {\n\t\treturn false;\n\t}\n}\n"],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import { n as resolveTscBinary, t as TscBuilder } from "./tsc-puVAcwmo.js";
2
+
3
+ export { TscBuilder };
@@ -1,5 +1,5 @@
1
- import { t as cliDiagnostics } from "./diagnostics-3JRAy8Xj.js";
2
- import { r as resolveBinary } from "./project-D-8VIcyF.js";
1
+ import { t as cliDiagnostics } from "./diagnostics-BysbNnPD.js";
2
+ import { r as resolveBinary } from "./project-zlQStwsf.js";
3
3
  import { EventEmitter } from "node:events";
4
4
  import { spawn } from "node:child_process";
5
5
 
@@ -31,12 +31,17 @@ var ProcessSupervisor = class extends EventEmitter {
31
31
  }
32
32
  start() {
33
33
  if (this.#child) throw new Error("The process is already running, call stop() or restart() first.");
34
- const { command, args, cwd, env } = this.options;
34
+ const { command, args, cwd, env, ipc = false } = this.options;
35
35
  this.#setState("starting");
36
36
  const child = spawn(command, args, {
37
37
  cwd,
38
38
  env,
39
- stdio: [
39
+ stdio: ipc ? [
40
+ "ignore",
41
+ "pipe",
42
+ "pipe",
43
+ "ipc"
44
+ ] : [
40
45
  "ignore",
41
46
  "pipe",
42
47
  "pipe"
@@ -50,6 +55,7 @@ var ProcessSupervisor = class extends EventEmitter {
50
55
  const stderr = createLineSplitter((line) => this.emit("stderr", line));
51
56
  child.stdout?.on("data", stdout.push);
52
57
  child.stderr?.on("data", stderr.push);
58
+ if (ipc) child.on("message", (message) => this.emit("message", message));
53
59
  child.once("spawn", () => {
54
60
  if (this.#child === child) this.#setState("running");
55
61
  });
@@ -97,6 +103,19 @@ var ProcessSupervisor = class extends EventEmitter {
97
103
  return this.#stopping;
98
104
  }
99
105
  /**
106
+ * Sends a message over the IPC channel. Returns whether it could be handed over: `false` without a running process,
107
+ * without `ipc`, or once the process closed its end of the channel.
108
+ */
109
+ send(message) {
110
+ const child = this.#child;
111
+ if (!child?.connected) return false;
112
+ try {
113
+ return child.send(message);
114
+ } catch {
115
+ return false;
116
+ }
117
+ }
118
+ /**
100
119
  * Sends `SIGKILL` right away, without waiting for the process to exit. Used to force a shutdown that is taking too long.
101
120
  */
102
121
  kill() {
@@ -260,4 +279,4 @@ function resolveTscBinary(root) {
260
279
 
261
280
  //#endregion
262
281
  export { createLineSplitter as i, resolveTscBinary as n, ProcessSupervisor as r, TscBuilder as t };
263
- //# sourceMappingURL=tsc-DEBcwIO0.js.map
282
+ //# sourceMappingURL=tsc-puVAcwmo.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tsc-puVAcwmo.js","names":[],"sources":["../src/utils/process-supervisor.ts","../src/builders/tsc.ts"],"sourcesContent":["import { spawn, type ChildProcess } from 'node:child_process';\nimport { EventEmitter } from 'node:events';\n\nexport type ProcessState = 'idle' | 'starting' | 'running' | 'stopping' | 'stopped' | 'crashed';\n\nexport interface ProcessExit {\n\tcode: number | null;\n\tsignal: NodeJS.Signals | null;\n\t/** Whether the exit was requested through {@link ProcessSupervisor.stop}. */\n\trequested: boolean;\n}\n\nexport interface ProcessSupervisorOptions {\n\tcommand: string;\n\targs: readonly string[];\n\tcwd: string;\n\tenv: NodeJS.ProcessEnv;\n\t/** Milliseconds to wait after `SIGTERM` before sending `SIGKILL`. */\n\tkillTimeout: number;\n\t/** Opens an IPC channel to the process, for {@link ProcessSupervisorEvents.message} and {@link ProcessSupervisor.send}. */\n\tipc?: boolean;\n}\n\nexport interface ProcessSupervisorEvents {\n\tstate: [state: ProcessState];\n\tstdout: [line: string];\n\tstderr: [line: string];\n\t/** A message the process sent over the IPC channel. */\n\tmessage: [message: unknown];\n\texit: [exit: ProcessExit];\n\terror: [error: Error];\n}\n\n/**\n * Owns a single child process: starts it, streams its output line by line and stops it gracefully.\n */\nexport class ProcessSupervisor extends EventEmitter<ProcessSupervisorEvents> {\n\t#child: ChildProcess | null = null;\n\t#state: ProcessState = 'idle';\n\t#startedAt: number | null = null;\n\t#stopping: Promise<void> | null = null;\n\n\tpublic constructor(private readonly options: ProcessSupervisorOptions) {\n\t\tsuper();\n\t}\n\n\tpublic get state(): ProcessState {\n\t\treturn this.#state;\n\t}\n\n\tpublic get pid(): number | null {\n\t\treturn this.#child?.pid ?? null;\n\t}\n\n\tpublic get startedAt(): number | null {\n\t\treturn this.#startedAt;\n\t}\n\n\tpublic get running(): boolean {\n\t\treturn this.#state === 'starting' || this.#state === 'running';\n\t}\n\n\tpublic start(): void {\n\t\tif (this.#child) throw new Error('The process is already running, call stop() or restart() first.');\n\n\t\tconst { command, args, cwd, env, ipc = false } = this.options;\n\t\tthis.#setState('starting');\n\n\t\tconst child = spawn(command, args, {\n\t\t\tcwd,\n\t\t\tenv,\n\t\t\tstdio: ipc ? ['ignore', 'pipe', 'pipe', 'ipc'] : ['ignore', 'pipe', 'pipe'],\n\t\t\twindowsHide: true\n\t\t});\n\t\tthis.#child = child;\n\t\tthis.#startedAt = Date.now();\n\n\t\tlet requested = false;\n\t\tconst stdout = createLineSplitter((line) => this.emit('stdout', line));\n\t\tconst stderr = createLineSplitter((line) => this.emit('stderr', line));\n\t\tchild.stdout?.on('data', stdout.push);\n\t\tchild.stderr?.on('data', stderr.push);\n\t\tif (ipc) child.on('message', (message) => this.emit('message', message));\n\n\t\tchild.once('spawn', () => {\n\t\t\tif (this.#child === child) this.#setState('running');\n\t\t});\n\n\t\tchild.once('error', (error) => {\n\t\t\tthis.emit('error', error);\n\t\t});\n\n\t\tchild.once('exit', (code, signal) => {\n\t\t\tstdout.flush();\n\t\t\tstderr.flush();\n\t\t\trequested = this.#state === 'stopping';\n\t\t\tthis.#child = null;\n\t\t\tthis.#startedAt = null;\n\t\t\tthis.#setState(requested || code === 0 ? 'stopped' : 'crashed');\n\t\t\tthis.emit('exit', { code, signal, requested });\n\t\t});\n\t}\n\n\t/**\n\t * Sends `SIGTERM`, escalates to `SIGKILL` after `killTimeout` and resolves once the process exited.\n\t */\n\tpublic stop(): Promise<void> {\n\t\tconst child = this.#child;\n\t\tif (!child) return Promise.resolve();\n\t\tif (this.#stopping) return this.#stopping;\n\n\t\tthis.#setState('stopping');\n\t\tthis.#stopping = new Promise<void>((resolve) => {\n\t\t\tconst timer = setTimeout(() => {\n\t\t\t\tif (child.exitCode === null && child.signalCode === null) child.kill('SIGKILL');\n\t\t\t}, this.options.killTimeout);\n\t\t\ttimer.unref();\n\n\t\t\tchild.once('exit', () => {\n\t\t\t\tclearTimeout(timer);\n\t\t\t\tthis.#stopping = null;\n\t\t\t\tresolve();\n\t\t\t});\n\n\t\t\tif (!child.kill('SIGTERM')) {\n\t\t\t\tclearTimeout(timer);\n\t\t\t\tthis.#stopping = null;\n\t\t\t\tresolve();\n\t\t\t}\n\t\t});\n\n\t\treturn this.#stopping;\n\t}\n\n\t/**\n\t * Sends a message over the IPC channel. Returns whether it could be handed over: `false` without a running process,\n\t * without `ipc`, or once the process closed its end of the channel.\n\t */\n\tpublic send(message: unknown): boolean {\n\t\tconst child = this.#child;\n\t\tif (!child?.connected) return false;\n\t\ttry {\n\t\t\treturn child.send(message as never);\n\t\t} catch {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t/**\n\t * Sends `SIGKILL` right away, without waiting for the process to exit. Used to force a shutdown that is taking too long.\n\t */\n\tpublic kill(): void {\n\t\tconst child = this.#child;\n\t\tif (child && child.exitCode === null && child.signalCode === null) child.kill('SIGKILL');\n\t}\n\n\tpublic async restart(): Promise<void> {\n\t\tawait this.stop();\n\t\tthis.start();\n\t}\n\n\t#setState(state: ProcessState): void {\n\t\tif (this.#state === state) return;\n\t\tthis.#state = state;\n\t\tthis.emit('state', state);\n\t}\n}\n\n/**\n * Splits a byte stream into complete lines, keeping the trailing partial line until the next chunk.\n */\nexport function createLineSplitter(onLine: (line: string) => void) {\n\tlet remainder = '';\n\treturn {\n\t\tpush(chunk: Buffer | string) {\n\t\t\tremainder += chunk.toString();\n\t\t\tconst lines = remainder.split(/\\r?\\n/);\n\t\t\tremainder = lines.pop() ?? '';\n\t\t\tfor (const line of lines) onLine(line);\n\t\t},\n\t\tflush() {\n\t\t\tif (remainder.length > 0) onLine(remainder);\n\t\t\tremainder = '';\n\t\t}\n\t};\n}\n","import { spawn, type ChildProcess } from 'node:child_process';\nimport { EventEmitter } from 'node:events';\nimport type { ResolvedStarsConfig } from '@wolfstar/schema';\nimport { cliDiagnostics } from '../utils/diagnostics.js';\nimport { createLineSplitter } from '../utils/process-supervisor.js';\nimport { resolveBinary } from '../utils/project.js';\nimport type { Builder, BuilderEvents, BuildOutcome } from './types.js';\n\nconst INSTALL_HINT = \"Install it with `pnpm add -D typescript`, or set `build.tool` to 'tsdown' or 'none'.\";\nconst WATCH_START = /Starting (incremental )?compilation/;\nconst WATCH_DONE = /Found (\\d+) errors?\\. Watching for file changes/;\nconst ERROR_LINE = /error TS\\d+:/;\n\n/**\n * Builds through the project's `tsc -b`, parsing its output to report progress.\n */\nexport class TscBuilder extends EventEmitter<BuilderEvents> implements Builder {\n\tpublic readonly tool = 'tsc' as const;\n\t#child: ChildProcess | null = null;\n\t#startedAt = 0;\n\t#firstError: string | null = null;\n\n\tpublic constructor(private readonly config: ResolvedStarsConfig) {\n\t\tsuper();\n\t}\n\n\tpublic build(): Promise<BuildOutcome> {\n\t\tconst child = this.#spawn([]);\n\t\tthis.#begin();\n\n\t\treturn new Promise((resolve) => {\n\t\t\tchild.once('exit', (code) => {\n\t\t\t\tthis.#child = null;\n\t\t\t\tresolve(this.#finish(code === 0 ? null : (this.#firstError ?? `tsc exited with code ${code}`)));\n\t\t\t});\n\t\t});\n\t}\n\n\tpublic watch(): Promise<void> {\n\t\tthis.#spawn(['--watch', '--preserveWatchOutput']);\n\t\tthis.#begin();\n\t\treturn Promise.resolve();\n\t}\n\n\tpublic close(): Promise<void> {\n\t\tconst child = this.#child;\n\t\tthis.#child = null;\n\t\tif (!child || child.exitCode !== null) return Promise.resolve();\n\n\t\treturn new Promise((resolve) => {\n\t\t\tchild.once('exit', () => resolve());\n\t\t\tchild.kill();\n\t\t});\n\t}\n\n\t#spawn(extraArgs: string[]): ChildProcess {\n\t\tconst tsc = resolveTscBinary(this.config.root);\n\t\tif (!tsc) throw cliDiagnostics.DEPENDENCY_MISSING({ name: 'typescript', root: this.config.root, hint: INSTALL_HINT });\n\n\t\tconst child = spawn(process.execPath, [tsc, '-b', this.config.build.tsconfig!, '--pretty', 'false', ...extraArgs], {\n\t\t\tcwd: this.config.root,\n\t\t\tenv: process.env,\n\t\t\tstdio: ['ignore', 'pipe', 'pipe'],\n\t\t\twindowsHide: true\n\t\t});\n\t\tthis.#child = child;\n\n\t\tconst handleLine = (line: string) => this.#handleLine(line);\n\t\tconst stdout = createLineSplitter(handleLine);\n\t\tconst stderr = createLineSplitter(handleLine);\n\t\tchild.stdout?.on('data', stdout.push);\n\t\tchild.stderr?.on('data', stderr.push);\n\t\tchild.once('exit', () => {\n\t\t\tstdout.flush();\n\t\t\tstderr.flush();\n\t\t});\n\t\tchild.once('error', (error) => this.emit('log', 'error', error.message));\n\n\t\treturn child;\n\t}\n\n\t#handleLine(line: string): void {\n\t\tconst text = line.trim();\n\t\tif (text.length === 0) return;\n\n\t\tif (WATCH_START.test(text)) {\n\t\t\tif (this.#startedAt === 0) this.#begin();\n\t\t\treturn;\n\t\t}\n\n\t\tif (ERROR_LINE.test(text)) {\n\t\t\tthis.#firstError ??= text;\n\t\t\tthis.emit('log', 'error', text);\n\t\t\treturn;\n\t\t}\n\n\t\tconst done = WATCH_DONE.exec(text);\n\t\tif (done) {\n\t\t\tconst errors = Number(done[1]);\n\t\t\tthis.emit('log', errors === 0 ? 'success' : 'error', text);\n\t\t\tthis.#finish(errors === 0 ? null : (this.#firstError ?? text));\n\t\t\treturn;\n\t\t}\n\n\t\tthis.emit('log', 'info', text);\n\t}\n\n\t#begin(): void {\n\t\tthis.#firstError = null;\n\t\tthis.#startedAt = performance.now();\n\t\tthis.emit('start');\n\t}\n\n\t#finish(message: string | null): BuildOutcome {\n\t\tconst outcome: BuildOutcome = { ok: message === null, durationMs: Math.round(performance.now() - this.#startedAt), message };\n\t\tthis.#startedAt = 0;\n\t\tthis.emit(outcome.ok ? 'success' : 'failure', outcome);\n\t\treturn outcome;\n\t}\n}\n\n/**\n * Locates the `tsc` script of the project's TypeScript through its `package.json#bin`, which works for both the\n * classic `lib/tsc.js` layout (TypeScript ≤ 6) and the native `bin/tsc` launcher (TypeScript 7, whose `exports` map\n * hides `lib/`).\n */\nexport function resolveTscBinary(root: string): string | null {\n\treturn resolveBinary(root, 'typescript', 'tsc');\n}\n"],"mappings":"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"}
@@ -1,5 +1,5 @@
1
1
  import { t as pluginRegistrations } from "./plugin-registrations-Dr_BicfC.js";
2
- import { n as importFromProject } from "./project-D-8VIcyF.js";
2
+ import { n as importFromProject } from "./project-zlQStwsf.js";
3
3
  import { t as loadAutoImportsModule } from "./framework-auto-imports-Gu_PXSyr.js";
4
4
  import { dirname, extname, relative, resolve } from "node:path";
5
5
  import { EventEmitter } from "node:events";
@@ -251,4 +251,4 @@ function errorSummary(args) {
251
251
 
252
252
  //#endregion
253
253
  export { TsdownBuilder };
254
- //# sourceMappingURL=tsdown-DrWXld54.js.map
254
+ //# sourceMappingURL=tsdown-Dwt3JhPw.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tsdown-Dwt3JhPw.js","names":[],"sources":["../src/builders/tsdown.ts"],"sourcesContent":["import { EventEmitter } from 'node:events';\nimport { dirname, extname, relative, resolve } from 'node:path';\nimport type { ResolvedStarsConfig } from '@wolfstar/schema';\nimport { loadAutoImportsModule } from '../utils/framework-auto-imports.js';\nimport type { StarsHookable } from '../utils/hooks.js';\nimport { pluginRegistrations } from '../utils/plugin-registrations.js';\nimport { importFromProject } from '../utils/project.js';\nimport type { Builder, BuilderEvents, BuildOutcome } from './types.js';\n\ntype TsdownModule = typeof import('tsdown');\ntype TsdownLogger = import('tsdown').Logger;\ntype TsdownHandle = import('tsdown').TsdownHandle;\ntype TsdownInlineConfig = NonNullable<Parameters<TsdownModule['build']>[0]>;\ntype TsdownOptions = Record<string, unknown>;\ntype AnyFunction = (...args: never[]) => unknown;\n\nconst INSTALL_HINT = \"Install it with `pnpm add -D tsdown`, or set `build.tool` to 'tsc' or 'none'.\";\nconst TYPESCRIPT_EXTENSIONS = new Set(['.ts', '.mts', '.cts']);\n/** `./src/lib` and `../shared` are paths; `preact/compat` is a module id and must be left alone. */\nconst RELATIVE_PATH = /^\\.\\.?[/\\\\]/;\n\n/**\n * Builds through the project's own `tsdown`, configured from `stars.config`.\n *\n * From `future.compatibilityVersion` 4 on this is the whole configuration: the entry's directory, `build.outDir` and\n * `build.tsconfig` produce the defaults a bot needs, the project's `tsdown` block is layered on top, and the auto\n * imports plugin is wired in — one configuration file instead of two. At 3 the project's own `tsdown.config.*` is\n * still loaded and everything here is merged over it by `tsdown` itself: scalars from `stars.config` win, and\n * `plugins` are appended rather than replaced.\n */\nexport class TsdownBuilder extends EventEmitter<BuilderEvents> implements Builder {\n\tpublic readonly tool = 'tsdown' as const;\n\t#handle: TsdownHandle | null = null;\n\t#hadError = false;\n\t#startedAt = 0;\n\n\tpublic constructor(\n\t\tprivate readonly config: ResolvedStarsConfig,\n\t\tprivate readonly hooks?: StarsHookable\n\t) {\n\t\tsuper();\n\t}\n\n\tpublic async build(): Promise<BuildOutcome> {\n\t\tconst tsdown = await this.#load();\n\t\tconst options = await this.#options();\n\t\tthis.#begin();\n\n\t\ttry {\n\t\t\tthis.#handle = await tsdown.build(options as TsdownInlineConfig);\n\t\t\treturn this.#finish(this.#hadError ? 'The build reported errors' : null);\n\t\t} catch (error) {\n\t\t\treturn this.#finish(error instanceof Error ? error.message : String(error));\n\t\t}\n\t}\n\n\tpublic async watch(): Promise<void> {\n\t\tconst tsdown = await this.#load();\n\t\tconst options = await this.#options();\n\n\t\tthis.#begin();\n\t\tthis.#handle = await tsdown.build(this.#watchOptions(options) as TsdownInlineConfig);\n\t}\n\n\tpublic async close(): Promise<void> {\n\t\tconst handle = this.#handle;\n\t\tthis.#handle = null;\n\t\tawait handle?.watch.close();\n\t}\n\n\t#load(): Promise<TsdownModule> {\n\t\treturn importFromProject<TsdownModule>(this.config.root, 'tsdown', INSTALL_HINT);\n\t}\n\n\t/**\n\t * The options handed to `tsdown.build()`, with the project's own `tsdown` block already layered on top of the\n\t * defaults (and of the plugins `stars` contributes).\n\t */\n\tasync #options(): Promise<TsdownOptions> {\n\t\tconst user = this.config.tsdown as TsdownOptions;\n\t\t// A `tsdown.config.*` (or `package.json#tsdown`) is the project's own; `build.configFile` is `null` from\n\t\t// compatibility version 4 on, where loading one is a configuration error rather than a fallback.\n\t\tconst defaults = this.config.build.configFile === null ? this.#defaults() : {};\n\t\tconst plugins = [pluginRegistrations(this.config), ...(await this.#plugins()), ...toArray(user.plugins)];\n\t\t// `plugins` and `alias` are added to rather than replaced: a project declaring one of its own would\n\t\t// otherwise silently drop the auto imports transform, or every `~`/`@` import in its sources.\n\t\tconst alias = { ...(defaults.alias as object), ...this.#alias(user.alias) };\n\n\t\tconst options: TsdownOptions = {\n\t\t\t...defaults,\n\t\t\t...user,\n\t\t\t...(plugins.length > 0 ? { plugins } : {}),\n\t\t\t...(Object.keys(alias).length > 0 ? { alias } : {})\n\t\t};\n\t\tawait this.hooks?.callHook('tsdown:options', options, this.config);\n\n\t\treturn {\n\t\t\t...options,\n\t\t\t// Last, and so not overridable (not even by `tsdown:options`): these are how the CLI talks to `tsdown` rather\n\t\t\t// than project build options — the project root it resolves from, its own compact progress UI, and the logger\n\t\t\t// that feeds diagnostics to the dev panel. `logLevel` also covers the few lifecycle messages tsdown writes\n\t\t\t// through its global logger.\n\t\t\tcwd: this.config.root,\n\t\t\tlogLevel: 'warn',\n\t\t\tcustomLogger: this.#logger()\n\t\t};\n\t}\n\n\t/**\n\t * What `stars.config` alone says the build is — the configuration a bot would otherwise write out by hand, taken\n\t * from the ones the WolfStar bots already keep next to theirs:\n\t *\n\t * - every source file next to the entry (minus tests), emitted one-to-one (`unbundle`) so the stores keep\n\t * loading pieces from `dist/commands` and friends at runtime;\n\t * - ESM on `platform: 'node'`, with the extension `build.output` — and so `stars dev`, `package.json#main` and\n\t * `node dist/…` — expects;\n\t * - sourcemaps and treeshaking on, minification off: a bot is deployed, not shipped, so readable stack traces\n\t * are worth more than bytes;\n\t * - dependencies left in `node_modules` rather than bundled into the output;\n\t * - Nuxt's own alias prefixes: `~` and `@` for the entry's directory, `~~` and `@@` for the project root;\n\t * - no declaration files: nothing consumes a bot's `dist/`, and emitting them roughly doubles the build. A\n\t * project that wants them sets `tsdown: { dts: true }`.\n\t *\n\t * Every one of these is overridable through the project's `tsdown` block.\n\t */\n\t#defaults(): TsdownOptions {\n\t\tconst { root, entry, build } = this.config;\n\t\tconst source = dirname(entry);\n\t\tconst sourceDir = relative(root, source) || '.';\n\t\tconst extensions = TYPESCRIPT_EXTENSIONS.has(extname(entry)) ? '{ts,mts,cts}' : '{js,mjs,cjs}';\n\n\t\treturn {\n\t\t\tconfig: false,\n\t\t\tentry: [`${sourceDir}/**/*.${extensions}`, `!${sourceDir}/**/*.{test,spec}.${extensions}`],\n\t\t\t// The prefixes Nuxt gives every project, pointing at the same two places its own do: the source\n\t\t\t// directory and the project root. A project's tsconfig needs the matching `paths` for them to type.\n\t\t\talias: { '~': source, '@': source, '~~': root, '@@': root },\n\t\t\tformat: 'esm',\n\t\t\tplatform: 'node',\n\t\t\tunbundle: true,\n\t\t\toutDir: build.outDir,\n\t\t\toutExtensions: () => ({ js: extname(build.output) }),\n\t\t\tsourcemap: true,\n\t\t\tclean: true,\n\t\t\ttreeshake: true,\n\t\t\tminify: false,\n\t\t\tdts: false,\n\t\t\tdeps: { neverBundle: true },\n\t\t\t...(build.tsconfig === null ? {} : { tsconfig: build.tsconfig })\n\t\t};\n\t}\n\n\t/**\n\t * The project's own aliases, with relative targets resolved against the project root the way every other path in\n\t * `stars.config` is. Module ids (`preact/compat`) and absolute paths are passed through untouched.\n\t */\n\t#alias(alias: unknown): Record<string, unknown> {\n\t\tif (alias === null || typeof alias !== 'object' || Array.isArray(alias)) return {};\n\n\t\treturn Object.fromEntries(\n\t\t\tObject.entries(alias as Record<string, unknown>).map(([key, value]) => [\n\t\t\t\tkey,\n\t\t\t\ttypeof value === 'string' && RELATIVE_PATH.test(value) ? resolve(this.config.root, value) : value\n\t\t\t])\n\t\t);\n\t}\n\n\t/**\n\t * The auto imports transform, the way `nuxt dev` wires its own into the build rather than asking the project to.\n\t * `stars dev`/`stars build` regenerate its declaration file (`stars prepare`) before the first build.\n\t */\n\tasync #plugins(): Promise<unknown[]> {\n\t\tif (!this.config.imports.enabled) return [];\n\n\t\tconst { autoImports } = await loadAutoImportsModule(this.config.root);\n\t\tconst { dirs, presets, exclude, dts } = this.config.imports;\n\t\treturn [await autoImports({ root: this.config.root, dirs, presets, exclude, dts })];\n\t}\n\n\t/**\n\t * Watch mode reports through the same events a single build does. The project's own `hooks`/`onSuccess` still\n\t * run: they are the reason a build is watched at all in some projects.\n\t */\n\t#watchOptions(options: TsdownOptions): TsdownOptions {\n\t\tconst hooks = (options.hooks ?? {}) as Record<string, unknown>;\n\t\tconst prepare = hooks['build:prepare'];\n\t\tconst before = hooks['build:before'];\n\t\tconst done = hooks['build:done'];\n\t\tconst success = options.onSuccess;\n\n\t\treturn {\n\t\t\t...options,\n\t\t\twatch: true,\n\t\t\t// tsdown's build:before runs once when the watcher is configured, not on every rebuild. Rolldown's\n\t\t\t// buildStart is the actual per-build boundary, including recovery after a failed compilation.\n\t\t\tplugins: [\n\t\t\t\t{\n\t\t\t\t\tname: 'stars:dev-progress',\n\t\t\t\t\tbuildStart: () => {\n\t\t\t\t\t\tif (this.#startedAt === 0) this.#begin();\n\t\t\t\t\t\tthis.emit('progress', 0.25, 'bundling app');\n\t\t\t\t\t}\n\t\t\t\t},\n\t\t\t\t...toArray(options.plugins)\n\t\t\t],\n\t\t\thooks: {\n\t\t\t\t...hooks,\n\t\t\t\t'build:prepare': async (...args: never[]) => {\n\t\t\t\t\tif (this.#startedAt === 0) this.#begin();\n\t\t\t\t\tif (typeof prepare === 'function') await (prepare as AnyFunction)(...args);\n\t\t\t\t},\n\t\t\t\t'build:before': async (...args: never[]) => {\n\t\t\t\t\tif (typeof before === 'function') await (before as AnyFunction)(...args);\n\t\t\t\t},\n\t\t\t\t'build:done': async (...args: never[]) => {\n\t\t\t\t\tthis.emit('progress', 0.5, 'finishing build');\n\t\t\t\t\tif (typeof done === 'function') await (done as AnyFunction)(...args);\n\t\t\t\t}\n\t\t\t},\n\t\t\tonSuccess: async (...args: never[]) => {\n\t\t\t\tif (typeof success === 'function') await (success as AnyFunction)(...args);\n\t\t\t\tthis.#finish(null);\n\t\t\t}\n\t\t};\n\t}\n\n\t#begin(): void {\n\t\tthis.#hadError = false;\n\t\tthis.#startedAt = performance.now();\n\t\tthis.emit('start');\n\t}\n\n\t#finish(message: string | null): BuildOutcome {\n\t\tconst outcome: BuildOutcome = {\n\t\t\tok: message === null && !this.#hadError,\n\t\t\tdurationMs: Math.round(performance.now() - this.#startedAt),\n\t\t\tmessage\n\t\t};\n\t\tthis.#startedAt = 0;\n\t\tthis.emit(outcome.ok ? 'success' : 'failure', outcome);\n\t\treturn outcome;\n\t}\n\n\t#logger(): TsdownLogger {\n\t\tconst log = (level: 'info' | 'warn' | 'error' | 'success', args: unknown[]) => {\n\t\t\t// tsdown passes its (possibly undefined) name label and other blanks as separate arguments.\n\t\t\tconst text = args\n\t\t\t\t.filter((argument) => argument !== undefined && argument !== null && argument !== false && argument !== '')\n\t\t\t\t.map((argument) => (argument instanceof Error ? (argument.stack ?? argument.message) : String(argument)))\n\t\t\t\t.join(' ');\n\t\t\tthis.emit('log', level, text);\n\t\t};\n\n\t\tconst warned = new Set<string>();\n\t\treturn {\n\t\t\t// `stars` owns the build progress and completion messages. Keeping tsdown at `warn` avoids copying its\n\t\t\t// entry list, target, output table and completion line into the dev session while preserving diagnostics\n\t\t\t// that need action from the project.\n\t\t\tlevel: 'warn',\n\t\t\tinfo: () => {},\n\t\t\twarn: (...args) => log('warn', args),\n\t\t\twarnOnce: (...args) => {\n\t\t\t\tconst key = args.map(String).join(' ');\n\t\t\t\tif (warned.has(key)) return;\n\t\t\t\twarned.add(key);\n\t\t\t\tlog('warn', args);\n\t\t\t},\n\t\t\terror: (...args) => {\n\t\t\t\tthis.#hadError = true;\n\t\t\t\tlog('error', args);\n\t\t\t\t// In watch mode tsdown never calls `onSuccess` after an error, report the failure now.\n\t\t\t\tif (this.#startedAt !== 0) this.#finish(errorSummary(args));\n\t\t\t},\n\t\t\tsuccess: () => {},\n\t\t\tclearScreen: () => {}\n\t\t};\n\t}\n}\n\nfunction toArray(value: unknown): unknown[] {\n\tif (value === undefined || value === null || value === false) return [];\n\treturn Array.isArray(value) ? value : [value];\n}\n\nfunction errorSummary(args: unknown[]): string {\n\tconst first = args[0];\n\tif (first instanceof Error) return first.message.split('\\n')[0] ?? 'Build failed';\n\treturn String(first ?? 'Build failed').split('\\n')[0] ?? 'Build failed';\n}\n"],"mappings":"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"}