botmux 2.114.0 → 3.1.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/dist/adapters/backend/herdr-backend.d.ts +9 -7
- package/dist/adapters/backend/herdr-backend.d.ts.map +1 -1
- package/dist/adapters/backend/herdr-backend.js +63 -53
- package/dist/adapters/backend/herdr-backend.js.map +1 -1
- package/dist/adapters/backend/riff-backend.d.ts +21 -1
- package/dist/adapters/backend/riff-backend.d.ts.map +1 -1
- package/dist/adapters/backend/riff-backend.js +16 -5
- package/dist/adapters/backend/riff-backend.js.map +1 -1
- package/dist/adapters/backend/sandbox.d.ts +20 -16
- package/dist/adapters/backend/sandbox.d.ts.map +1 -1
- package/dist/adapters/backend/sandbox.js +192 -65
- package/dist/adapters/backend/sandbox.js.map +1 -1
- package/dist/adapters/backend/tmux-backend.d.ts +39 -2
- package/dist/adapters/backend/tmux-backend.d.ts.map +1 -1
- package/dist/adapters/backend/tmux-backend.js +55 -5
- package/dist/adapters/backend/tmux-backend.js.map +1 -1
- package/dist/adapters/backend/tmux-pipe-backend.js +2 -2
- package/dist/adapters/backend/tmux-pipe-backend.js.map +1 -1
- package/dist/adapters/backend/zellij-backend.d.ts.map +1 -1
- package/dist/adapters/backend/zellij-backend.js +9 -3
- package/dist/adapters/backend/zellij-backend.js.map +1 -1
- package/dist/adapters/cli/claude-code.d.ts +25 -0
- package/dist/adapters/cli/claude-code.d.ts.map +1 -1
- package/dist/adapters/cli/claude-code.js +79 -9
- package/dist/adapters/cli/claude-code.js.map +1 -1
- package/dist/adapters/cli/read-isolation.d.ts +2 -1
- package/dist/adapters/cli/read-isolation.d.ts.map +1 -1
- package/dist/adapters/cli/read-isolation.js.map +1 -1
- package/dist/adapters/cli/types.d.ts +2 -2
- package/dist/adapters/hook-installer.d.ts +11 -0
- package/dist/adapters/hook-installer.d.ts.map +1 -1
- package/dist/adapters/hook-installer.js +72 -11
- package/dist/adapters/hook-installer.js.map +1 -1
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +15 -4
- package/dist/cli.js.map +1 -1
- package/dist/config.d.ts +6 -0
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +18 -0
- package/dist/config.js.map +1 -1
- package/dist/core/command-handler.d.ts.map +1 -1
- package/dist/core/command-handler.js +211 -57
- package/dist/core/command-handler.js.map +1 -1
- package/dist/core/dashboard-ipc-server.d.ts.map +1 -1
- package/dist/core/dashboard-ipc-server.js +13 -6
- package/dist/core/dashboard-ipc-server.js.map +1 -1
- package/dist/core/dashboard-rows.d.ts +5 -0
- package/dist/core/dashboard-rows.d.ts.map +1 -1
- package/dist/core/dashboard-rows.js +2 -0
- package/dist/core/dashboard-rows.js.map +1 -1
- package/dist/core/doc-comment-prompt.d.ts +2 -0
- package/dist/core/doc-comment-prompt.d.ts.map +1 -1
- package/dist/core/doc-comment-prompt.js +30 -0
- package/dist/core/doc-comment-prompt.js.map +1 -1
- package/dist/core/github-auth.d.ts +8 -0
- package/dist/core/github-auth.d.ts.map +1 -0
- package/dist/core/github-auth.js +44 -0
- package/dist/core/github-auth.js.map +1 -0
- package/dist/core/managed-origin-capability.d.ts +7 -0
- package/dist/core/managed-origin-capability.d.ts.map +1 -1
- package/dist/core/managed-origin-capability.js +12 -0
- package/dist/core/managed-origin-capability.js.map +1 -1
- package/dist/core/passthrough-commands.d.ts.map +1 -1
- package/dist/core/passthrough-commands.js +1 -1
- package/dist/core/passthrough-commands.js.map +1 -1
- package/dist/core/restart-report.d.ts +7 -1
- package/dist/core/restart-report.d.ts.map +1 -1
- package/dist/core/restart-report.js +19 -5
- package/dist/core/restart-report.js.map +1 -1
- package/dist/core/session-activity.d.ts +8 -0
- package/dist/core/session-activity.d.ts.map +1 -1
- package/dist/core/session-activity.js +16 -0
- package/dist/core/session-activity.js.map +1 -1
- package/dist/core/session-discovery.d.ts.map +1 -1
- package/dist/core/session-discovery.js +4 -2
- package/dist/core/session-discovery.js.map +1 -1
- package/dist/core/update-check.d.ts +11 -0
- package/dist/core/update-check.d.ts.map +1 -1
- package/dist/core/update-check.js +6 -1
- package/dist/core/update-check.js.map +1 -1
- package/dist/core/vc-meeting-prepare-command.d.ts +22 -0
- package/dist/core/vc-meeting-prepare-command.d.ts.map +1 -0
- package/dist/core/vc-meeting-prepare-command.js +50 -0
- package/dist/core/vc-meeting-prepare-command.js.map +1 -0
- package/dist/core/worker-pool.d.ts.map +1 -1
- package/dist/core/worker-pool.js +11 -2
- package/dist/core/worker-pool.js.map +1 -1
- package/dist/daemon.d.ts +15 -5
- package/dist/daemon.d.ts.map +1 -1
- package/dist/daemon.js +555 -41
- package/dist/daemon.js.map +1 -1
- package/dist/dashboard/compat.d.ts +19 -0
- package/dist/dashboard/compat.d.ts.map +1 -0
- package/dist/dashboard/compat.js +38 -0
- package/dist/dashboard/compat.js.map +1 -0
- package/dist/dashboard/stale-chunk-module.d.ts +3 -0
- package/dist/dashboard/stale-chunk-module.d.ts.map +1 -0
- package/dist/dashboard/stale-chunk-module.js +55 -0
- package/dist/dashboard/stale-chunk-module.js.map +1 -0
- package/dist/dashboard/web/app.d.ts.map +1 -1
- package/dist/dashboard/web/app.js +64 -2
- package/dist/dashboard/web/app.js.map +1 -1
- package/dist/dashboard/web/bot-defaults-page.d.ts.map +1 -1
- package/dist/dashboard/web/bot-defaults-page.js +14 -7
- package/dist/dashboard/web/bot-defaults-page.js.map +1 -1
- package/dist/dashboard/web/i18n.d.ts.map +1 -1
- package/dist/dashboard/web/i18n.js +44 -10
- package/dist/dashboard/web/i18n.js.map +1 -1
- package/dist/dashboard/web/preferences.d.ts +1 -1
- package/dist/dashboard/web/preferences.d.ts.map +1 -1
- package/dist/dashboard/web/preferences.js +1 -1
- package/dist/dashboard/web/preferences.js.map +1 -1
- package/dist/dashboard/web/sessions-page.d.ts +19 -0
- package/dist/dashboard/web/sessions-page.d.ts.map +1 -1
- package/dist/dashboard/web/sessions-page.js +68 -9
- package/dist/dashboard/web/sessions-page.js.map +1 -1
- package/dist/dashboard/web/sessions.d.ts +31 -0
- package/dist/dashboard/web/sessions.d.ts.map +1 -1
- package/dist/dashboard/web/sessions.js +82 -0
- package/dist/dashboard/web/sessions.js.map +1 -1
- package/dist/dashboard/web/stale-chunk-reload.d.ts +16 -0
- package/dist/dashboard/web/stale-chunk-reload.d.ts.map +1 -0
- package/dist/dashboard/web/stale-chunk-reload.js +51 -0
- package/dist/dashboard/web/stale-chunk-reload.js.map +1 -0
- package/dist/dashboard-web/app.js +1 -1
- package/dist/dashboard-web/chunks/{bot-defaults-page-SRCBF7Z3.js → bot-defaults-page-KLDCZNLP.js} +5 -5
- package/dist/dashboard-web/chunks/{chunk-NGRUZCXP.js → chunk-EZAW2EPM.js} +1 -1
- package/dist/dashboard-web/chunks/{chunk-D2I5F4MY.js → chunk-FMJNOATE.js} +1 -1
- package/dist/dashboard-web/chunks/{chunk-3H6MVXXU.js → chunk-KEAOTUL3.js} +7 -7
- package/dist/dashboard-web/chunks/{chunk-77KD4TK2.js → chunk-MLNI5BKE.js} +1 -1
- package/dist/dashboard-web/chunks/{connectors-page-RM3BJVMV.js → connectors-page-O32LFAL5.js} +1 -1
- package/dist/dashboard-web/chunks/{groups-page-3D4YSYLA.js → groups-page-PSAFIZ6M.js} +1 -1
- package/dist/dashboard-web/chunks/{insights-page-CRFJKA54.js → insights-page-V23LLATX.js} +1 -1
- package/dist/dashboard-web/chunks/{monitor-room-HLK3XDT2.js → monitor-room-7X5AKYOF.js} +1 -1
- package/dist/dashboard-web/chunks/{monitoring-page-E3SNZFFN.js → monitoring-page-CBA3CQYL.js} +1 -1
- package/dist/dashboard-web/chunks/{office-page-MKQ2TENK.js → office-page-RL6QSEM7.js} +1 -1
- package/dist/dashboard-web/chunks/{overview-page-ICFKKRLV.js → overview-page-XQIPO6KH.js} +1 -1
- package/dist/dashboard-web/chunks/{roles-page-2DFJ7YRU.js → roles-page-ACIWV7QS.js} +1 -1
- package/dist/dashboard-web/chunks/{schedules-page-S4WDIXH5.js → schedules-page-KJDUKOJV.js} +1 -1
- package/dist/dashboard-web/chunks/sessions-page-2WDWHSP4.js +3 -0
- package/dist/dashboard-web/chunks/{settings-page-OBTE4LYP.js → settings-page-6VX4OUGG.js} +1 -1
- package/dist/dashboard-web/chunks/{skills-page-CTRQJR47.js → skills-page-WXE3UYLT.js} +1 -1
- package/dist/dashboard-web/chunks/{team-federation-page-GICLDKJP.js → team-federation-page-PYTF4FLM.js} +1 -1
- package/dist/dashboard-web/chunks/{v3-page-DI55IRL5.js → v3-page-G6CD6O3I.js} +1 -1
- package/dist/dashboard-web/chunks/{whiteboards-page-7KFWMILV.js → whiteboards-page-6SG33GP4.js} +1 -1
- package/dist/dashboard-web/style.css +167 -2
- package/dist/dashboard.js +26 -0
- package/dist/dashboard.js.map +1 -1
- package/dist/desktop/main/auto-start.d.ts +17 -0
- package/dist/desktop/main/auto-start.d.ts.map +1 -0
- package/dist/desktop/main/auto-start.js +37 -0
- package/dist/desktop/main/auto-start.js.map +1 -0
- package/dist/desktop/main/dashboard-compat.d.ts +25 -0
- package/dist/desktop/main/dashboard-compat.d.ts.map +1 -0
- package/dist/desktop/main/dashboard-compat.js +117 -0
- package/dist/desktop/main/dashboard-compat.js.map +1 -0
- package/dist/desktop/main/external-runtime.d.ts +29 -0
- package/dist/desktop/main/external-runtime.d.ts.map +1 -0
- package/dist/desktop/main/external-runtime.js +202 -0
- package/dist/desktop/main/external-runtime.js.map +1 -0
- package/dist/desktop/main/ipc.d.ts +20 -0
- package/dist/desktop/main/ipc.d.ts.map +1 -0
- package/dist/desktop/main/ipc.js +241 -0
- package/dist/desktop/main/ipc.js.map +1 -0
- package/dist/desktop/main/log-service.d.ts +4 -0
- package/dist/desktop/main/log-service.d.ts.map +1 -0
- package/dist/desktop/main/log-service.js +53 -0
- package/dist/desktop/main/log-service.js.map +1 -0
- package/dist/desktop/main/login-item.d.ts +10 -0
- package/dist/desktop/main/login-item.d.ts.map +1 -0
- package/dist/desktop/main/login-item.js +11 -0
- package/dist/desktop/main/login-item.js.map +1 -0
- package/dist/desktop/main/node-command.d.ts +22 -0
- package/dist/desktop/main/node-command.d.ts.map +1 -0
- package/dist/desktop/main/node-command.js +56 -0
- package/dist/desktop/main/node-command.js.map +1 -0
- package/dist/desktop/main/paths.d.ts +11 -0
- package/dist/desktop/main/paths.d.ts.map +1 -0
- package/dist/desktop/main/paths.js +13 -0
- package/dist/desktop/main/paths.js.map +1 -0
- package/dist/desktop/main/pm2-apps.d.ts +15 -0
- package/dist/desktop/main/pm2-apps.d.ts.map +1 -0
- package/dist/desktop/main/pm2-apps.js +97 -0
- package/dist/desktop/main/pm2-apps.js.map +1 -0
- package/dist/desktop/main/runtime-service.d.ts +49 -0
- package/dist/desktop/main/runtime-service.d.ts.map +1 -0
- package/dist/desktop/main/runtime-service.js +297 -0
- package/dist/desktop/main/runtime-service.js.map +1 -0
- package/dist/desktop/main/runtime-source.d.ts +17 -0
- package/dist/desktop/main/runtime-source.d.ts.map +1 -0
- package/dist/desktop/main/runtime-source.js +61 -0
- package/dist/desktop/main/runtime-source.js.map +1 -0
- package/dist/desktop/main/tray.d.ts +10 -0
- package/dist/desktop/main/tray.d.ts.map +1 -0
- package/dist/desktop/main/tray.js +27 -0
- package/dist/desktop/main/tray.js.map +1 -0
- package/dist/desktop/main/window.d.ts +16 -0
- package/dist/desktop/main/window.d.ts.map +1 -0
- package/dist/desktop/main/window.js +113 -0
- package/dist/desktop/main/window.js.map +1 -0
- package/dist/desktop/main.d.ts +2 -0
- package/dist/desktop/main.d.ts.map +1 -0
- package/dist/desktop/main.js +175 -0
- package/dist/desktop/main.js.map +1 -0
- package/dist/desktop/preload.d.ts +2 -0
- package/dist/desktop/preload.d.ts.map +1 -0
- package/dist/desktop/preload.js +24 -0
- package/dist/desktop/preload.js.map +1 -0
- package/dist/desktop/renderer/app.d.ts +35 -0
- package/dist/desktop/renderer/app.d.ts.map +1 -0
- package/dist/desktop/renderer/app.js +945 -0
- package/dist/desktop/renderer/app.js.map +1 -0
- package/dist/desktop/renderer/dashboard-url.d.ts +13 -0
- package/dist/desktop/renderer/dashboard-url.d.ts.map +1 -0
- package/dist/desktop/renderer/dashboard-url.js +98 -0
- package/dist/desktop/renderer/dashboard-url.js.map +1 -0
- package/dist/desktop/renderer/runtime-state.d.ts +8 -0
- package/dist/desktop/renderer/runtime-state.d.ts.map +1 -0
- package/dist/desktop/renderer/runtime-state.js +67 -0
- package/dist/desktop/renderer/runtime-state.js.map +1 -0
- package/dist/desktop/shared/types.d.ts +48 -0
- package/dist/desktop/shared/types.d.ts.map +1 -0
- package/dist/desktop/shared/types.js +2 -0
- package/dist/desktop/shared/types.js.map +1 -0
- package/dist/desktop/smoke.d.ts +28 -0
- package/dist/desktop/smoke.d.ts.map +1 -0
- package/dist/desktop/smoke.js +258 -0
- package/dist/desktop/smoke.js.map +1 -0
- package/dist/i18n/en.d.ts.map +1 -1
- package/dist/i18n/en.js +18 -3
- package/dist/i18n/en.js.map +1 -1
- package/dist/i18n/zh.d.ts.map +1 -1
- package/dist/i18n/zh.js +18 -3
- package/dist/i18n/zh.js.map +1 -1
- package/dist/im/lark/card-builder.d.ts.map +1 -1
- package/dist/im/lark/card-builder.js +11 -2
- package/dist/im/lark/card-builder.js.map +1 -1
- package/dist/im/lark/event-dispatcher.d.ts +4 -0
- package/dist/im/lark/event-dispatcher.d.ts.map +1 -1
- package/dist/im/lark/event-dispatcher.js +249 -5
- package/dist/im/lark/event-dispatcher.js.map +1 -1
- package/dist/im/lark/forward-followup-buffer.d.ts +26 -0
- package/dist/im/lark/forward-followup-buffer.d.ts.map +1 -0
- package/dist/im/lark/forward-followup-buffer.js +48 -0
- package/dist/im/lark/forward-followup-buffer.js.map +1 -0
- package/dist/im/lark/forward-followup-content.d.ts +6 -0
- package/dist/im/lark/forward-followup-content.d.ts.map +1 -0
- package/dist/im/lark/forward-followup-content.js +46 -0
- package/dist/im/lark/forward-followup-content.js.map +1 -0
- package/dist/im/lark/forward-followup-store.d.ts +9 -0
- package/dist/im/lark/forward-followup-store.d.ts.map +1 -0
- package/dist/im/lark/forward-followup-store.js +48 -0
- package/dist/im/lark/forward-followup-store.js.map +1 -0
- package/dist/im/lark/message-parser.d.ts +1 -1
- package/dist/im/lark/message-parser.d.ts.map +1 -1
- package/dist/im/lark/message-parser.js +1 -2
- package/dist/im/lark/message-parser.js.map +1 -1
- package/dist/platform/tunnel-client.js +3 -3
- package/dist/platform/tunnel-client.js.map +1 -1
- package/dist/services/local-cli-opener.d.ts +7 -0
- package/dist/services/local-cli-opener.d.ts.map +1 -1
- package/dist/services/local-cli-opener.js +111 -3
- package/dist/services/local-cli-opener.js.map +1 -1
- package/dist/services/skill-registry-store.d.ts.map +1 -1
- package/dist/services/skill-registry-store.js +15 -2
- package/dist/services/skill-registry-store.js.map +1 -1
- package/dist/services/vc-meeting-consumer-isolation.d.ts +7 -5
- package/dist/services/vc-meeting-consumer-isolation.d.ts.map +1 -1
- package/dist/services/vc-meeting-consumer-isolation.js +7 -5
- package/dist/services/vc-meeting-consumer-isolation.js.map +1 -1
- package/dist/services/vc-meeting-preparations-store.d.ts +22 -0
- package/dist/services/vc-meeting-preparations-store.d.ts.map +1 -0
- package/dist/services/vc-meeting-preparations-store.js +131 -0
- package/dist/services/vc-meeting-preparations-store.js.map +1 -0
- package/dist/services/vc-meeting-runtime-store.d.ts +9 -0
- package/dist/services/vc-meeting-runtime-store.d.ts.map +1 -1
- package/dist/services/vc-meeting-runtime-store.js +16 -0
- package/dist/services/vc-meeting-runtime-store.js.map +1 -1
- package/dist/setup/ensure-tmux.d.ts.map +1 -1
- package/dist/setup/ensure-tmux.js +9 -11
- package/dist/setup/ensure-tmux.js.map +1 -1
- package/dist/utils/child-env.d.ts +16 -8
- package/dist/utils/child-env.d.ts.map +1 -1
- package/dist/utils/child-env.js +30 -8
- package/dist/utils/child-env.js.map +1 -1
- package/dist/utils/daemon-discovery.d.ts +8 -0
- package/dist/utils/daemon-discovery.d.ts.map +1 -1
- package/dist/utils/daemon-discovery.js +19 -0
- package/dist/utils/daemon-discovery.js.map +1 -1
- package/dist/utils/ready-gate.d.ts +9 -3
- package/dist/utils/ready-gate.d.ts.map +1 -1
- package/dist/utils/ready-gate.js +12 -4
- package/dist/utils/ready-gate.js.map +1 -1
- package/dist/utils/version-info.d.ts +25 -0
- package/dist/utils/version-info.d.ts.map +1 -0
- package/dist/utils/version-info.js +48 -0
- package/dist/utils/version-info.js.map +1 -0
- package/dist/worker.js +131 -28
- package/dist/worker.js.map +1 -1
- package/dist/workflows/ops-projection.d.ts.map +1 -1
- package/dist/workflows/ops-projection.js +27 -5
- package/dist/workflows/ops-projection.js.map +1 -1
- package/dist/workflows/v3/distillation-runner.d.ts +4 -0
- package/dist/workflows/v3/distillation-runner.d.ts.map +1 -1
- package/dist/workflows/v3/distillation-runner.js +4 -2
- package/dist/workflows/v3/distillation-runner.js.map +1 -1
- package/package.json +9 -1
- package/dist/dashboard-web/chunks/sessions-page-4XWGUGB5.js +0 -3
|
@@ -0,0 +1,241 @@
|
|
|
1
|
+
import { app, ipcMain, shell } from 'electron';
|
|
2
|
+
import { closeSync, existsSync, openSync, readSync, readdirSync, statSync } from 'node:fs';
|
|
3
|
+
import { homedir } from 'node:os';
|
|
4
|
+
import { detectLegacyAutostart } from './login-item.js';
|
|
5
|
+
import { listLogTargets, tailLogText } from './log-service.js';
|
|
6
|
+
import { validateDashboardCompat } from './dashboard-compat.js';
|
|
7
|
+
export function registerDesktopIpc(args) {
|
|
8
|
+
// Keep the renderer's surface area narrow: every filesystem/process action
|
|
9
|
+
// must go through an explicit handler here.
|
|
10
|
+
ipcMain.handle('desktop:get-state', () => args.runtime.getState());
|
|
11
|
+
ipcMain.handle('desktop:start', () => runRuntimeAction(args.runtime.start, args.monitor));
|
|
12
|
+
ipcMain.handle('desktop:stop', () => runRuntimeAction(args.runtime.stop, args.monitor));
|
|
13
|
+
ipcMain.handle('desktop:restart', () => runRuntimeAction(args.runtime.restart, args.monitor));
|
|
14
|
+
ipcMain.handle('desktop:takeover', () => runRuntimeAction(args.runtime.takeover.bind(args.runtime), args.monitor));
|
|
15
|
+
ipcMain.handle('desktop:locate-dashboard', () => locateDashboard(args.runtime));
|
|
16
|
+
ipcMain.handle('desktop:get-dashboard-url', async () => {
|
|
17
|
+
const result = await args.runtime.dashboard();
|
|
18
|
+
return result.code === 0 ? selectDesktopDashboardUrl(result.stdout) : null;
|
|
19
|
+
});
|
|
20
|
+
ipcMain.handle('desktop:list-log-targets', () => listTargets(args.paths));
|
|
21
|
+
ipcMain.handle('desktop:tail-logs', (_event, targetId) => {
|
|
22
|
+
// targetId is selected from a generated list, but validate again at the IPC
|
|
23
|
+
// boundary because renderer state is not trusted.
|
|
24
|
+
if (typeof targetId !== 'string')
|
|
25
|
+
return { targetId: '', text: '', truncated: false };
|
|
26
|
+
const target = listTargets(args.paths).find(candidate => candidate.id === targetId);
|
|
27
|
+
if (!target)
|
|
28
|
+
return { targetId, text: '', truncated: false };
|
|
29
|
+
const text = target.files
|
|
30
|
+
.flatMap(file => {
|
|
31
|
+
try {
|
|
32
|
+
return [`==> ${file}\n${readFileTail(file, 200_000)}`];
|
|
33
|
+
}
|
|
34
|
+
catch {
|
|
35
|
+
return [];
|
|
36
|
+
}
|
|
37
|
+
})
|
|
38
|
+
.join('\n');
|
|
39
|
+
return { ...tailLogText(text, 200_000), targetId };
|
|
40
|
+
});
|
|
41
|
+
ipcMain.handle('desktop:open-logs-dir', () => shell.openPath(args.paths.logsDir));
|
|
42
|
+
ipcMain.handle('desktop:open-botmux-home', () => shell.openPath(args.paths.botmuxHome));
|
|
43
|
+
ipcMain.handle('desktop:get-login-item', () => getLoginItemState());
|
|
44
|
+
ipcMain.handle('desktop:set-login-item', (_event, enabled) => {
|
|
45
|
+
if (typeof enabled !== 'boolean')
|
|
46
|
+
throw new Error('desktop:set-login-item expects a boolean');
|
|
47
|
+
app.setLoginItemSettings({ openAtLogin: enabled, openAsHidden: true });
|
|
48
|
+
return getLoginItemState();
|
|
49
|
+
});
|
|
50
|
+
}
|
|
51
|
+
export function createRuntimeStateMonitor(args) {
|
|
52
|
+
const intervalMs = args.intervalMs ?? 5000;
|
|
53
|
+
let timer = null;
|
|
54
|
+
let inFlight = null;
|
|
55
|
+
async function refresh() {
|
|
56
|
+
if (inFlight)
|
|
57
|
+
return inFlight;
|
|
58
|
+
inFlight = (async () => {
|
|
59
|
+
try {
|
|
60
|
+
const state = await args.runtime.getState();
|
|
61
|
+
// Push complete state snapshots; the renderer validates the IPC payload
|
|
62
|
+
// before trusting it to drive controls or dashboard navigation.
|
|
63
|
+
args.sendState(state);
|
|
64
|
+
}
|
|
65
|
+
catch (error) {
|
|
66
|
+
console.warn('[desktop] runtime state refresh failed', error);
|
|
67
|
+
}
|
|
68
|
+
finally {
|
|
69
|
+
inFlight = null;
|
|
70
|
+
}
|
|
71
|
+
})();
|
|
72
|
+
return inFlight;
|
|
73
|
+
}
|
|
74
|
+
return {
|
|
75
|
+
start() {
|
|
76
|
+
if (timer)
|
|
77
|
+
return;
|
|
78
|
+
void refresh();
|
|
79
|
+
timer = setInterval(() => {
|
|
80
|
+
void refresh();
|
|
81
|
+
}, intervalMs);
|
|
82
|
+
},
|
|
83
|
+
stop() {
|
|
84
|
+
if (!timer)
|
|
85
|
+
return;
|
|
86
|
+
clearInterval(timer);
|
|
87
|
+
timer = null;
|
|
88
|
+
},
|
|
89
|
+
refresh,
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
async function runRuntimeAction(action, monitor) {
|
|
93
|
+
const result = await action();
|
|
94
|
+
// Action output returns immediately; the monitor refresh runs beside it so a
|
|
95
|
+
// slow PM2/dashboard status path cannot keep renderer buttons disabled.
|
|
96
|
+
void monitor?.refresh();
|
|
97
|
+
return result;
|
|
98
|
+
}
|
|
99
|
+
async function locateDashboard(runtime) {
|
|
100
|
+
const state = await runtime.getState();
|
|
101
|
+
if (state.status !== 'running') {
|
|
102
|
+
const message = state.message ?? 'Runtime is not running';
|
|
103
|
+
const reason = state.status === 'degraded' ? classifyDashboardLocateFailure(message) : 'not_running';
|
|
104
|
+
return {
|
|
105
|
+
ok: false,
|
|
106
|
+
reason: reason === 'unknown' ? 'not_running' : reason,
|
|
107
|
+
message,
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
const current = await runtime.currentDashboard();
|
|
111
|
+
const currentUrl = current.code === 0 ? selectDesktopDashboardUrl(current.stdout) : '';
|
|
112
|
+
if (currentUrl)
|
|
113
|
+
return validateLocatedDashboard(currentUrl, 'current');
|
|
114
|
+
if (!isNoActiveDashboardToken(current)) {
|
|
115
|
+
const message = current.stderr.trim() || current.stdout.trim() || `Dashboard lookup failed with exit code ${current.code}`;
|
|
116
|
+
return {
|
|
117
|
+
ok: false,
|
|
118
|
+
reason: classifyDashboardLocateFailure(message),
|
|
119
|
+
message,
|
|
120
|
+
};
|
|
121
|
+
}
|
|
122
|
+
const result = await runtime.dashboard();
|
|
123
|
+
const url = result.code === 0 ? selectDesktopDashboardUrl(result.stdout) : '';
|
|
124
|
+
if (url) {
|
|
125
|
+
return validateLocatedDashboard(url, 'rotated');
|
|
126
|
+
}
|
|
127
|
+
const message = result.stderr.trim() || result.stdout.trim() || `Dashboard lookup failed with exit code ${result.code}`;
|
|
128
|
+
return {
|
|
129
|
+
ok: false,
|
|
130
|
+
reason: classifyDashboardLocateFailure(message),
|
|
131
|
+
message,
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
function selectDesktopDashboardUrl(output) {
|
|
135
|
+
const urls = extractHttpUrls(output);
|
|
136
|
+
if (urls.length === 0)
|
|
137
|
+
return output.trim();
|
|
138
|
+
return urls.find(isLocalDashboardUrl) ?? urls[0] ?? output.trim();
|
|
139
|
+
}
|
|
140
|
+
function extractHttpUrls(output) {
|
|
141
|
+
return output
|
|
142
|
+
.split(/\r?\n/)
|
|
143
|
+
.flatMap(line => [...line.matchAll(/https?:\/\/[^\s]+/g)].map(match => trimUrlSuffix(match[0])))
|
|
144
|
+
.filter(Boolean);
|
|
145
|
+
}
|
|
146
|
+
function trimUrlSuffix(url) {
|
|
147
|
+
return url.replace(/[),.;,。;)]+$/u, '');
|
|
148
|
+
}
|
|
149
|
+
function isLocalDashboardUrl(url) {
|
|
150
|
+
try {
|
|
151
|
+
const host = new URL(url).hostname.toLowerCase();
|
|
152
|
+
return host === 'localhost'
|
|
153
|
+
|| host === '127.0.0.1'
|
|
154
|
+
|| host === '[::1]'
|
|
155
|
+
|| isPrivateIpv4(host);
|
|
156
|
+
}
|
|
157
|
+
catch {
|
|
158
|
+
return false;
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
function isPrivateIpv4(host) {
|
|
162
|
+
const parts = host.split('.').map(part => Number(part));
|
|
163
|
+
if (parts.length !== 4 || parts.some(part => !Number.isInteger(part) || part < 0 || part > 255))
|
|
164
|
+
return false;
|
|
165
|
+
const [a, b] = parts;
|
|
166
|
+
return a === 10 || (a === 172 && b >= 16 && b <= 31) || (a === 192 && b === 168);
|
|
167
|
+
}
|
|
168
|
+
async function validateLocatedDashboard(url, source) {
|
|
169
|
+
const compat = await validateDashboardCompat(url);
|
|
170
|
+
if (!compat.ok) {
|
|
171
|
+
return {
|
|
172
|
+
ok: false,
|
|
173
|
+
reason: compat.reason,
|
|
174
|
+
message: compat.message,
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
return { ok: true, url, source };
|
|
178
|
+
}
|
|
179
|
+
function isNoActiveDashboardToken(result) {
|
|
180
|
+
const message = `${result.stderr}\n${result.stdout}`.toLowerCase();
|
|
181
|
+
return message.includes('no-active-token') || message.includes('no_active_token');
|
|
182
|
+
}
|
|
183
|
+
function classifyDashboardLocateFailure(message) {
|
|
184
|
+
const normalized = message.toLowerCase();
|
|
185
|
+
if (normalized.includes('src/desktop/install-local.sh') ||
|
|
186
|
+
normalized.includes('desktop 兼容') ||
|
|
187
|
+
normalized.includes('兼容'))
|
|
188
|
+
return 'incompatible';
|
|
189
|
+
if (normalized.includes('no-secret') || normalized.includes('.dashboard-secret') || normalized.includes('not initialised')) {
|
|
190
|
+
return 'no_secret';
|
|
191
|
+
}
|
|
192
|
+
if (normalized.includes('wrong-service') || normalized.includes('不是 dashboard') || normalized.includes('not dashboard')) {
|
|
193
|
+
return 'wrong_service';
|
|
194
|
+
}
|
|
195
|
+
if (normalized.includes('unreachable') ||
|
|
196
|
+
normalized.includes('not reachable') ||
|
|
197
|
+
normalized.includes('econnrefused') ||
|
|
198
|
+
normalized.includes('timed out')) {
|
|
199
|
+
return 'unreachable';
|
|
200
|
+
}
|
|
201
|
+
return 'unknown';
|
|
202
|
+
}
|
|
203
|
+
function listTargets(paths) {
|
|
204
|
+
if (!existsSync(paths.logsDir))
|
|
205
|
+
return listLogTargets(paths.logsDir, []);
|
|
206
|
+
try {
|
|
207
|
+
const filenames = readdirSync(paths.logsDir, { withFileTypes: true })
|
|
208
|
+
.filter(entry => entry.isFile())
|
|
209
|
+
.map(entry => entry.name);
|
|
210
|
+
return listLogTargets(paths.logsDir, filenames);
|
|
211
|
+
}
|
|
212
|
+
catch {
|
|
213
|
+
return listLogTargets(paths.logsDir, []);
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
function getLoginItemState() {
|
|
217
|
+
return {
|
|
218
|
+
openAtLogin: app.getLoginItemSettings().openAtLogin,
|
|
219
|
+
...detectLegacyAutostart({ homeDir: homedir(), existsSync }),
|
|
220
|
+
};
|
|
221
|
+
}
|
|
222
|
+
function readFileTail(file, maxBytes) {
|
|
223
|
+
const size = statSync(file).size;
|
|
224
|
+
const length = Math.min(size, maxBytes);
|
|
225
|
+
const fd = openSync(file, 'r');
|
|
226
|
+
try {
|
|
227
|
+
// Read from the end of the file to keep large daemon logs responsive.
|
|
228
|
+
const buffer = Buffer.alloc(length);
|
|
229
|
+
const bytesRead = readSync(fd, buffer, 0, length, size - length);
|
|
230
|
+
const actual = buffer.subarray(0, bytesRead);
|
|
231
|
+
let start = 0;
|
|
232
|
+
// Match log-service tailing and avoid returning invalid UTF-8 fragments.
|
|
233
|
+
while (start < actual.length && (actual[start] & 0xc0) === 0x80)
|
|
234
|
+
start += 1;
|
|
235
|
+
return actual.subarray(start).toString('utf-8');
|
|
236
|
+
}
|
|
237
|
+
finally {
|
|
238
|
+
closeSync(fd);
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
//# sourceMappingURL=ipc.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ipc.js","sourceRoot":"","sources":["../../../src/desktop/main/ipc.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { LogTarget, LogTail } from '../shared/types.js';
|
|
2
|
+
export declare function listLogTargets(logsDir: string, filenames: string[]): LogTarget[];
|
|
3
|
+
export declare function tailLogText(text: string, maxBytes: number): LogTail;
|
|
4
|
+
//# sourceMappingURL=log-service.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log-service.d.ts","sourceRoot":"","sources":["../../../src/desktop/main/log-service.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAE7D,wBAAgB,cAAc,CAAC,OAAO,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,GAAG,SAAS,EAAE,CAgChF;AAQD,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CASnE"}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import { basename, join } from 'node:path';
|
|
2
|
+
export function listLogTargets(logsDir, filenames) {
|
|
3
|
+
// Only accept known botmux log basenames before joining with logsDir.
|
|
4
|
+
const safeNames = filenames.filter(isLogFilename).sort();
|
|
5
|
+
const targets = [
|
|
6
|
+
{ id: 'all', label: 'All logs', files: safeNames.map(name => join(logsDir, name)) },
|
|
7
|
+
];
|
|
8
|
+
const dashboard = safeNames.filter(name => name.startsWith('dashboard-'));
|
|
9
|
+
if (dashboard.length) {
|
|
10
|
+
targets.push({
|
|
11
|
+
id: 'dashboard',
|
|
12
|
+
label: 'Dashboard',
|
|
13
|
+
files: dashboard.map(name => join(logsDir, name)),
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
const botIndexes = new Set();
|
|
17
|
+
for (const name of safeNames) {
|
|
18
|
+
const match = name.match(/^daemon-(\d+)-(?:out|error)\.log$/);
|
|
19
|
+
if (match) {
|
|
20
|
+
botIndexes.add(Number(match[1]));
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
for (const idx of [...botIndexes].sort((a, b) => a - b)) {
|
|
24
|
+
const files = safeNames
|
|
25
|
+
.filter(name => name === `daemon-${idx}-out.log` || name === `daemon-${idx}-error.log`)
|
|
26
|
+
.map(name => join(logsDir, name));
|
|
27
|
+
targets.push({ id: `bot-${idx}`, label: `Bot ${idx}`, files });
|
|
28
|
+
}
|
|
29
|
+
return targets;
|
|
30
|
+
}
|
|
31
|
+
function isLogFilename(name) {
|
|
32
|
+
// basename(name) rejects path traversal attempts from untrusted IPC input.
|
|
33
|
+
if (basename(name) !== name)
|
|
34
|
+
return false;
|
|
35
|
+
return /^dashboard-(?:out|error)\.log$/.test(name) || /^daemon-\d+-(?:out|error)\.log$/.test(name);
|
|
36
|
+
}
|
|
37
|
+
export function tailLogText(text, maxBytes) {
|
|
38
|
+
const bytes = Buffer.byteLength(text);
|
|
39
|
+
if (bytes <= maxBytes) {
|
|
40
|
+
return { targetId: '', text, truncated: false };
|
|
41
|
+
}
|
|
42
|
+
const buf = Buffer.from(text);
|
|
43
|
+
const start = utf8BoundaryStart(buf, Math.max(0, buf.length - maxBytes));
|
|
44
|
+
return { targetId: '', text: buf.subarray(start).toString('utf-8'), truncated: true };
|
|
45
|
+
}
|
|
46
|
+
function utf8BoundaryStart(buf, start) {
|
|
47
|
+
// Avoid decoding from the middle of a multi-byte UTF-8 sequence.
|
|
48
|
+
while (start < buf.length && (buf[start] & 0xc0) === 0x80) {
|
|
49
|
+
start += 1;
|
|
50
|
+
}
|
|
51
|
+
return start;
|
|
52
|
+
}
|
|
53
|
+
//# sourceMappingURL=log-service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log-service.js","sourceRoot":"","sources":["../../../src/desktop/main/log-service.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
export interface DetectLegacyAutostartInput {
|
|
2
|
+
homeDir: string;
|
|
3
|
+
existsSync(path: string): boolean;
|
|
4
|
+
}
|
|
5
|
+
export declare function legacyAutostartPath(homeDir: string): string;
|
|
6
|
+
export declare function detectLegacyAutostart(input: DetectLegacyAutostartInput): {
|
|
7
|
+
legacyAutostart: boolean;
|
|
8
|
+
legacyPath: string;
|
|
9
|
+
};
|
|
10
|
+
//# sourceMappingURL=login-item.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"login-item.d.ts","sourceRoot":"","sources":["../../../src/desktop/main/login-item.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,0BAA0B;IACzC,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC;CACnC;AAED,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAI3D;AAED,wBAAgB,qBAAqB,CAAC,KAAK,EAAE,0BAA0B,GAAG;IACxE,eAAe,EAAE,OAAO,CAAC;IACzB,UAAU,EAAE,MAAM,CAAC;CACpB,CAGA"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { join } from 'node:path';
|
|
2
|
+
export function legacyAutostartPath(homeDir) {
|
|
3
|
+
// The desktop app uses Electron login items, but still reports the older CLI
|
|
4
|
+
// LaunchAgent so users can migrate knowingly.
|
|
5
|
+
return join(homeDir, 'Library', 'LaunchAgents', 'com.botmux.daemon.plist');
|
|
6
|
+
}
|
|
7
|
+
export function detectLegacyAutostart(input) {
|
|
8
|
+
const legacyPath = legacyAutostartPath(input.homeDir);
|
|
9
|
+
return { legacyAutostart: input.existsSync(legacyPath), legacyPath };
|
|
10
|
+
}
|
|
11
|
+
//# sourceMappingURL=login-item.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"login-item.js","sourceRoot":"","sources":["../../../src/desktop/main/login-item.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAOjC,MAAM,UAAU,mBAAmB,CAAC,OAAe;IACjD,6EAA6E;IAC7E,8CAA8C;IAC9C,OAAO,IAAI,CAAC,OAAO,EAAE,SAAS,EAAE,cAAc,EAAE,yBAAyB,CAAC,CAAC;AAC7E,CAAC;AAED,MAAM,UAAU,qBAAqB,CAAC,KAAiC;IAIrE,MAAM,UAAU,GAAG,mBAAmB,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;IACtD,OAAO,EAAE,eAAe,EAAE,KAAK,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,UAAU,EAAE,CAAC;AACvE,CAAC"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
export interface BuildBotmuxCommandInput {
|
|
2
|
+
electronExecPath: string;
|
|
3
|
+
cliPath: string;
|
|
4
|
+
botmuxHome: string;
|
|
5
|
+
args: string[];
|
|
6
|
+
baseEnv: NodeJS.ProcessEnv;
|
|
7
|
+
}
|
|
8
|
+
export interface BotmuxCommand {
|
|
9
|
+
command: string;
|
|
10
|
+
args: string[];
|
|
11
|
+
env: NodeJS.ProcessEnv;
|
|
12
|
+
}
|
|
13
|
+
export interface BuildExternalBotmuxCommandInput {
|
|
14
|
+
binPath: string;
|
|
15
|
+
botmuxHome: string;
|
|
16
|
+
args: string[];
|
|
17
|
+
baseEnv: NodeJS.ProcessEnv;
|
|
18
|
+
pathEnv?: string;
|
|
19
|
+
}
|
|
20
|
+
export declare function buildBotmuxCommand(input: BuildBotmuxCommandInput): BotmuxCommand;
|
|
21
|
+
export declare function buildExternalBotmuxCommand(input: BuildExternalBotmuxCommandInput): BotmuxCommand;
|
|
22
|
+
//# sourceMappingURL=node-command.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"node-command.d.ts","sourceRoot":"","sources":["../../../src/desktop/main/node-command.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,uBAAuB;IACtC,gBAAgB,EAAE,MAAM,CAAC;IACzB,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,OAAO,EAAE,MAAM,CAAC,UAAU,CAAC;CAC5B;AAED,MAAM,WAAW,aAAa;IAC5B,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,GAAG,EAAE,MAAM,CAAC,UAAU,CAAC;CACxB;AAED,MAAM,WAAW,+BAA+B;IAC9C,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,OAAO,EAAE,MAAM,CAAC,UAAU,CAAC;IAC3B,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,uBAAuB,GAAG,aAAa,CAahF;AAED,wBAAgB,0BAA0B,CAAC,KAAK,EAAE,+BAA+B,GAAG,aAAa,CAgBhG"}
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
import { delimiter, dirname, join } from 'node:path';
|
|
2
|
+
export function buildBotmuxCommand(input) {
|
|
3
|
+
return {
|
|
4
|
+
command: input.electronExecPath,
|
|
5
|
+
args: [input.cliPath, ...input.args],
|
|
6
|
+
env: {
|
|
7
|
+
...input.baseEnv,
|
|
8
|
+
// Reuse Electron's embedded Node runtime to execute the packaged CLI.
|
|
9
|
+
ELECTRON_RUN_AS_NODE: '1',
|
|
10
|
+
// Isolate desktop-managed PM2/session state from any global PM2 daemon.
|
|
11
|
+
PM2_HOME: join(input.botmuxHome, 'pm2'),
|
|
12
|
+
SESSION_DATA_DIR: join(input.botmuxHome, 'data'),
|
|
13
|
+
},
|
|
14
|
+
};
|
|
15
|
+
}
|
|
16
|
+
export function buildExternalBotmuxCommand(input) {
|
|
17
|
+
const env = {
|
|
18
|
+
...input.baseEnv,
|
|
19
|
+
// External CLI bins often use /usr/bin/env node; Finder-launched apps have
|
|
20
|
+
// a small PATH, so put the bin's directory first before invoking it.
|
|
21
|
+
PATH: buildExternalPath(input.baseEnv.PATH, input.binPath, input.pathEnv),
|
|
22
|
+
PM2_HOME: join(input.botmuxHome, 'pm2'),
|
|
23
|
+
SESSION_DATA_DIR: join(input.botmuxHome, 'data'),
|
|
24
|
+
};
|
|
25
|
+
delete env.ELECTRON_RUN_AS_NODE;
|
|
26
|
+
return {
|
|
27
|
+
command: input.binPath,
|
|
28
|
+
args: input.args,
|
|
29
|
+
env,
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
function buildExternalPath(current, binPath, pathEnv) {
|
|
33
|
+
return joinPathEntries([
|
|
34
|
+
dirname(binPath),
|
|
35
|
+
pathEnv,
|
|
36
|
+
'/opt/homebrew/bin',
|
|
37
|
+
'/usr/local/bin',
|
|
38
|
+
'/usr/bin',
|
|
39
|
+
'/bin',
|
|
40
|
+
current,
|
|
41
|
+
]);
|
|
42
|
+
}
|
|
43
|
+
function joinPathEntries(entries) {
|
|
44
|
+
const seen = new Set();
|
|
45
|
+
const ordered = entries
|
|
46
|
+
.flatMap(entry => entry ? entry.split(delimiter) : [])
|
|
47
|
+
.map(entry => entry.trim())
|
|
48
|
+
.filter(entry => {
|
|
49
|
+
if (!entry || seen.has(entry))
|
|
50
|
+
return false;
|
|
51
|
+
seen.add(entry);
|
|
52
|
+
return true;
|
|
53
|
+
});
|
|
54
|
+
return ordered.join(delimiter);
|
|
55
|
+
}
|
|
56
|
+
//# sourceMappingURL=node-command.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"node-command.js","sourceRoot":"","sources":["../../../src/desktop/main/node-command.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAwBrD,MAAM,UAAU,kBAAkB,CAAC,KAA8B;IAC/D,OAAO;QACL,OAAO,EAAE,KAAK,CAAC,gBAAgB;QAC/B,IAAI,EAAE,CAAC,KAAK,CAAC,OAAO,EAAE,GAAG,KAAK,CAAC,IAAI,CAAC;QACpC,GAAG,EAAE;YACH,GAAG,KAAK,CAAC,OAAO;YAChB,sEAAsE;YACtE,oBAAoB,EAAE,GAAG;YACzB,wEAAwE;YACxE,QAAQ,EAAE,IAAI,CAAC,KAAK,CAAC,UAAU,EAAE,KAAK,CAAC;YACvC,gBAAgB,EAAE,IAAI,CAAC,KAAK,CAAC,UAAU,EAAE,MAAM,CAAC;SACjD;KACF,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,0BAA0B,CAAC,KAAsC;IAC/E,MAAM,GAAG,GAAsB;QAC7B,GAAG,KAAK,CAAC,OAAO;QAChB,2EAA2E;QAC3E,qEAAqE;QACrE,IAAI,EAAE,iBAAiB,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,EAAE,KAAK,CAAC,OAAO,EAAE,KAAK,CAAC,OAAO,CAAC;QACzE,QAAQ,EAAE,IAAI,CAAC,KAAK,CAAC,UAAU,EAAE,KAAK,CAAC;QACvC,gBAAgB,EAAE,IAAI,CAAC,KAAK,CAAC,UAAU,EAAE,MAAM,CAAC;KACjD,CAAC;IACF,OAAO,GAAG,CAAC,oBAAoB,CAAC;IAEhC,OAAO;QACL,OAAO,EAAE,KAAK,CAAC,OAAO;QACtB,IAAI,EAAE,KAAK,CAAC,IAAI;QAChB,GAAG;KACJ,CAAC;AACJ,CAAC;AAED,SAAS,iBAAiB,CAAC,OAA2B,EAAE,OAAe,EAAE,OAA2B;IAClG,OAAO,eAAe,CAAC;QACrB,OAAO,CAAC,OAAO,CAAC;QAChB,OAAO;QACP,mBAAmB;QACnB,gBAAgB;QAChB,UAAU;QACV,MAAM;QACN,OAAO;KACR,CAAC,CAAC;AACL,CAAC;AAED,SAAS,eAAe,CAAC,OAAkC;IACzD,MAAM,IAAI,GAAG,IAAI,GAAG,EAAU,CAAC;IAC/B,MAAM,OAAO,GAAG,OAAO;SACpB,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;SACrD,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;SAC1B,MAAM,CAAC,KAAK,CAAC,EAAE;QACd,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC;YAAE,OAAO,KAAK,CAAC;QAC5C,IAAI,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;QAChB,OAAO,IAAI,CAAC;IACd,CAAC,CAAC,CAAC;IACL,OAAO,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;AACjC,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { DesktopPaths } from '../shared/types.js';
|
|
2
|
+
export interface ResolveDesktopPathsInput {
|
|
3
|
+
homeDir: string;
|
|
4
|
+
userDataDir: string;
|
|
5
|
+
resourcesPath: string;
|
|
6
|
+
appVersion: string;
|
|
7
|
+
isPackaged: boolean;
|
|
8
|
+
devRepoRoot?: string;
|
|
9
|
+
}
|
|
10
|
+
export declare function resolveDesktopPaths(input: ResolveDesktopPathsInput): DesktopPaths;
|
|
11
|
+
//# sourceMappingURL=paths.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paths.d.ts","sourceRoot":"","sources":["../../../src/desktop/main/paths.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAEvD,MAAM,WAAW,wBAAwB;IACvC,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,EAAE,MAAM,CAAC;IACpB,aAAa,EAAE,MAAM,CAAC;IACtB,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,OAAO,CAAC;IACpB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,wBAAwB,GAAG,YAAY,CAWjF"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { join } from 'node:path';
|
|
2
|
+
export function resolveDesktopPaths(input) {
|
|
3
|
+
// Keep user data shared with the CLI/dashboard while storing app-managed
|
|
4
|
+
// process state outside ~/.botmux's package tree, so CLI config survives.
|
|
5
|
+
const botmuxHome = join(input.homeDir, '.botmux');
|
|
6
|
+
return {
|
|
7
|
+
botmuxHome,
|
|
8
|
+
dataDir: join(botmuxHome, 'data'),
|
|
9
|
+
logsDir: join(botmuxHome, 'logs'),
|
|
10
|
+
pm2Home: join(botmuxHome, 'pm2'),
|
|
11
|
+
};
|
|
12
|
+
}
|
|
13
|
+
//# sourceMappingURL=paths.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paths.js","sourceRoot":"","sources":["../../../src/desktop/main/paths.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAYjC,MAAM,UAAU,mBAAmB,CAAC,KAA+B;IACjE,yEAAyE;IACzE,0EAA0E;IAC1E,MAAM,UAAU,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;IAElD,OAAO;QACL,UAAU;QACV,OAAO,EAAE,IAAI,CAAC,UAAU,EAAE,MAAM,CAAC;QACjC,OAAO,EAAE,IAAI,CAAC,UAAU,EAAE,MAAM,CAAC;QACjC,OAAO,EAAE,IAAI,CAAC,UAAU,EAAE,KAAK,CAAC;KACjC,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { spawn as spawnProcess } from 'node:child_process';
|
|
2
|
+
import type { DesktopPaths } from '../shared/types.js';
|
|
3
|
+
import type { ExternalRuntimeCandidate } from './runtime-service.js';
|
|
4
|
+
import { type Pm2AppSummary } from './runtime-source.js';
|
|
5
|
+
interface Pm2ListDeps {
|
|
6
|
+
existsSync?: (path: string) => boolean;
|
|
7
|
+
spawn?: typeof spawnProcess;
|
|
8
|
+
execPath?: string;
|
|
9
|
+
env?: NodeJS.ProcessEnv;
|
|
10
|
+
timeoutMs?: number;
|
|
11
|
+
}
|
|
12
|
+
export declare const defaultPm2ListTimeoutMs = 25000;
|
|
13
|
+
export declare function listPm2Apps(paths: DesktopPaths, runtime: ExternalRuntimeCandidate, deps?: Pm2ListDeps): Promise<Pm2AppSummary[]>;
|
|
14
|
+
export {};
|
|
15
|
+
//# sourceMappingURL=pm2-apps.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pm2-apps.d.ts","sourceRoot":"","sources":["../../../src/desktop/main/pm2-apps.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,IAAI,YAAY,EAAuC,MAAM,oBAAoB,CAAC;AAGhG,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AACvD,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAgB,KAAK,aAAa,EAAE,MAAM,qBAAqB,CAAC;AAEvE,UAAU,WAAW;IACnB,UAAU,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC;IACvC,KAAK,CAAC,EAAE,OAAO,YAAY,CAAC;IAC5B,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,GAAG,CAAC,EAAE,MAAM,CAAC,UAAU,CAAC;IACxB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,eAAO,MAAM,uBAAuB,QAAS,CAAC;AAE9C,wBAAgB,WAAW,CACzB,KAAK,EAAE,YAAY,EACnB,OAAO,EAAE,wBAAwB,EACjC,IAAI,GAAE,WAAgB,GACrB,OAAO,CAAC,aAAa,EAAE,CAAC,CAkE1B"}
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
import { spawn as spawnProcess } from 'node:child_process';
|
|
2
|
+
import { existsSync as pathExistsSync } from 'node:fs';
|
|
3
|
+
import { delimiter, dirname, join } from 'node:path';
|
|
4
|
+
import { parsePm2Apps } from './runtime-source.js';
|
|
5
|
+
export const defaultPm2ListTimeoutMs = 25_000;
|
|
6
|
+
export function listPm2Apps(paths, runtime, deps = {}) {
|
|
7
|
+
const existsSync = deps.existsSync ?? pathExistsSync;
|
|
8
|
+
const packageRoot = runtime.root;
|
|
9
|
+
const pm2Bin = join(packageRoot, 'node_modules', 'pm2', 'bin', 'pm2');
|
|
10
|
+
if (!existsSync(pm2Bin)) {
|
|
11
|
+
return Promise.reject(new Error(`PM2 binary not found: ${pm2Bin}`));
|
|
12
|
+
}
|
|
13
|
+
const command = pm2Bin;
|
|
14
|
+
const args = ['jlist'];
|
|
15
|
+
const baseEnv = deps.env ?? process.env;
|
|
16
|
+
const env = {
|
|
17
|
+
...baseEnv,
|
|
18
|
+
// External PM2 bins use /usr/bin/env node; Finder-launched apps need a
|
|
19
|
+
// repaired PATH so discovery does not depend on the user's shell startup.
|
|
20
|
+
PATH: withRuntimePath(baseEnv.PATH, runtime.binPath, runtime.pathEnv),
|
|
21
|
+
PM2_HOME: paths.pm2Home,
|
|
22
|
+
SESSION_DATA_DIR: paths.dataDir,
|
|
23
|
+
};
|
|
24
|
+
delete env.ELECTRON_RUN_AS_NODE;
|
|
25
|
+
return new Promise((resolve, reject) => {
|
|
26
|
+
// PM2 discovery is a status input, not decorative data: errors reject so
|
|
27
|
+
// runtime-service can surface a degraded state instead of pretending stopped.
|
|
28
|
+
const child = (deps.spawn ?? spawnProcess)(command, args, { cwd: packageRoot, env });
|
|
29
|
+
let stdout = '';
|
|
30
|
+
let stderr = '';
|
|
31
|
+
let settled = false;
|
|
32
|
+
const timer = setTimeout(() => {
|
|
33
|
+
if (settled)
|
|
34
|
+
return;
|
|
35
|
+
settled = true;
|
|
36
|
+
child.kill();
|
|
37
|
+
reject(new Error(`PM2 jlist timed out after ${deps.timeoutMs ?? defaultPm2ListTimeoutMs}ms`));
|
|
38
|
+
}, deps.timeoutMs ?? defaultPm2ListTimeoutMs);
|
|
39
|
+
const finish = (fn) => {
|
|
40
|
+
if (settled)
|
|
41
|
+
return;
|
|
42
|
+
settled = true;
|
|
43
|
+
clearTimeout(timer);
|
|
44
|
+
fn();
|
|
45
|
+
};
|
|
46
|
+
child.stdout.on('data', chunk => {
|
|
47
|
+
stdout += String(chunk);
|
|
48
|
+
});
|
|
49
|
+
child.stderr.on('data', chunk => {
|
|
50
|
+
stderr += String(chunk);
|
|
51
|
+
});
|
|
52
|
+
child.on('error', error => {
|
|
53
|
+
finish(() => reject(new Error(`PM2 jlist failed: ${error.message}`)));
|
|
54
|
+
});
|
|
55
|
+
child.on('close', code => {
|
|
56
|
+
finish(() => {
|
|
57
|
+
if (code !== 0 || !stdout) {
|
|
58
|
+
const detail = concise(stderr || `exit code ${code ?? 1}`);
|
|
59
|
+
reject(new Error(`PM2 jlist failed: ${detail}`));
|
|
60
|
+
return;
|
|
61
|
+
}
|
|
62
|
+
try {
|
|
63
|
+
resolve(parsePm2Apps(stdout));
|
|
64
|
+
}
|
|
65
|
+
catch (error) {
|
|
66
|
+
reject(new Error(`PM2 jlist parse failed: ${error instanceof Error ? error.message : String(error)}`));
|
|
67
|
+
}
|
|
68
|
+
});
|
|
69
|
+
});
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
function withRuntimePath(current, binPath, pathEnv) {
|
|
73
|
+
const entries = [
|
|
74
|
+
dirname(binPath),
|
|
75
|
+
...(pathEnv ? pathEnv.split(delimiter) : []),
|
|
76
|
+
'/opt/homebrew/bin',
|
|
77
|
+
'/usr/local/bin',
|
|
78
|
+
'/usr/bin',
|
|
79
|
+
'/bin',
|
|
80
|
+
...(current ? current.split(delimiter) : []),
|
|
81
|
+
];
|
|
82
|
+
const seen = new Set();
|
|
83
|
+
return entries
|
|
84
|
+
.map(entry => entry.trim())
|
|
85
|
+
.filter(entry => {
|
|
86
|
+
if (!entry || seen.has(entry))
|
|
87
|
+
return false;
|
|
88
|
+
seen.add(entry);
|
|
89
|
+
return true;
|
|
90
|
+
})
|
|
91
|
+
.join(delimiter);
|
|
92
|
+
}
|
|
93
|
+
function concise(value) {
|
|
94
|
+
const text = value.replace(/\s+/g, ' ').trim();
|
|
95
|
+
return text.length > 200 ? `${text.slice(0, 197)}...` : text;
|
|
96
|
+
}
|
|
97
|
+
//# sourceMappingURL=pm2-apps.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pm2-apps.js","sourceRoot":"","sources":["../../../src/desktop/main/pm2-apps.ts"],"names":[],"mappings":"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"}
|