kaizenai 0.3.0 → 0.4.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/bin/kaizen +16 -5
- package/dist/client/app-icon-180.png +0 -0
- package/dist/client/app-icon-192.png +0 -0
- package/dist/client/app-icon-512.png +0 -0
- package/dist/client/app-icon-96.png +0 -0
- package/dist/client/apple-touch-icon.png +0 -0
- package/dist/client/assets/index-BR0jGwm_.css +32 -0
- package/dist/client/assets/index-CYqy6l6r.js +628 -0
- package/dist/client/favicon.png +0 -0
- package/dist/client/index.html +17 -10
- package/dist/client/manifest-dark.webmanifest +3 -3
- package/dist/client/manifest.webmanifest +3 -3
- package/dist/client/pwa-192.png +0 -0
- package/dist/client/pwa-512.png +0 -0
- package/dist/server/cli-supervisor.js +307 -0
- package/dist/server/cli.js +12371 -0
- package/package.json +7 -9
- package/dist/client/assets/index-BBs80KD-.js +0 -623
- package/dist/client/assets/index-CkCgyLNq.css +0 -32
- package/src/server/acp-shared.ts +0 -315
- package/src/server/agent.ts +0 -1159
- package/src/server/attachments.ts +0 -133
- package/src/server/backgrounds.ts +0 -74
- package/src/server/cli-runtime.ts +0 -375
- package/src/server/cli-supervisor.ts +0 -97
- package/src/server/cli.ts +0 -68
- package/src/server/codex-app-server-protocol.ts +0 -453
- package/src/server/codex-app-server.ts +0 -1350
- package/src/server/cursor-acp.ts +0 -819
- package/src/server/discovery.ts +0 -322
- package/src/server/event-store.ts +0 -1470
- package/src/server/events.ts +0 -252
- package/src/server/external-open.ts +0 -272
- package/src/server/gemini-acp.ts +0 -844
- package/src/server/gemini-cli.ts +0 -525
- package/src/server/generate-title.ts +0 -36
- package/src/server/git-manager.ts +0 -79
- package/src/server/git-repository.ts +0 -101
- package/src/server/harness-types.ts +0 -20
- package/src/server/keybindings.ts +0 -177
- package/src/server/machine-name.ts +0 -22
- package/src/server/paths.ts +0 -112
- package/src/server/process-utils.ts +0 -22
- package/src/server/project-icon.ts +0 -352
- package/src/server/project-metadata.ts +0 -10
- package/src/server/provider-catalog.ts +0 -85
- package/src/server/provider-settings.ts +0 -155
- package/src/server/quick-response.ts +0 -153
- package/src/server/read-models.ts +0 -275
- package/src/server/recovery.ts +0 -507
- package/src/server/restart.ts +0 -56
- package/src/server/server.ts +0 -244
- package/src/server/terminal-manager.ts +0 -350
- package/src/server/theme-settings.ts +0 -179
- package/src/server/update-manager.ts +0 -230
- package/src/server/usage/base-provider-usage.ts +0 -57
- package/src/server/usage/claude-usage.ts +0 -558
- package/src/server/usage/codex-usage.ts +0 -144
- package/src/server/usage/cursor-browser.ts +0 -120
- package/src/server/usage/cursor-cookies.ts +0 -390
- package/src/server/usage/cursor-usage.ts +0 -490
- package/src/server/usage/gemini-usage.ts +0 -24
- package/src/server/usage/provider-usage.ts +0 -61
- package/src/server/usage/test-helpers.ts +0 -9
- package/src/server/usage/types.ts +0 -54
- package/src/server/usage/utils.ts +0 -325
- package/src/server/ws-router.ts +0 -742
- package/src/shared/branding.ts +0 -83
- package/src/shared/dev-ports.ts +0 -43
- package/src/shared/ports.ts +0 -2
- package/src/shared/protocol.ts +0 -156
- package/src/shared/tools.ts +0 -251
- package/src/shared/types.ts +0 -1040
package/dist/client/favicon.png
CHANGED
|
Binary file
|
package/dist/client/index.html
CHANGED
|
@@ -3,20 +3,27 @@
|
|
|
3
3
|
<head>
|
|
4
4
|
<meta charset="UTF-8" />
|
|
5
5
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
6
|
-
<meta
|
|
6
|
+
<meta
|
|
7
|
+
name="description"
|
|
8
|
+
content="KaizenAI is a local-first coding agent workspace for running Codex, Claude Code, Gemini, and Cursor from one browser-based interface."
|
|
9
|
+
/>
|
|
7
10
|
<meta name="theme-color" content="#ffffff" />
|
|
8
11
|
<meta name="apple-mobile-web-app-capable" content="yes" />
|
|
9
12
|
<meta name="apple-mobile-web-app-status-bar-style" content="default" />
|
|
10
|
-
<meta name="apple-mobile-web-app-title" content="
|
|
11
|
-
<link rel="icon" type="image/svg+xml" href="/app-icon.svg" />
|
|
12
|
-
<link rel="alternate icon" type="image/png" href="/app-icon-96.png" />
|
|
13
|
-
<link rel="apple-touch-icon" href="/app-icon-180.png" />
|
|
14
|
-
<link
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
13
|
+
<meta name="apple-mobile-web-app-title" content="KaizenAI" />
|
|
14
|
+
<link rel="icon" type="image/svg+xml" href="/app-icon.svg?v=20260329-iconpad" />
|
|
15
|
+
<link rel="alternate icon" type="image/png" href="/app-icon-96.png?v=20260329-iconpad" />
|
|
16
|
+
<link rel="apple-touch-icon" href="/app-icon-180.png?v=20260329-iconpad" />
|
|
17
|
+
<link
|
|
18
|
+
rel="manifest"
|
|
19
|
+
id="app-manifest"
|
|
20
|
+
href="/manifest.webmanifest?v=20260329-iconpad"
|
|
21
|
+
/>
|
|
22
|
+
<title>KaizenAI</title>
|
|
23
|
+
<script type="module" crossorigin src="/assets/index-CYqy6l6r.js"></script>
|
|
24
|
+
<link rel="stylesheet" crossorigin href="/assets/index-BR0jGwm_.css">
|
|
18
25
|
</head>
|
|
19
26
|
<body>
|
|
20
27
|
<div id="root"></div>
|
|
21
28
|
</body>
|
|
22
|
-
|
|
29
|
+
</html>
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
|
-
"name": "
|
|
3
|
-
"short_name": "
|
|
4
|
-
"description": "Local
|
|
2
|
+
"name": "KaizenAI",
|
|
3
|
+
"short_name": "KaizenAI",
|
|
4
|
+
"description": "Local-first coding agent workspace for Codex, Claude Code, Gemini, and Cursor.",
|
|
5
5
|
"id": "/?source=pwa-dark",
|
|
6
6
|
"start_url": "/",
|
|
7
7
|
"scope": "/",
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
|
-
"name": "
|
|
3
|
-
"short_name": "
|
|
4
|
-
"description": "Local
|
|
2
|
+
"name": "KaizenAI",
|
|
3
|
+
"short_name": "KaizenAI",
|
|
4
|
+
"description": "Local-first coding agent workspace for Codex, Claude Code, Gemini, and Cursor.",
|
|
5
5
|
"id": "/?source=pwa",
|
|
6
6
|
"start_url": "/",
|
|
7
7
|
"scope": "/",
|
package/dist/client/pwa-192.png
CHANGED
|
Binary file
|
package/dist/client/pwa-512.png
CHANGED
|
Binary file
|
|
@@ -0,0 +1,307 @@
|
|
|
1
|
+
// @bun
|
|
2
|
+
// src/server/cli-supervisor.ts
|
|
3
|
+
import process from "process";
|
|
4
|
+
import { spawn } from "child_process";
|
|
5
|
+
import { fileURLToPath } from "url";
|
|
6
|
+
// package.json
|
|
7
|
+
var package_default = {
|
|
8
|
+
name: "kaizenai",
|
|
9
|
+
type: "module",
|
|
10
|
+
version: "0.4.0",
|
|
11
|
+
description: "Local web UI for coding agents",
|
|
12
|
+
license: "MIT",
|
|
13
|
+
keywords: [
|
|
14
|
+
"claude",
|
|
15
|
+
"claude-code",
|
|
16
|
+
"ai",
|
|
17
|
+
"chat",
|
|
18
|
+
"ui",
|
|
19
|
+
"agent",
|
|
20
|
+
"anthropic",
|
|
21
|
+
"bun",
|
|
22
|
+
"react"
|
|
23
|
+
],
|
|
24
|
+
repository: {
|
|
25
|
+
type: "git",
|
|
26
|
+
url: "git+https://github.com/jayleaton/kaizen.git"
|
|
27
|
+
},
|
|
28
|
+
homepage: "https://github.com/jayleaton/kaizen#readme",
|
|
29
|
+
bugs: {
|
|
30
|
+
url: "https://github.com/jayleaton/kaizen/issues"
|
|
31
|
+
},
|
|
32
|
+
bin: {
|
|
33
|
+
kaizen: "bin/kaizen"
|
|
34
|
+
},
|
|
35
|
+
publishConfig: {
|
|
36
|
+
access: "public"
|
|
37
|
+
},
|
|
38
|
+
packageManager: "bun@1.3.5",
|
|
39
|
+
files: [
|
|
40
|
+
"bin/",
|
|
41
|
+
"dist/server/",
|
|
42
|
+
"dist/client/"
|
|
43
|
+
],
|
|
44
|
+
engines: {
|
|
45
|
+
bun: ">=1.3.5"
|
|
46
|
+
},
|
|
47
|
+
scripts: {
|
|
48
|
+
build: "vite build && bun run ./scripts/build-server.ts",
|
|
49
|
+
check: "tsc --noEmit && bun run build",
|
|
50
|
+
dev: "bun run ./scripts/dev.ts",
|
|
51
|
+
"dev:client": "vite --host 0.0.0.0 --port 5174",
|
|
52
|
+
"dev:server": "bun run ./scripts/dev-server.ts --no-open --port 5175",
|
|
53
|
+
fmt: "prettier package.json README.md --check",
|
|
54
|
+
"install:dev": "bun install && bun run build && bun install -g .",
|
|
55
|
+
lint: "tsc --noEmit",
|
|
56
|
+
start: "bun run ./dist/server/cli.js",
|
|
57
|
+
test: "bun test",
|
|
58
|
+
typecheck: "tsc --noEmit",
|
|
59
|
+
prepublishOnly: "bun run build"
|
|
60
|
+
},
|
|
61
|
+
dependencies: {
|
|
62
|
+
"@anthropic-ai/claude-agent-sdk": "^0.2.39",
|
|
63
|
+
"@radix-ui/react-context-menu": "^2.2.16",
|
|
64
|
+
"@radix-ui/react-select": "^2.2.6",
|
|
65
|
+
"@xterm/addon-fit": "^0.11.0",
|
|
66
|
+
"@xterm/addon-serialize": "^0.14.0",
|
|
67
|
+
"@xterm/addon-web-links": "^0.12.0",
|
|
68
|
+
"@xterm/headless": "^6.0.0",
|
|
69
|
+
"@xterm/xterm": "^6.0.0",
|
|
70
|
+
"default-shell": "^2.2.0",
|
|
71
|
+
"puppeteer-core": "^24.40.0",
|
|
72
|
+
"react-resizable-panels": "^4.7.3",
|
|
73
|
+
sonner: "^2.0.7"
|
|
74
|
+
},
|
|
75
|
+
devDependencies: {
|
|
76
|
+
"@dnd-kit/core": "^6.3.1",
|
|
77
|
+
"@dnd-kit/sortable": "^10.0.0",
|
|
78
|
+
"@dnd-kit/utilities": "^3.2.2",
|
|
79
|
+
"@radix-ui/react-dialog": "^1.1.15",
|
|
80
|
+
"@radix-ui/react-popover": "^1.1.15",
|
|
81
|
+
"@radix-ui/react-tooltip": "^1.2.8",
|
|
82
|
+
"@tailwindcss/postcss": "^4.1.18",
|
|
83
|
+
"@tailwindcss/typography": "^0.5.19",
|
|
84
|
+
"@kaizen-core/themes": "workspace:*",
|
|
85
|
+
"@types/bun": "latest",
|
|
86
|
+
"@types/node": "^24.10.1",
|
|
87
|
+
"@types/react": "19.2.7",
|
|
88
|
+
"@types/react-dom": "19.2.3",
|
|
89
|
+
"@vitejs/plugin-react": "5.1.1",
|
|
90
|
+
autoprefixer: "^10.4.23",
|
|
91
|
+
"class-variance-authority": "^0.7.1",
|
|
92
|
+
clsx: "^2.1.1",
|
|
93
|
+
"lucide-react": "^0.562.0",
|
|
94
|
+
react: "19.2.1",
|
|
95
|
+
"react-dom": "19.2.1",
|
|
96
|
+
"react-markdown": "^10.1.0",
|
|
97
|
+
"react-router-dom": "^7.12.0",
|
|
98
|
+
prettier: "^3.6.2",
|
|
99
|
+
"remark-gfm": "^4.0.1",
|
|
100
|
+
"tailwind-merge": "^3.4.0",
|
|
101
|
+
tailwindcss: "^4.1.18",
|
|
102
|
+
typescript: "5.8.3",
|
|
103
|
+
vite: "^6.0.0",
|
|
104
|
+
zustand: "^5.0.10"
|
|
105
|
+
}
|
|
106
|
+
};
|
|
107
|
+
|
|
108
|
+
// src/shared/branding.ts
|
|
109
|
+
var APP_NAME = "Kaizen";
|
|
110
|
+
var CLI_COMMAND = "kaizen";
|
|
111
|
+
var DATA_ROOT_NAME = ".kaizen";
|
|
112
|
+
var DEV_DATA_ROOT_NAME = ".kaizen-dev";
|
|
113
|
+
var PACKAGE_NAME = "kaizenai";
|
|
114
|
+
var PROJECT_METADATA_DIR_NAME = ".kaizen";
|
|
115
|
+
var RUNTIME_PROFILE_ENV_VAR = "KAIZEN_RUNTIME_PROFILE";
|
|
116
|
+
var DISABLE_SELF_UPDATE_ENV_VAR = "KAIZEN_DISABLE_SELF_UPDATE";
|
|
117
|
+
var SDK_CLIENT_APP = `kaizen/${package_default.version}`;
|
|
118
|
+
var LOG_PREFIX = "[kaizen]";
|
|
119
|
+
var DEFAULT_NEW_PROJECT_ROOT = `~/${APP_NAME}`;
|
|
120
|
+
function getRuntimeEnv() {
|
|
121
|
+
const candidate = globalThis;
|
|
122
|
+
return candidate.process?.env;
|
|
123
|
+
}
|
|
124
|
+
function getRuntimeProfile(env = getRuntimeEnv()) {
|
|
125
|
+
const profile = env?.[RUNTIME_PROFILE_ENV_VAR];
|
|
126
|
+
return profile?.trim().toLowerCase() === "dev" ? "dev" : "prod";
|
|
127
|
+
}
|
|
128
|
+
function getDataRootName(env = getRuntimeEnv()) {
|
|
129
|
+
return getRuntimeProfile(env) === "dev" ? DEV_DATA_ROOT_NAME : DATA_ROOT_NAME;
|
|
130
|
+
}
|
|
131
|
+
function getDataRootDir(homeDir, env = getRuntimeEnv()) {
|
|
132
|
+
return `${homeDir}/${getDataRootName(env)}`;
|
|
133
|
+
}
|
|
134
|
+
function getDataRootDirDisplay(env = getRuntimeEnv()) {
|
|
135
|
+
return `~/${getDataRootName(env)}`;
|
|
136
|
+
}
|
|
137
|
+
function getDataDir(homeDir, env = getRuntimeEnv()) {
|
|
138
|
+
return `${getDataRootDir(homeDir, env)}/data`;
|
|
139
|
+
}
|
|
140
|
+
function getDataDirDisplay(env = getRuntimeEnv()) {
|
|
141
|
+
return `${getDataRootDirDisplay(env)}/data`;
|
|
142
|
+
}
|
|
143
|
+
function getKeybindingsFilePath(homeDir, env = getRuntimeEnv()) {
|
|
144
|
+
return `${getDataRootDir(homeDir, env)}/keybindings.json`;
|
|
145
|
+
}
|
|
146
|
+
function getThemeSettingsFilePath(homeDir, env = getRuntimeEnv()) {
|
|
147
|
+
return `${getDataRootDir(homeDir, env)}/theme.json`;
|
|
148
|
+
}
|
|
149
|
+
function getThemesDirPath(homeDir, env = getRuntimeEnv()) {
|
|
150
|
+
return `${getDataRootDir(homeDir, env)}/themes`;
|
|
151
|
+
}
|
|
152
|
+
function getThemesTemplateFilePath(homeDir, env = getRuntimeEnv()) {
|
|
153
|
+
return `${getThemesDirPath(homeDir, env)}/custom-theme.example.json`;
|
|
154
|
+
}
|
|
155
|
+
function getThemesReadmeFilePath(homeDir, env = getRuntimeEnv()) {
|
|
156
|
+
return `${getThemesDirPath(homeDir, env)}/THEME_README.md`;
|
|
157
|
+
}
|
|
158
|
+
function getProviderSettingsFilePath(homeDir, env = getRuntimeEnv()) {
|
|
159
|
+
return `${getDataRootDir(homeDir, env)}/providers.json`;
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
// src/server/restart.ts
|
|
163
|
+
var CLI_CHILD_MODE_ENV_VAR = "KAIZEN_CLI_MODE";
|
|
164
|
+
var CLI_CHILD_MODE = "child";
|
|
165
|
+
var CLI_STARTUP_UPDATE_RESTART_EXIT_CODE = 75;
|
|
166
|
+
var CLI_UI_UPDATE_RESTART_EXIT_CODE = 76;
|
|
167
|
+
var CLI_CHILD_COMMAND_ENV_VAR = "KAIZEN_CLI_CHILD_COMMAND";
|
|
168
|
+
var CLI_CHILD_ARGS_ENV_VAR = "KAIZEN_CLI_CHILD_ARGS";
|
|
169
|
+
var CLI_SUPPRESS_OPEN_ONCE_ENV_VAR = "KAIZEN_SUPPRESS_OPEN_ONCE";
|
|
170
|
+
var CLI_SKIP_STARTUP_UPDATE_ONCE_ENV_VAR = "KAIZEN_SKIP_STARTUP_UPDATE_ONCE";
|
|
171
|
+
var CLI_WEB_ONLY_MODE_ENV_VAR = "KAIZEN_WEB_ONLY_MODE";
|
|
172
|
+
var MAX_UPDATE_RESTART_ATTEMPTS = 5;
|
|
173
|
+
function shouldRestartCliProcess(code, signal) {
|
|
174
|
+
return signal === null && (code === CLI_STARTUP_UPDATE_RESTART_EXIT_CODE || code === CLI_UI_UPDATE_RESTART_EXIT_CODE);
|
|
175
|
+
}
|
|
176
|
+
function isStartupUpdateRestart(code, signal) {
|
|
177
|
+
return signal === null && code === CLI_STARTUP_UPDATE_RESTART_EXIT_CODE;
|
|
178
|
+
}
|
|
179
|
+
function isUiUpdateRestart(code, signal) {
|
|
180
|
+
return signal === null && code === CLI_UI_UPDATE_RESTART_EXIT_CODE;
|
|
181
|
+
}
|
|
182
|
+
function shouldSkipStartupUpdateOnce(value) {
|
|
183
|
+
return value === "1";
|
|
184
|
+
}
|
|
185
|
+
function shouldRunWebOnlyMode(value) {
|
|
186
|
+
return value === "1";
|
|
187
|
+
}
|
|
188
|
+
function isUpdateRestart(code, signal) {
|
|
189
|
+
return isStartupUpdateRestart(code, signal) || isUiUpdateRestart(code, signal);
|
|
190
|
+
}
|
|
191
|
+
function getNextUpdateRestartAttempt(currentAttempt, code, signal) {
|
|
192
|
+
if (!isUpdateRestart(code, signal)) {
|
|
193
|
+
return 0;
|
|
194
|
+
}
|
|
195
|
+
return currentAttempt + 1;
|
|
196
|
+
}
|
|
197
|
+
function shouldStartWebOnlyFallback(updateRestartAttempt) {
|
|
198
|
+
return updateRestartAttempt >= MAX_UPDATE_RESTART_ATTEMPTS;
|
|
199
|
+
}
|
|
200
|
+
function parseChildArgsEnv(value) {
|
|
201
|
+
if (!value)
|
|
202
|
+
return [];
|
|
203
|
+
try {
|
|
204
|
+
const parsed = JSON.parse(value);
|
|
205
|
+
if (!Array.isArray(parsed) || !parsed.every((entry) => typeof entry === "string")) {
|
|
206
|
+
throw new Error("child args must be an array of strings");
|
|
207
|
+
}
|
|
208
|
+
return parsed;
|
|
209
|
+
} catch (error) {
|
|
210
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
211
|
+
throw new Error(`Invalid ${CLI_CHILD_ARGS_ENV_VAR}: ${message}`);
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
// src/server/cli-supervisor.ts
|
|
216
|
+
function getChildProcessSpec(env = process.env) {
|
|
217
|
+
const command = env[CLI_CHILD_COMMAND_ENV_VAR] || CLI_COMMAND;
|
|
218
|
+
const args = parseChildArgsEnv(env[CLI_CHILD_ARGS_ENV_VAR]);
|
|
219
|
+
return { command, args };
|
|
220
|
+
}
|
|
221
|
+
function getFallbackChildProcessSpec() {
|
|
222
|
+
return {
|
|
223
|
+
command: process.execPath,
|
|
224
|
+
args: [fileURLToPath(new URL("./cli.ts", import.meta.url))]
|
|
225
|
+
};
|
|
226
|
+
}
|
|
227
|
+
function createChildEnv(env, options) {
|
|
228
|
+
return {
|
|
229
|
+
...env,
|
|
230
|
+
[CLI_CHILD_MODE_ENV_VAR]: CLI_CHILD_MODE,
|
|
231
|
+
...options.suppressOpen ? { [CLI_SUPPRESS_OPEN_ONCE_ENV_VAR]: "1" } : {},
|
|
232
|
+
...options.skipStartupUpdate ? { [CLI_SKIP_STARTUP_UPDATE_ONCE_ENV_VAR]: "1" } : {},
|
|
233
|
+
...options.webOnlyMode ? { [CLI_WEB_ONLY_MODE_ENV_VAR]: "1" } : {}
|
|
234
|
+
};
|
|
235
|
+
}
|
|
236
|
+
function spawnChild(argv, childProcess, options) {
|
|
237
|
+
const suppressOpenThisChild = suppressOpenOnNextChild;
|
|
238
|
+
const skipStartupUpdateThisChild = skipStartupUpdateOnNextChild;
|
|
239
|
+
suppressOpenOnNextChild = false;
|
|
240
|
+
skipStartupUpdateOnNextChild = false;
|
|
241
|
+
return new Promise((resolve, reject) => {
|
|
242
|
+
const child = spawn(childProcess.command, [...childProcess.args, ...argv], {
|
|
243
|
+
stdio: "inherit",
|
|
244
|
+
env: createChildEnv(process.env, {
|
|
245
|
+
suppressOpen: options.suppressOpen || suppressOpenThisChild,
|
|
246
|
+
skipStartupUpdate: options.skipStartupUpdate || skipStartupUpdateThisChild,
|
|
247
|
+
webOnlyMode: options.webOnlyMode
|
|
248
|
+
})
|
|
249
|
+
});
|
|
250
|
+
const forwardSignal = (signal) => {
|
|
251
|
+
if (child.exitCode !== null)
|
|
252
|
+
return;
|
|
253
|
+
child.kill(signal);
|
|
254
|
+
};
|
|
255
|
+
const onSigint = () => {
|
|
256
|
+
forwardSignal("SIGINT");
|
|
257
|
+
};
|
|
258
|
+
const onSigterm = () => {
|
|
259
|
+
forwardSignal("SIGTERM");
|
|
260
|
+
};
|
|
261
|
+
process.on("SIGINT", onSigint);
|
|
262
|
+
process.on("SIGTERM", onSigterm);
|
|
263
|
+
child.once("error", (error) => {
|
|
264
|
+
process.off("SIGINT", onSigint);
|
|
265
|
+
process.off("SIGTERM", onSigterm);
|
|
266
|
+
reject(error);
|
|
267
|
+
});
|
|
268
|
+
child.once("exit", (code, signal) => {
|
|
269
|
+
process.off("SIGINT", onSigint);
|
|
270
|
+
process.off("SIGTERM", onSigterm);
|
|
271
|
+
resolve({ code, signal });
|
|
272
|
+
});
|
|
273
|
+
});
|
|
274
|
+
}
|
|
275
|
+
var argv = process.argv.slice(2);
|
|
276
|
+
var suppressOpenOnNextChild = false;
|
|
277
|
+
var skipStartupUpdateOnNextChild = false;
|
|
278
|
+
var updateRestartAttempt = 0;
|
|
279
|
+
var childProcess = getChildProcessSpec();
|
|
280
|
+
while (true) {
|
|
281
|
+
const result = await spawnChild(argv, childProcess, {
|
|
282
|
+
suppressOpen: false,
|
|
283
|
+
skipStartupUpdate: false,
|
|
284
|
+
webOnlyMode: shouldRunWebOnlyMode(process.env[CLI_WEB_ONLY_MODE_ENV_VAR])
|
|
285
|
+
});
|
|
286
|
+
updateRestartAttempt = getNextUpdateRestartAttempt(updateRestartAttempt, result.code, result.signal);
|
|
287
|
+
if (shouldRestartCliProcess(result.code, result.signal)) {
|
|
288
|
+
if (shouldStartWebOnlyFallback(updateRestartAttempt)) {
|
|
289
|
+
console.error(`${LOG_PREFIX} update restart failed ${String(updateRestartAttempt)} times; starting web-only fallback`);
|
|
290
|
+
childProcess = getFallbackChildProcessSpec();
|
|
291
|
+
process.env[CLI_WEB_ONLY_MODE_ENV_VAR] = "1";
|
|
292
|
+
suppressOpenOnNextChild = isUiUpdateRestart(result.code, result.signal);
|
|
293
|
+
skipStartupUpdateOnNextChild = true;
|
|
294
|
+
updateRestartAttempt = 0;
|
|
295
|
+
continue;
|
|
296
|
+
}
|
|
297
|
+
suppressOpenOnNextChild = isUiUpdateRestart(result.code, result.signal);
|
|
298
|
+
skipStartupUpdateOnNextChild = isStartupUpdateRestart(result.code, result.signal);
|
|
299
|
+
console.log(`${LOG_PREFIX} supervisor restarting ${CLI_COMMAND} in the same terminal session`);
|
|
300
|
+
continue;
|
|
301
|
+
}
|
|
302
|
+
process.exit(result.code ?? (result.signal ? 1 : 0));
|
|
303
|
+
}
|
|
304
|
+
export {
|
|
305
|
+
getChildProcessSpec,
|
|
306
|
+
createChildEnv
|
|
307
|
+
};
|