@runweave/server-linux-x64 0.1.12 → 0.1.14
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/manifest.json +146 -146
- package/native.tar.gz +0 -0
- package/package.json +1 -1
- package/payload/app-server/build-info.json +3 -3
- package/payload/app-server/index.cjs +1 -1
- package/payload/backend/build-info.json +4 -4
- package/payload/backend/index.cjs +225 -119
- package/payload/frontend/dist/assets/{_baseUniq-VUz3u9LC.js → _baseUniq-BqvkeJO_.js} +1 -1
- package/payload/frontend/dist/assets/{access-DYX0dB6C.js → access-DdS0UJde.js} +1 -1
- package/payload/frontend/dist/assets/{advanced-CweRHp2W.js → advanced-BbcDBPNv.js} +1 -1
- package/payload/frontend/dist/assets/{appearance-494KUegR.js → appearance-BvmkpQdR.js} +1 -1
- package/payload/frontend/dist/assets/{arc-Z2kK66lq.js → arc-C0XOrQvn.js} +1 -1
- package/payload/frontend/dist/assets/{architectureDiagram-Q4EWVU46-qCVxxH3R.js → architectureDiagram-Q4EWVU46-BPP9wqzx.js} +1 -1
- package/payload/frontend/dist/assets/{blockDiagram-DXYQGD6D-BlIbAFEf.js → blockDiagram-DXYQGD6D-C-tmnyfm.js} +1 -1
- package/payload/frontend/dist/assets/{c4Diagram-AHTNJAMY-E3iDtEa4.js → c4Diagram-AHTNJAMY-C6uI9h_3.js} +1 -1
- package/payload/frontend/dist/assets/channel-DaIQFY7W.js +1 -0
- package/payload/frontend/dist/assets/{chunk-4BX2VUAB-BMmYQfLj.js → chunk-4BX2VUAB-CCI-uz3D.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-4TB4RGXK-CWBrRDbS.js → chunk-4TB4RGXK-CqUM0_7D.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-55IACEB6-B-RyyBnf.js → chunk-55IACEB6-DDxrCLKB.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-EDXVE4YY-BKzU4TXS.js → chunk-EDXVE4YY-LwYMVaGh.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-FMBD7UC4-n132OCI6.js → chunk-FMBD7UC4-CQR_-5z5.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-OYMX7WX6-4b-D8G11.js → chunk-OYMX7WX6-DQ0IiFt5.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-QZHKN3VN-C3zjki3z.js → chunk-QZHKN3VN-BPX4TBXp.js} +1 -1
- package/payload/frontend/dist/assets/{chunk-YZCP3GAM-Bi7S_JyD.js → chunk-YZCP3GAM-DqZhVlNy.js} +1 -1
- package/payload/frontend/dist/assets/classDiagram-6PBFFD2Q-TM6ckD19.js +1 -0
- package/payload/frontend/dist/assets/classDiagram-v2-HSJHXN6E-TM6ckD19.js +1 -0
- package/payload/frontend/dist/assets/clone-BoG338Z7.js +1 -0
- package/payload/frontend/dist/assets/{connection-DtjjR8IP.js → connection-ToakGqMm.js} +1 -1
- package/payload/frontend/dist/assets/{connections-BytUAh1Z.js → connections-DD38aD2_.js} +1 -1
- package/payload/frontend/dist/assets/{cose-bilkent-S5V4N54A-CDCFpAOm.js → cose-bilkent-S5V4N54A-Bi6kn4wb.js} +1 -1
- package/payload/frontend/dist/assets/{dagre-KV5264BT-DTQVpeTz.js → dagre-KV5264BT-D7PPmb_h.js} +1 -1
- package/payload/frontend/dist/assets/{desktop-BuftJPyE.js → desktop-D80mAqEi.js} +1 -1
- package/payload/frontend/dist/assets/{diagram-5BDNPKRD-ShI36c2G.js → diagram-5BDNPKRD-2Fg0LDFB.js} +1 -1
- package/payload/frontend/dist/assets/{diagram-G4DWMVQ6-BPxdrMgU.js → diagram-G4DWMVQ6-DDht1hGL.js} +1 -1
- package/payload/frontend/dist/assets/{diagram-MMDJMWI5-iwh0ZT7T.js → diagram-MMDJMWI5-_slCo5qd.js} +1 -1
- package/payload/frontend/dist/assets/{diagram-TYMM5635-CX2F4XD4.js → diagram-TYMM5635-BibhtXBj.js} +1 -1
- package/payload/frontend/dist/assets/{erDiagram-SMLLAGMA-DwXz5Tds.js → erDiagram-SMLLAGMA-Tb9JdHm7.js} +1 -1
- package/payload/frontend/dist/assets/{flowDiagram-DWJPFMVM-CVDi2XWl.js → flowDiagram-DWJPFMVM-DmV0VUHI.js} +1 -1
- package/payload/frontend/dist/assets/{ganttDiagram-T4ZO3ILL-DLuDUXuQ.js → ganttDiagram-T4ZO3ILL-boTSPZL8.js} +1 -1
- package/payload/frontend/dist/assets/{gitGraphDiagram-UUTBAWPF-DsqOAHKo.js → gitGraphDiagram-UUTBAWPF-3Akku_ak.js} +1 -1
- package/payload/frontend/dist/assets/{graph-6BysLM8d.js → graph-GAq0lcsb.js} +1 -1
- package/payload/frontend/dist/assets/{image-dI1rk_wX.js → image-PejzD76r.js} +1 -1
- package/payload/frontend/dist/assets/{index-CNnzZKYi.js → index-BBNE8InR.js} +5 -5
- package/payload/frontend/dist/assets/{infoDiagram-42DDH7IO-ByaP-F4m.js → infoDiagram-42DDH7IO-TrixGt-D.js} +1 -1
- package/payload/frontend/dist/assets/{ishikawaDiagram-UXIWVN3A-BbNJbxvT.js → ishikawaDiagram-UXIWVN3A-BYKU82ro.js} +1 -1
- package/payload/frontend/dist/assets/{journeyDiagram-VCZTEJTY-CrOVnF8b.js → journeyDiagram-VCZTEJTY-BL_50q1o.js} +1 -1
- package/payload/frontend/dist/assets/{kanban-definition-6JOO6SKY-B0uutGkA.js → kanban-definition-6JOO6SKY-Clxk3CDg.js} +1 -1
- package/payload/frontend/dist/assets/{layout-BNJKrH1C.js → layout-BbxLzgiJ.js} +1 -1
- package/payload/frontend/dist/assets/{linear-CzieEpVo.js → linear-DWemxXgm.js} +1 -1
- package/payload/frontend/dist/assets/{main-DPDWozNB.js → main-BHwOPARZ.js} +150 -150
- package/payload/frontend/dist/assets/{min-COzbZh0B.js → min-DIL93Hib.js} +1 -1
- package/payload/frontend/dist/assets/{mindmap-definition-QFDTVHPH-COtW2jp5.js → mindmap-definition-QFDTVHPH-DlfLczjR.js} +1 -1
- package/payload/frontend/dist/assets/{monitoring-VTNGzAyv.js → monitoring-B6pQ-P1J.js} +1 -1
- package/payload/frontend/dist/assets/{notifications-D-GW-TTF.js → notifications-B9lXATqv.js} +1 -1
- package/payload/frontend/dist/assets/{pieDiagram-DEJITSTG-EKQe1mDG.js → pieDiagram-DEJITSTG-BaU_H2x3.js} +1 -1
- package/payload/frontend/dist/assets/{quadrantDiagram-34T5L4WZ-UdkJN2GP.js → quadrantDiagram-34T5L4WZ-D3nVMaXv.js} +1 -1
- package/payload/frontend/dist/assets/{record-content-BMMqgX4o.js → record-content-Dn6GE_dv.js} +1 -1
- package/payload/frontend/dist/assets/{requirementDiagram-MS252O5E-DUp6aMLi.js → requirementDiagram-MS252O5E-C7J-xGnU.js} +1 -1
- package/payload/frontend/dist/assets/{sankeyDiagram-XADWPNL6-BEHbyQqG.js → sankeyDiagram-XADWPNL6-BAkualMS.js} +1 -1
- package/payload/frontend/dist/assets/{sequenceDiagram-FGHM5R23-DOidQGue.js → sequenceDiagram-FGHM5R23-BYWAdS9C.js} +1 -1
- package/payload/frontend/dist/assets/{stateDiagram-FHFEXIEX-D19ZNvzk.js → stateDiagram-FHFEXIEX-C3qD8m-7.js} +1 -1
- package/payload/frontend/dist/assets/stateDiagram-v2-QKLJ7IA2-C18IEkog.js +1 -0
- package/payload/frontend/dist/assets/{status-DgyGUiXv.js → status-MDvjSQ51.js} +1 -1
- package/payload/frontend/dist/assets/suiji-B6w3AzG7.js +1 -0
- package/payload/frontend/dist/assets/{svg-DaiBcNRS.js → svg-C0XZL3qU.js} +1 -1
- package/payload/frontend/dist/assets/{tabs-DPvaaQlw.js → tabs-Y-BEbPyW.js} +1 -1
- package/payload/frontend/dist/assets/{timeline-definition-GMOUNBTQ-DyZYnin1.js → timeline-definition-GMOUNBTQ-JER6Qyhn.js} +1 -1
- package/payload/frontend/dist/assets/{vennDiagram-DHZGUBPP-CvLT97Cb.js → vennDiagram-DHZGUBPP-kRp3Wh4r.js} +1 -1
- package/payload/frontend/dist/assets/{wardley-RL74JXVD-Bi_yW1_U.js → wardley-RL74JXVD-Dnh_rEyA.js} +1 -1
- package/payload/frontend/dist/assets/{wardleyDiagram-NUSXRM2D-Bg55_fJ7.js → wardleyDiagram-NUSXRM2D-DxiIy5IP.js} +1 -1
- package/payload/frontend/dist/assets/{xychartDiagram-5P7HB3ND-CgI-KDMY.js → xychartDiagram-5P7HB3ND-DcckHE39.js} +1 -1
- package/payload/frontend/dist/build-info.json +4 -4
- package/payload/frontend/dist/companion.html +1 -1
- package/payload/frontend/dist/index.html +2 -2
- package/payload/pty-host/index.cjs +21 -3
- package/payload/frontend/dist/assets/channel-CoPKff4t.js +0 -1
- package/payload/frontend/dist/assets/classDiagram-6PBFFD2Q-FUK_Ald7.js +0 -1
- package/payload/frontend/dist/assets/classDiagram-v2-HSJHXN6E-FUK_Ald7.js +0 -1
- package/payload/frontend/dist/assets/clone-ByE4QDPq.js +0 -1
- package/payload/frontend/dist/assets/stateDiagram-v2-QKLJ7IA2-BHG_Lyc2.js +0 -1
- package/payload/frontend/dist/assets/suiji-C9TumXnC.js +0 -1
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/* runweave:build-info */var __RUNWEAVE_BUILD_INFO__={"version":"0.1.0","buildId":"
|
|
1
|
+
/* runweave:build-info */var __RUNWEAVE_BUILD_INFO__={"version":"0.1.0","buildId":"20261109T213633989Z-9301bc5f","sourceRevision":"9301bc5fbeb157ec84245bf38efb0073647b86fe","sourceDirty":false,"builtAt":"2026-11-09T21:36:33.989Z","contentSha256":"ee24c2adfe7a38b0f7698d68d8493b560042b699baba92c63e79961518d9a9af"};
|
|
2
2
|
const __IMPORT_META_URL__ = require('url').pathToFileURL(__filename).href;
|
|
3
3
|
"use strict";
|
|
4
4
|
var __create = Object.create;
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": "0.1.0",
|
|
3
|
-
"buildId": "
|
|
4
|
-
"sourceRevision": "
|
|
3
|
+
"buildId": "20261109T213633400Z-9301bc5f",
|
|
4
|
+
"sourceRevision": "9301bc5fbeb157ec84245bf38efb0073647b86fe",
|
|
5
5
|
"sourceDirty": false,
|
|
6
|
-
"builtAt": "2026-11-
|
|
7
|
-
"contentSha256": "
|
|
6
|
+
"builtAt": "2026-11-09T21:36:33.400Z",
|
|
7
|
+
"contentSha256": "9206f699f02fa2889905044732d8ef8f84de3fe27d4d46d168895cb13b43d93d"
|
|
8
8
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/* runweave:build-info */var __RUNWEAVE_BUILD_INFO__={"version":"0.1.0","buildId":"
|
|
1
|
+
/* runweave:build-info */var __RUNWEAVE_BUILD_INFO__={"version":"0.1.0","buildId":"20261109T213633400Z-9301bc5f","sourceRevision":"9301bc5fbeb157ec84245bf38efb0073647b86fe","sourceDirty":false,"builtAt":"2026-11-09T21:36:33.400Z","contentSha256":"9206f699f02fa2889905044732d8ef8f84de3fe27d4d46d168895cb13b43d93d"};
|
|
2
2
|
const __IMPORT_META_URL__ = require('url').pathToFileURL(__filename).href;
|
|
3
3
|
"use strict";
|
|
4
4
|
var __create = Object.create;
|
|
@@ -32074,7 +32074,7 @@ var require_websocket = __commonJS({
|
|
|
32074
32074
|
var http4 = require("http");
|
|
32075
32075
|
var net8 = require("net");
|
|
32076
32076
|
var tls2 = require("tls");
|
|
32077
|
-
var { randomBytes: randomBytes8, createHash:
|
|
32077
|
+
var { randomBytes: randomBytes8, createHash: createHash49 } = require("crypto");
|
|
32078
32078
|
var { Duplex, Readable: Readable2 } = require("stream");
|
|
32079
32079
|
var { URL: URL2 } = require("url");
|
|
32080
32080
|
var PerMessageDeflate = require_permessage_deflate();
|
|
@@ -32734,7 +32734,7 @@ var require_websocket = __commonJS({
|
|
|
32734
32734
|
abortHandshake(websocket, socket, "Invalid Upgrade header");
|
|
32735
32735
|
return;
|
|
32736
32736
|
}
|
|
32737
|
-
const digest7 =
|
|
32737
|
+
const digest7 = createHash49("sha1").update(key2 + GUID).digest("base64");
|
|
32738
32738
|
if (res.headers["sec-websocket-accept"] !== digest7) {
|
|
32739
32739
|
abortHandshake(websocket, socket, "Invalid Sec-WebSocket-Accept header");
|
|
32740
32740
|
return;
|
|
@@ -33101,7 +33101,7 @@ var require_websocket_server = __commonJS({
|
|
|
33101
33101
|
var EventEmitter = require("events");
|
|
33102
33102
|
var http4 = require("http");
|
|
33103
33103
|
var { Duplex } = require("stream");
|
|
33104
|
-
var { createHash:
|
|
33104
|
+
var { createHash: createHash49 } = require("crypto");
|
|
33105
33105
|
var extension = require_extension();
|
|
33106
33106
|
var PerMessageDeflate = require_permessage_deflate();
|
|
33107
33107
|
var subprotocol = require_subprotocol();
|
|
@@ -33402,7 +33402,7 @@ var require_websocket_server = __commonJS({
|
|
|
33402
33402
|
);
|
|
33403
33403
|
}
|
|
33404
33404
|
if (this._state > RUNNING) return abortHandshake(socket, 503);
|
|
33405
|
-
const digest7 =
|
|
33405
|
+
const digest7 = createHash49("sha1").update(key2 + GUID).digest("base64");
|
|
33406
33406
|
const headers = [
|
|
33407
33407
|
"HTTP/1.1 101 Switching Protocols",
|
|
33408
33408
|
"Upgrade: websocket",
|
|
@@ -71434,6 +71434,21 @@ function buildAgentResumeArgs(agent, thread) {
|
|
|
71434
71434
|
return [resumeFlags[agent] ?? "resume", thread];
|
|
71435
71435
|
}
|
|
71436
71436
|
|
|
71437
|
+
// packages/shared/src/terminal/shell.ts
|
|
71438
|
+
function terminalShellName(command) {
|
|
71439
|
+
return (command.split(/[\\/]/).at(-1) ?? command).toLowerCase().replace(/\.exe$/, "");
|
|
71440
|
+
}
|
|
71441
|
+
function isInteractiveShellLaunch(launch) {
|
|
71442
|
+
const name = terminalShellName(launch.command);
|
|
71443
|
+
if (!["sh", "bash", "zsh", "dash", "ksh", "fish", "powershell", "pwsh", "cmd"].includes(name)) return false;
|
|
71444
|
+
return !(launch.args ?? []).some((arg) => {
|
|
71445
|
+
const value = arg.toLowerCase();
|
|
71446
|
+
if (name === "cmd") return !/^\/(?:d|q|a|u|e:(?:on|off)|f:(?:on|off)|v:(?:on|off))$/.test(value);
|
|
71447
|
+
if (name === "powershell" || name === "pwsh") return !["-nologo", "-noprofile", "-noexit", "-login", "-l"].includes(value);
|
|
71448
|
+
return ["--help", "--version"].includes(value) || !value.startsWith("-") || value === "--" || /^-[^-]*[cs]/.test(value) || /^--(?:command|init-command)(?:=|$)/.test(value);
|
|
71449
|
+
});
|
|
71450
|
+
}
|
|
71451
|
+
|
|
71437
71452
|
// backend/src/terminal/runtime/pi-editor.ts
|
|
71438
71453
|
var import_node_crypto12 = require("node:crypto");
|
|
71439
71454
|
var import_node_http = require("node:http");
|
|
@@ -71575,7 +71590,19 @@ function buildAgentResumeCommand(thread) {
|
|
|
71575
71590
|
thread.sessionFile ?? thread.threadId
|
|
71576
71591
|
)
|
|
71577
71592
|
];
|
|
71578
|
-
|
|
71593
|
+
const configured = thread.provider === "codex" ? settingText("agents.codex.binary")?.trim() : ["trae", "traex", "traecli"].includes(thread.provider) ? settingText("agents.traex.binary")?.trim() : void 0;
|
|
71594
|
+
const executable = thread.executable ?? configured ?? thread.provider;
|
|
71595
|
+
const shell = terminalShellName(thread.shell ?? "sh");
|
|
71596
|
+
if (["powershell", "pwsh", "cmd"].includes(shell)) {
|
|
71597
|
+
const parts = [executable, ...args];
|
|
71598
|
+
if (parts.some((part) => [...part].some((character) => character.charCodeAt(0) < 32 || character.charCodeAt(0) === 127)))
|
|
71599
|
+
throw new Error("Agent resume arguments contain terminal control characters");
|
|
71600
|
+
const command = `& ${parts.map((part) => `'${part.replaceAll("'", "''")}'`).join(" ")}`;
|
|
71601
|
+
return shell === "cmd" ? `powershell.exe -NoProfile -EncodedCommand ${Buffer.from(command, "utf16le").toString("base64")}
|
|
71602
|
+
` : `${command}
|
|
71603
|
+
`;
|
|
71604
|
+
}
|
|
71605
|
+
return `${shellQuote(executable)} ${args.map(shellQuote).join(" ")}
|
|
71579
71606
|
`;
|
|
71580
71607
|
}
|
|
71581
71608
|
function shellQuote(value) {
|
|
@@ -71878,21 +71905,6 @@ var aiDiagnosticLog = createAiDiagnosticLog({
|
|
|
71878
71905
|
source: "backend"
|
|
71879
71906
|
});
|
|
71880
71907
|
|
|
71881
|
-
// packages/shared/src/terminal/shell.ts
|
|
71882
|
-
function terminalShellName(command) {
|
|
71883
|
-
return (command.split(/[\\/]/).at(-1) ?? command).toLowerCase().replace(/\.exe$/, "");
|
|
71884
|
-
}
|
|
71885
|
-
function isInteractiveShellLaunch(launch) {
|
|
71886
|
-
const name = terminalShellName(launch.command);
|
|
71887
|
-
if (!["sh", "bash", "zsh", "dash", "ksh", "fish", "powershell", "pwsh", "cmd"].includes(name)) return false;
|
|
71888
|
-
return !(launch.args ?? []).some((arg) => {
|
|
71889
|
-
const value = arg.toLowerCase();
|
|
71890
|
-
if (name === "cmd") return !/^\/(?:d|q|a|u|e:(?:on|off)|f:(?:on|off)|v:(?:on|off))$/.test(value);
|
|
71891
|
-
if (name === "powershell" || name === "pwsh") return !["-nologo", "-noprofile", "-noexit", "-login", "-l"].includes(value);
|
|
71892
|
-
return ["--help", "--version"].includes(value) || !value.startsWith("-") || value === "--" || /^-[^-]*[cs]/.test(value) || /^--(?:command|init-command)(?:=|$)/.test(value);
|
|
71893
|
-
});
|
|
71894
|
-
}
|
|
71895
|
-
|
|
71896
71908
|
// backend/src/terminal/runtime/pty-host-client.ts
|
|
71897
71909
|
var import_node_crypto15 = require("node:crypto");
|
|
71898
71910
|
|
|
@@ -72069,27 +72081,37 @@ var ownerId = (0, import_node_crypto15.randomUUID)();
|
|
|
72069
72081
|
var connection;
|
|
72070
72082
|
var generation;
|
|
72071
72083
|
var hostInstanceId;
|
|
72084
|
+
var upstreams;
|
|
72072
72085
|
var stopped = false;
|
|
72073
72086
|
function usesPtyHost() {
|
|
72074
72087
|
return process.platform === "win32" && Boolean(process.env.RUNWEAVE_RUNTIME_RELEASE_ID);
|
|
72075
72088
|
}
|
|
72076
72089
|
async function getPtyHost() {
|
|
72077
72090
|
if (stopped) throw new Error("HOST_CLIENT_STOPPED");
|
|
72078
|
-
connection ??= PtyHostClient.connect(configuration().context, ownerId, generation, hostInstanceId).then((client) => {
|
|
72091
|
+
connection ??= PtyHostClient.connect(configuration().context, ownerId, generation, hostInstanceId).then(async (client) => {
|
|
72079
72092
|
generation = client.generation;
|
|
72080
72093
|
hostInstanceId = client.descriptor.hostInstanceId;
|
|
72081
72094
|
client.disconnected.add(() => {
|
|
72082
72095
|
connection = void 0;
|
|
72083
72096
|
});
|
|
72084
|
-
|
|
72097
|
+
try {
|
|
72098
|
+
if (upstreams) await client.request("setUpstreams", upstreams);
|
|
72099
|
+
return client;
|
|
72100
|
+
} catch (error2) {
|
|
72101
|
+
client.close();
|
|
72102
|
+
throw error2;
|
|
72103
|
+
}
|
|
72085
72104
|
}).catch((error2) => {
|
|
72086
72105
|
connection = void 0;
|
|
72087
72106
|
throw error2;
|
|
72088
72107
|
});
|
|
72089
72108
|
return connection;
|
|
72090
72109
|
}
|
|
72091
|
-
async function syncPtyHostUpstreams(
|
|
72092
|
-
if (usesPtyHost())
|
|
72110
|
+
async function syncPtyHostUpstreams(value) {
|
|
72111
|
+
if (usesPtyHost()) {
|
|
72112
|
+
upstreams = { ...value };
|
|
72113
|
+
await (await getPtyHost()).request("setUpstreams", value);
|
|
72114
|
+
}
|
|
72093
72115
|
}
|
|
72094
72116
|
async function createHostedPty(options) {
|
|
72095
72117
|
const client = await getPtyHost();
|
|
@@ -73186,63 +73208,139 @@ function createTerminalRuntimeRecorder(terminalSessionManager, terminalSessionId
|
|
|
73186
73208
|
};
|
|
73187
73209
|
}
|
|
73188
73210
|
|
|
73211
|
+
// backend/src/terminal/runtime/recovery-policy.ts
|
|
73212
|
+
var RebuildWindowMs = 6e4;
|
|
73213
|
+
var MaxRebuildAttempts = 3;
|
|
73214
|
+
var TerminalRebuildLimitError = class extends Error {
|
|
73215
|
+
constructor(terminalSessionId, count, windowMs, maxAttempts, runtime = "terminal") {
|
|
73216
|
+
super(`${runtime} session rebuild exceeded ${maxAttempts} attempts in ${windowMs} ms for ${terminalSessionId}`);
|
|
73217
|
+
this.terminalSessionId = terminalSessionId;
|
|
73218
|
+
this.count = count;
|
|
73219
|
+
this.windowMs = windowMs;
|
|
73220
|
+
this.maxAttempts = maxAttempts;
|
|
73221
|
+
this.name = "TerminalRebuildLimitError";
|
|
73222
|
+
}
|
|
73223
|
+
};
|
|
73224
|
+
function recordTerminalRebuildAttempt(history, terminalSessionId, now2 = Date.now()) {
|
|
73225
|
+
const attempts = (history.get(terminalSessionId) ?? []).filter((timestamp3) => timestamp3 >= now2 - RebuildWindowMs);
|
|
73226
|
+
history.set(terminalSessionId, attempts);
|
|
73227
|
+
if (attempts.length >= MaxRebuildAttempts)
|
|
73228
|
+
throw new TerminalRebuildLimitError(terminalSessionId, attempts.length + 1, RebuildWindowMs, MaxRebuildAttempts);
|
|
73229
|
+
attempts.push(now2);
|
|
73230
|
+
return { allowed: true, count: attempts.length, windowMs: RebuildWindowMs, maxAttempts: MaxRebuildAttempts };
|
|
73231
|
+
}
|
|
73232
|
+
function resolveAgentThreadToResume(session) {
|
|
73233
|
+
const activeProvider = getAgentForCommand(session.activeCommand) ?? (session.terminalState?.state.startsWith("agent_") ? session.terminalState.agent : null);
|
|
73234
|
+
if (!activeProvider) return null;
|
|
73235
|
+
const currentThreadId = session.threadId?.trim();
|
|
73236
|
+
const currentProvider = session.threadProvider ?? (currentThreadId ? "codex" : void 0);
|
|
73237
|
+
if (currentThreadId && currentProvider === activeProvider)
|
|
73238
|
+
return { provider: activeProvider, threadId: currentThreadId };
|
|
73239
|
+
const recentThreadId = session.lastThreadId?.trim();
|
|
73240
|
+
return recentThreadId && session.lastThreadProvider === activeProvider ? { provider: activeProvider, threadId: recentThreadId } : null;
|
|
73241
|
+
}
|
|
73242
|
+
|
|
73189
73243
|
// backend/src/terminal/runtime/pty-host-runtime.ts
|
|
73190
73244
|
var launches = /* @__PURE__ */ new Map();
|
|
73245
|
+
var rebuildAttempts = /* @__PURE__ */ new Map();
|
|
73191
73246
|
function ensureHostedTerminal(options) {
|
|
73192
73247
|
const previous = launches.get(options.session.id);
|
|
73193
73248
|
if (previous) return previous;
|
|
73194
|
-
const launch = (
|
|
73195
|
-
const { session, terminalSessionManager, runtimeRegistry } = options;
|
|
73196
|
-
const existing = runtimeRegistry.getSessionRuntime(session.id);
|
|
73197
|
-
if (existing) return existing;
|
|
73198
|
-
let binding = session.ptyHost;
|
|
73199
|
-
const creating = !binding;
|
|
73200
|
-
if (!binding) {
|
|
73201
|
-
binding = { hostInstanceId: (await getPtyHost()).descriptor.hostInstanceId, sessionInstanceId: (0, import_node_crypto16.randomUUID)() };
|
|
73202
|
-
await terminalSessionManager.updateRuntimeMetadata(session.id, { runtimeKind: "pty", ptyHost: binding, recoverable: true });
|
|
73203
|
-
}
|
|
73204
|
-
const fallback = creating ? resolveTerminalFallbackLaunchConfig(session) : null;
|
|
73205
|
-
const terminalEnv = buildTerminalRuntimeEnvironment({ terminalSessionId: session.id, projectId: session.projectId, source: session.source });
|
|
73206
|
-
const runtime = await createHostedPty({
|
|
73207
|
-
terminalSessionId: session.id,
|
|
73208
|
-
binding,
|
|
73209
|
-
onLaunch: async (launch2) => {
|
|
73210
|
-
if (launch2.fallbackReason) logger.warn("terminal.pty-host.fallback.activated", { terminalSessionId: session.id, command: launch2.command, reason: launch2.fallbackReason });
|
|
73211
|
-
await terminalSessionManager.updateSessionLaunch(session.id, { command: launch2.command, args: launch2.args });
|
|
73212
|
-
},
|
|
73213
|
-
create: creating ? {
|
|
73214
|
-
sessionInstanceId: binding.sessionInstanceId,
|
|
73215
|
-
terminalSessionId: session.id,
|
|
73216
|
-
projectId: session.projectId,
|
|
73217
|
-
command: session.command,
|
|
73218
|
-
args: session.args,
|
|
73219
|
-
cwd: session.cwd,
|
|
73220
|
-
cols: 80,
|
|
73221
|
-
rows: 24,
|
|
73222
|
-
env: buildPtyEnv(process.env, terminalEnv, session.command),
|
|
73223
|
-
...fallback ? { fallback: { ...fallback, env: buildPtyEnv(process.env, terminalEnv, fallback.command) } } : {}
|
|
73224
|
-
} : void 0
|
|
73225
|
-
});
|
|
73226
|
-
runtimeRegistry.createRuntime(session.id, runtime);
|
|
73227
|
-
runtimeRegistry.ensureRecorder(session.id, createTerminalRuntimeRecorder(terminalSessionManager, session.id));
|
|
73228
|
-
return runtime;
|
|
73229
|
-
})().catch((error2) => {
|
|
73230
|
-
if (error2 instanceof Error && error2.message === "HOST_SESSION_GONE") {
|
|
73231
|
-
options.terminalSessionManager.markExited(options.session.id);
|
|
73232
|
-
}
|
|
73233
|
-
throw error2;
|
|
73234
|
-
}).finally(() => {
|
|
73249
|
+
const launch = attachOrRebuild(options).finally(() => {
|
|
73235
73250
|
launches.delete(options.session.id);
|
|
73236
73251
|
});
|
|
73237
73252
|
launches.set(options.session.id, launch);
|
|
73238
73253
|
return launch;
|
|
73239
73254
|
}
|
|
73255
|
+
async function attachOrRebuild(options) {
|
|
73256
|
+
const { session, terminalSessionManager, runtimeRegistry } = options;
|
|
73257
|
+
const existing = runtimeRegistry.getSessionRuntime(session.id);
|
|
73258
|
+
if (existing) return { runtime: existing };
|
|
73259
|
+
let runtime;
|
|
73260
|
+
let warning;
|
|
73261
|
+
try {
|
|
73262
|
+
runtime = await launchHostedTerminal(options, !session.ptyHost);
|
|
73263
|
+
} catch (error2) {
|
|
73264
|
+
if (!(error2 instanceof Error) || error2.message !== "HOST_SESSION_GONE" || session.status !== "running") throw error2;
|
|
73265
|
+
({ runtime, warning } = await rebuildHostedTerminal(options));
|
|
73266
|
+
}
|
|
73267
|
+
runtimeRegistry.createRuntime(session.id, runtime);
|
|
73268
|
+
runtimeRegistry.ensureRecorder(session.id, createTerminalRuntimeRecorder(terminalSessionManager, session.id));
|
|
73269
|
+
return { runtime, warning };
|
|
73270
|
+
}
|
|
73271
|
+
async function launchHostedTerminal(options, creating) {
|
|
73272
|
+
const { session, terminalSessionManager } = options;
|
|
73273
|
+
let binding = session.ptyHost;
|
|
73274
|
+
if (creating) {
|
|
73275
|
+
binding = { hostInstanceId: (await getPtyHost()).descriptor.hostInstanceId, sessionInstanceId: (0, import_node_crypto16.randomUUID)() };
|
|
73276
|
+
await terminalSessionManager.updateRuntimeMetadata(session.id, { runtimeKind: "pty", ptyHost: binding, recoverable: true });
|
|
73277
|
+
}
|
|
73278
|
+
if (!binding) throw new Error("HOST_SESSION_GONE");
|
|
73279
|
+
const fallback = creating ? resolveTerminalFallbackLaunchConfig(session) : null;
|
|
73280
|
+
const terminalEnv = buildTerminalRuntimeEnvironment({ terminalSessionId: session.id, projectId: session.projectId, source: session.source });
|
|
73281
|
+
return createHostedPty({
|
|
73282
|
+
terminalSessionId: session.id,
|
|
73283
|
+
binding,
|
|
73284
|
+
onLaunch: async (launch) => {
|
|
73285
|
+
if (launch.fallbackReason) logger.warn("terminal.pty-host.fallback.activated", { terminalSessionId: session.id, command: launch.command, reason: launch.fallbackReason });
|
|
73286
|
+
await terminalSessionManager.updateSessionLaunch(session.id, { command: launch.command, args: launch.args });
|
|
73287
|
+
},
|
|
73288
|
+
create: creating ? {
|
|
73289
|
+
sessionInstanceId: binding.sessionInstanceId,
|
|
73290
|
+
terminalSessionId: session.id,
|
|
73291
|
+
projectId: session.projectId,
|
|
73292
|
+
command: session.command,
|
|
73293
|
+
args: session.args,
|
|
73294
|
+
cwd: session.cwd,
|
|
73295
|
+
cols: 80,
|
|
73296
|
+
rows: 24,
|
|
73297
|
+
env: buildPtyEnv(process.env, terminalEnv, session.command),
|
|
73298
|
+
...fallback ? { fallback: { ...fallback, env: buildPtyEnv(process.env, terminalEnv, fallback.command) } } : {}
|
|
73299
|
+
} : void 0
|
|
73300
|
+
});
|
|
73301
|
+
}
|
|
73302
|
+
async function rebuildHostedTerminal(options) {
|
|
73303
|
+
const { session, terminalSessionManager } = options;
|
|
73304
|
+
const interactive = isInteractiveShellLaunch(session);
|
|
73305
|
+
const thread = interactive ? resolveAgentThreadToResume(session) : null;
|
|
73306
|
+
let warning = "Command exited; returned to a shell.";
|
|
73307
|
+
if (interactive) {
|
|
73308
|
+
try {
|
|
73309
|
+
const attempt = recordTerminalRebuildAttempt(rebuildAttempts, session.id);
|
|
73310
|
+
warning = thread ? `Original PTY Host session was lost; starting ${thread.provider} resume from saved threadId (${attempt.count}/${attempt.maxAttempts}).` : `Original PTY Host session was lost; created a fresh terminal session (${attempt.count}/${attempt.maxAttempts}).`;
|
|
73311
|
+
} catch (error2) {
|
|
73312
|
+
if (error2 instanceof TerminalRebuildLimitError) {
|
|
73313
|
+
await terminalSessionManager.updateRuntimeMetadata(session.id, { runtimeKind: "pty", ptyHost: session.ptyHost, recoverable: false });
|
|
73314
|
+
terminalSessionManager.markExited(session.id, 1);
|
|
73315
|
+
}
|
|
73316
|
+
throw error2;
|
|
73317
|
+
}
|
|
73318
|
+
} else {
|
|
73319
|
+
await terminalSessionManager.updateSessionLaunch(session.id, resolveDefaultTerminalLaunchConfig());
|
|
73320
|
+
await terminalSessionManager.updateSessionMetadata(session.id, { cwd: session.cwd, activeCommand: null });
|
|
73321
|
+
terminalSessionManager.markRunning(session.id);
|
|
73322
|
+
}
|
|
73323
|
+
const sessionFile = thread ? await getAgentAdapter(thread.provider).resolveResumeTarget(thread.threadId, session.pi) : void 0;
|
|
73324
|
+
const runtime = await launchHostedTerminal(options, true);
|
|
73325
|
+
try {
|
|
73326
|
+
if (thread) {
|
|
73327
|
+
const command = buildAgentResumeCommand({ ...thread, sessionFile, shell: session.command });
|
|
73328
|
+
await runtime.hosted.writeSteps([{ type: "text", data: command.replace(/\n$/, "") }, { type: "delay", ms: 200 }, { type: "text", data: "\r" }], `recovery:${session.ptyHost.sessionInstanceId}`);
|
|
73329
|
+
await terminalSessionManager.updateSessionThreadId(session.id, thread.threadId, thread.provider);
|
|
73330
|
+
}
|
|
73331
|
+
} catch (error2) {
|
|
73332
|
+
runtime.dispose();
|
|
73333
|
+
throw error2;
|
|
73334
|
+
}
|
|
73335
|
+
logger.warn("terminal.pty-host.session-missing.rebuild", { terminalSessionId: session.id, warning });
|
|
73336
|
+
return { runtime, warning };
|
|
73337
|
+
}
|
|
73240
73338
|
async function reconcileHostedTerminals(manager, registry2) {
|
|
73241
73339
|
if (!usesPtyHost()) return;
|
|
73242
73340
|
for (const session of manager.listSessions()) {
|
|
73243
73341
|
if (session.runtimeKind !== "pty" || session.status !== "running") continue;
|
|
73244
73342
|
if (!session.ptyHost) {
|
|
73245
|
-
|
|
73343
|
+
manager.markExited(session.id);
|
|
73246
73344
|
continue;
|
|
73247
73345
|
}
|
|
73248
73346
|
try {
|
|
@@ -73296,8 +73394,6 @@ var import_node_fs16 = require("node:fs");
|
|
|
73296
73394
|
var import_node_path25 = __toESM(require("node:path"), 1);
|
|
73297
73395
|
var RUNWEAVE_TMUX_PREFIX = "runweave-";
|
|
73298
73396
|
var TmuxCommandTimeoutMs = 5e3;
|
|
73299
|
-
var RebuildWindowMs = 6e4;
|
|
73300
|
-
var MaxRebuildAttempts = 3;
|
|
73301
73397
|
var CaptureHistoryLines = 5e3;
|
|
73302
73398
|
var InteractivePaneReadyMinWaitMs = 1e3;
|
|
73303
73399
|
var InteractivePaneReadyStableMs = 200;
|
|
@@ -74050,28 +74146,13 @@ var TmuxSessionService = class extends TmuxProcess {
|
|
|
74050
74146
|
return orphanedSessions;
|
|
74051
74147
|
}
|
|
74052
74148
|
recordRebuildAttempt(terminalSessionId) {
|
|
74053
|
-
|
|
74054
|
-
|
|
74055
|
-
|
|
74056
|
-
(
|
|
74057
|
-
|
|
74058
|
-
|
|
74059
|
-
this.rebuildAttempts.set(terminalSessionId, attempts);
|
|
74060
|
-
throw new TmuxRebuildLimitError(
|
|
74061
|
-
terminalSessionId,
|
|
74062
|
-
attempts.length + 1,
|
|
74063
|
-
RebuildWindowMs,
|
|
74064
|
-
MaxRebuildAttempts
|
|
74065
|
-
);
|
|
74149
|
+
try {
|
|
74150
|
+
return recordTerminalRebuildAttempt(this.rebuildAttempts, terminalSessionId, this.now());
|
|
74151
|
+
} catch (error2) {
|
|
74152
|
+
if (error2 instanceof TerminalRebuildLimitError)
|
|
74153
|
+
throw new TmuxRebuildLimitError(error2.terminalSessionId, error2.count, error2.windowMs, error2.maxAttempts);
|
|
74154
|
+
throw error2;
|
|
74066
74155
|
}
|
|
74067
|
-
attempts.push(now2);
|
|
74068
|
-
this.rebuildAttempts.set(terminalSessionId, attempts);
|
|
74069
|
-
return {
|
|
74070
|
-
allowed: true,
|
|
74071
|
-
count: attempts.length,
|
|
74072
|
-
windowMs: RebuildWindowMs,
|
|
74073
|
-
maxAttempts: MaxRebuildAttempts
|
|
74074
|
-
};
|
|
74075
74156
|
}
|
|
74076
74157
|
};
|
|
74077
74158
|
|
|
@@ -74812,7 +74893,7 @@ async function ensureTerminalRuntime(options) {
|
|
|
74812
74893
|
};
|
|
74813
74894
|
});
|
|
74814
74895
|
}
|
|
74815
|
-
if (options.session.ptyHost || usesPtyHost()) return
|
|
74896
|
+
if (options.session.ptyHost || usesPtyHost()) return ensureHostedTerminal(options);
|
|
74816
74897
|
const runtime = options.ptyService.spawnSession({
|
|
74817
74898
|
command: options.session.command,
|
|
74818
74899
|
args: options.session.args,
|
|
@@ -74852,19 +74933,6 @@ async function ensureTerminalRuntime(options) {
|
|
|
74852
74933
|
function isInteractiveShellLaunch2(command, args) {
|
|
74853
74934
|
return isInteractiveShellLaunch({ command, args });
|
|
74854
74935
|
}
|
|
74855
|
-
function resolveAgentThreadToResume(session) {
|
|
74856
|
-
const activeProvider = getAgentForCommand(session.activeCommand);
|
|
74857
|
-
if (!activeProvider) {
|
|
74858
|
-
return null;
|
|
74859
|
-
}
|
|
74860
|
-
const currentThreadId = session.threadId?.trim();
|
|
74861
|
-
const currentProvider = session.threadProvider ?? (currentThreadId ? "codex" : void 0);
|
|
74862
|
-
if (currentThreadId && currentProvider === activeProvider) {
|
|
74863
|
-
return { provider: activeProvider, threadId: currentThreadId };
|
|
74864
|
-
}
|
|
74865
|
-
const recentThreadId = session.lastThreadId?.trim();
|
|
74866
|
-
return recentThreadId && session.lastThreadProvider === activeProvider ? { provider: activeProvider, threadId: recentThreadId } : null;
|
|
74867
|
-
}
|
|
74868
74936
|
function createTmuxInputPacedRuntime(runtime) {
|
|
74869
74937
|
const queuedInput = [];
|
|
74870
74938
|
let holdInputUntil = 0;
|
|
@@ -112268,6 +112336,9 @@ function isRemoteBrowserProfileState(value) {
|
|
|
112268
112336
|
|
|
112269
112337
|
// backend/src/remote/browser-bindings.ts
|
|
112270
112338
|
var import_node_crypto55 = require("node:crypto");
|
|
112339
|
+
function matchesOwner(owner, binding) {
|
|
112340
|
+
return owner.desktopId === binding.desktopId && owner.hostId === binding.hostId && (owner.ownerKeyHash ? owner.ownerKeyHash === binding.ownerKeyHash : owner.ownerSessionId === binding.ownerSessionId);
|
|
112341
|
+
}
|
|
112271
112342
|
var RemoteBrowserError = class extends Error {
|
|
112272
112343
|
constructor(code, status, message2) {
|
|
112273
112344
|
super(message2);
|
|
@@ -112280,10 +112351,10 @@ var DesktopBrowserBindings = class {
|
|
|
112280
112351
|
this.sessions = sessions;
|
|
112281
112352
|
}
|
|
112282
112353
|
bindings = /* @__PURE__ */ new Map();
|
|
112283
|
-
|
|
112354
|
+
pendingSelection = Promise.resolve();
|
|
112284
112355
|
capabilities = /* @__PURE__ */ new Map();
|
|
112285
112356
|
async bind(ownerSessionId, input2) {
|
|
112286
|
-
if (!input2 || input2.protocolVersion !== 2 || !/^[a-zA-Z0-9_-]{1,128}$/.test(input2.desktopId) || !/^[a-zA-Z0-9_-]{1,128}$/.test(input2.hostId) || !Number.isInteger(input2.generation) || input2.generation < 1 || !Number.isInteger(input2.reversePort) || input2.reversePort < 1 || input2.reversePort > 65535 || !/^[0-9a-f]{64}$/.test(input2.gatewayKey)) {
|
|
112357
|
+
if (!input2 || input2.protocolVersion !== 2 || !/^[a-zA-Z0-9_-]{1,128}$/.test(input2.desktopId) || !/^[a-zA-Z0-9_-]{1,128}$/.test(input2.hostId) || !Number.isInteger(input2.generation) || input2.generation < 1 || !Number.isInteger(input2.reversePort) || input2.reversePort < 1 || input2.reversePort > 65535 || !/^[0-9a-f]{64}$/.test(input2.gatewayKey) || input2.ownerKey !== void 0 && (typeof input2.ownerKey !== "string" || !/^[0-9a-f]{64}$/.test(input2.ownerKey))) {
|
|
112287
112358
|
throw new RemoteBrowserError(
|
|
112288
112359
|
"BROWSER_SCOPE_DENIED",
|
|
112289
112360
|
400,
|
|
@@ -112311,10 +112382,11 @@ var DesktopBrowserBindings = class {
|
|
|
112311
112382
|
"Desktop bridge identity does not match"
|
|
112312
112383
|
);
|
|
112313
112384
|
}
|
|
112385
|
+
const ownerKeyHash = input2.ownerKey ? (0, import_node_crypto55.createHash)("sha256").update(input2.ownerKey).digest("hex") : void 0;
|
|
112314
112386
|
let existingId;
|
|
112315
112387
|
for (const [id7, binding] of this.bindings) {
|
|
112316
|
-
if (binding.ownerSessionId === ownerSessionId && binding.desktopId === input2.desktopId && binding.hostId === input2.hostId) {
|
|
112317
|
-
if (binding.generation === input2.generation) existingId = id7;
|
|
112388
|
+
if ((binding.ownerSessionId === ownerSessionId || !!ownerKeyHash && binding.ownerKeyHash === ownerKeyHash) && binding.desktopId === input2.desktopId && binding.hostId === input2.hostId) {
|
|
112389
|
+
if (binding.ownerSessionId === ownerSessionId && binding.generation === input2.generation) existingId = id7;
|
|
112318
112390
|
this.bindings.delete(id7);
|
|
112319
112391
|
}
|
|
112320
112392
|
}
|
|
@@ -112322,6 +112394,7 @@ var DesktopBrowserBindings = class {
|
|
|
112322
112394
|
id: existingId ?? (0, import_node_crypto55.randomUUID)(),
|
|
112323
112395
|
protocolVersion: 2,
|
|
112324
112396
|
ownerSessionId,
|
|
112397
|
+
ownerKeyHash,
|
|
112325
112398
|
desktopId: input2.desktopId,
|
|
112326
112399
|
hostId: input2.hostId,
|
|
112327
112400
|
generation: input2.generation,
|
|
@@ -112361,7 +112434,16 @@ var DesktopBrowserBindings = class {
|
|
|
112361
112434
|
return this.liveBindings().filter((binding) => binding.ownerSessionId === ownerSessionId).map((binding) => this.publicBinding(binding));
|
|
112362
112435
|
}
|
|
112363
112436
|
select(ownerSessionId, terminalSessionId, bindingId) {
|
|
112364
|
-
|
|
112437
|
+
const operation = this.pendingSelection.then(
|
|
112438
|
+
() => this.selectBinding(ownerSessionId, terminalSessionId, bindingId)
|
|
112439
|
+
);
|
|
112440
|
+
this.pendingSelection = operation.catch(() => {
|
|
112441
|
+
});
|
|
112442
|
+
return operation;
|
|
112443
|
+
}
|
|
112444
|
+
async selectBinding(ownerSessionId, terminalSessionId, bindingId) {
|
|
112445
|
+
const session = this.sessions.getSession(terminalSessionId);
|
|
112446
|
+
if (!session)
|
|
112365
112447
|
throw new RemoteBrowserError(
|
|
112366
112448
|
"BROWSER_SCOPE_DENIED",
|
|
112367
112449
|
404,
|
|
@@ -112376,9 +112458,11 @@ var DesktopBrowserBindings = class {
|
|
|
112376
112458
|
403,
|
|
112377
112459
|
"Desktop binding is not owned by this session"
|
|
112378
112460
|
);
|
|
112379
|
-
const previous =
|
|
112380
|
-
if (previous && (previous
|
|
112381
|
-
|
|
112461
|
+
const previous = session.browserBinding;
|
|
112462
|
+
if (previous && matchesOwner(previous, binding) && previous.ownerKeyHash === binding.ownerKeyHash)
|
|
112463
|
+
return;
|
|
112464
|
+
if (previous && !matchesOwner(previous, binding) && this.liveBindings().some(
|
|
112465
|
+
(candidate) => matchesOwner(previous, candidate)
|
|
112382
112466
|
)) {
|
|
112383
112467
|
throw new RemoteBrowserError(
|
|
112384
112468
|
"BROWSER_BINDING_CONFLICT",
|
|
@@ -112386,20 +112470,21 @@ var DesktopBrowserBindings = class {
|
|
|
112386
112470
|
"Terminal already belongs to another desktop"
|
|
112387
112471
|
);
|
|
112388
112472
|
}
|
|
112389
|
-
this.
|
|
112473
|
+
await this.sessions.updateSessionBrowserBinding(terminalSessionId, {
|
|
112390
112474
|
desktopId: binding.desktopId,
|
|
112391
112475
|
hostId: binding.hostId,
|
|
112392
|
-
ownerSessionId: binding.ownerSessionId
|
|
112476
|
+
ownerSessionId: binding.ownerSessionId,
|
|
112477
|
+
ownerKeyHash: binding.ownerKeyHash
|
|
112393
112478
|
});
|
|
112394
112479
|
}
|
|
112395
112480
|
selectedBinding(terminalSessionId) {
|
|
112396
112481
|
const candidates = this.liveBindings();
|
|
112397
|
-
const owner = this.
|
|
112482
|
+
const owner = this.sessions.getSession(terminalSessionId)?.browserBinding;
|
|
112398
112483
|
const selected = candidates.find(
|
|
112399
|
-
(binding) =>
|
|
112484
|
+
(binding) => !!owner && matchesOwner(owner, binding)
|
|
112400
112485
|
);
|
|
112401
112486
|
if (selected) return selected;
|
|
112402
|
-
if (
|
|
112487
|
+
if (owner)
|
|
112403
112488
|
throw new RemoteBrowserError(
|
|
112404
112489
|
"DESKTOP_UNAVAILABLE",
|
|
112405
112490
|
503,
|
|
@@ -112685,14 +112770,14 @@ function registerRemoteBrowserRoutes(app, auth, sessions, requireTunnelAuth, bro
|
|
|
112685
112770
|
}
|
|
112686
112771
|
res.json(bindings.list(owner));
|
|
112687
112772
|
});
|
|
112688
|
-
app.put("/api/terminal/session/:id/browser/binding", requireAuth, (req, res) => {
|
|
112773
|
+
app.put("/api/terminal/session/:id/browser/binding", requireAuth, async (req, res) => {
|
|
112689
112774
|
const owner = auth.verifyAccessToken(readBearerToken(req) ?? "")?.sessionId;
|
|
112690
112775
|
if (!owner || typeof req.body?.bindingId !== "string") {
|
|
112691
112776
|
res.sendStatus(400);
|
|
112692
112777
|
return;
|
|
112693
112778
|
}
|
|
112694
112779
|
try {
|
|
112695
|
-
bindings.select(owner, String(req.params.id), req.body.bindingId);
|
|
112780
|
+
await bindings.select(owner, String(req.params.id), req.body.bindingId);
|
|
112696
112781
|
res.sendStatus(204);
|
|
112697
112782
|
} catch (error2) {
|
|
112698
112783
|
sendError(res, error2);
|
|
@@ -126764,6 +126849,7 @@ function toPersistedProject(project) {
|
|
|
126764
126849
|
}
|
|
126765
126850
|
function buildSessionRecord(persisted) {
|
|
126766
126851
|
return {
|
|
126852
|
+
browserBinding: persisted.browserBinding,
|
|
126767
126853
|
source: persisted.source,
|
|
126768
126854
|
id: persisted.id,
|
|
126769
126855
|
projectId: persisted.projectId,
|
|
@@ -126827,6 +126913,7 @@ function createRuntimeRecord(record3, options) {
|
|
|
126827
126913
|
}
|
|
126828
126914
|
function toPersistedSession(session) {
|
|
126829
126915
|
return {
|
|
126916
|
+
browserBinding: session.browserBinding,
|
|
126830
126917
|
source: session.source,
|
|
126831
126918
|
id: session.id,
|
|
126832
126919
|
projectId: session.projectId,
|
|
@@ -128544,6 +128631,13 @@ var TerminalManagerPanelOperations = class extends TerminalManagerSessionRuntime
|
|
|
128544
128631
|
// backend/src/terminal/manager/manager.ts
|
|
128545
128632
|
var TerminalSessionManager = class extends TerminalManagerPanelOperations {
|
|
128546
128633
|
pendingSessionMove = Promise.resolve();
|
|
128634
|
+
async updateSessionBrowserBinding(terminalSessionId, owner) {
|
|
128635
|
+
const session = this.sessions.get(terminalSessionId);
|
|
128636
|
+
if (!session) throw new Error("Terminal session not found");
|
|
128637
|
+
const browserBinding = structuredClone(owner);
|
|
128638
|
+
await this.sessionStore.updateSessionBrowserBinding(terminalSessionId, browserBinding);
|
|
128639
|
+
session.browserBinding = browserBinding;
|
|
128640
|
+
}
|
|
128547
128641
|
moveSession(terminalSessionId, projectId) {
|
|
128548
128642
|
const operation = this.pendingSessionMove.then(async () => {
|
|
128549
128643
|
const session = this.sessions.get(terminalSessionId);
|
|
@@ -130015,6 +130109,7 @@ var import_node_path116 = __toESM(require("node:path"), 1);
|
|
|
130015
130109
|
var import_node_path115 = __toESM(require("node:path"), 1);
|
|
130016
130110
|
function toMetadataRecord(session) {
|
|
130017
130111
|
return {
|
|
130112
|
+
browserBinding: session.browserBinding,
|
|
130018
130113
|
ptyHost: session.ptyHost,
|
|
130019
130114
|
source: session.source,
|
|
130020
130115
|
feishuNotificationState: session.feishuNotificationState,
|
|
@@ -130599,6 +130694,17 @@ var LowDbPanelStore = class extends LowDbScrollbackStore {
|
|
|
130599
130694
|
|
|
130600
130695
|
// backend/src/terminal/store/lowdb-store.ts
|
|
130601
130696
|
var LowDbTerminalSessionStore = class extends LowDbPanelStore {
|
|
130697
|
+
async updateSessionBrowserBinding(terminalSessionId, owner) {
|
|
130698
|
+
const browserBinding = structuredClone(owner);
|
|
130699
|
+
await this.enqueueWrite(async () => {
|
|
130700
|
+
const database = this.getDatabase();
|
|
130701
|
+
if (!database.data.sessions.some((session) => session.id === terminalSessionId))
|
|
130702
|
+
throw new Error("Terminal session not found");
|
|
130703
|
+
const sessions = database.data.sessions.map((session) => session.id === terminalSessionId ? { ...session, browserBinding } : session);
|
|
130704
|
+
await database.adapter.write({ ...database.data, sessions });
|
|
130705
|
+
database.data.sessions = sessions;
|
|
130706
|
+
});
|
|
130707
|
+
}
|
|
130602
130708
|
async moveSession(terminalSessionId, projectId, orderedIds) {
|
|
130603
130709
|
await this.enqueueWrite(async () => {
|
|
130604
130710
|
const database = this.getDatabase();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{aY as L,bm as ln,aI as A,aW as P,aH as W,bn as gn,bo as dn,bp as hn,bq as z,br as pn,bs as An,bt as m,aZ as N,b2 as U,b5 as T,bu as _n,b0 as on,bv as wn,bw as On,aJ as V,bx as vn,by as R}from"./index-
|
|
1
|
+
import{aY as L,bm as ln,aI as A,aW as P,aH as W,bn as gn,bo as dn,bp as hn,bq as z,br as pn,bs as An,bt as m,aZ as N,b2 as U,b5 as T,bu as _n,b0 as on,bv as wn,bw as On,aJ as V,bx as vn,by as R}from"./index-BBNE8InR.js";var Pn="[object Symbol]";function x(n){return typeof n=="symbol"||L(n)&&ln(n)==Pn}function bn(n,r){for(var e=-1,i=n==null?0:n.length,f=Array(i);++e<i;)f[e]=r(n[e],e,n);return f}var B=P?P.prototype:void 0,H=B?B.toString:void 0;function k(n){if(typeof n=="string")return n;if(A(n))return bn(n,k)+"";if(x(n))return H?H.call(n):"";var r=n+"";return r=="0"&&1/n==-1/0?"-0":r}function yn(){}function En(n,r){for(var e=-1,i=n==null?0:n.length;++e<i&&r(n[e],e,n)!==!1;);return n}function cn(n,r,e,i){for(var f=n.length,t=e+-1;++t<f;)if(r(n[t],t,n))return t;return-1}function Tn(n){return n!==n}function In(n,r,e){for(var i=e-1,f=n.length;++i<f;)if(n[i]===r)return i;return-1}function Rn(n,r,e){return r===r?In(n,r,e):cn(n,Tn,e)}function Sn(n,r){var e=n==null?0:n.length;return!!e&&Rn(n,r,0)>-1}function M(n){return W(n)?gn(n):dn(n)}var Ln=/\.|\[(?:[^[\]]*|(["'])(?:(?!\1)[^\\]|\\.)*?\1)\]/,xn=/^\w*$/;function $(n,r){if(A(n))return!1;var e=typeof n;return e=="number"||e=="symbol"||e=="boolean"||n==null||x(n)?!0:xn.test(n)||!Ln.test(n)||r!=null&&n in Object(r)}var Mn=500;function $n(n){var r=hn(n,function(i){return e.size===Mn&&e.clear(),i}),e=r.cache;return r}var Cn=/[^.[\]]+|\[(?:(-?\d+(?:\.\d+)?)|(["'])((?:(?!\2)[^\\]|\\.)*?)\2)\]|(?=(?:\.|\[\])(?:\.|\[\]|$))/g,Dn=/\\(\\)?/g,Fn=$n(function(n){var r=[];return n.charCodeAt(0)===46&&r.push(""),n.replace(Cn,function(e,i,f,t){r.push(f?t.replace(Dn,"$1"):i||e)}),r});function Gn(n){return n==null?"":k(n)}function j(n,r){return A(n)?n:$(n,r)?[n]:Fn(Gn(n))}function I(n){if(typeof n=="string"||x(n))return n;var r=n+"";return r=="0"&&1/n==-1/0?"-0":r}function nn(n,r){r=j(r,n);for(var e=0,i=r.length;n!=null&&e<i;)n=n[I(r[e++])];return e&&e==i?n:void 0}function mn(n,r,e){var i=n==null?void 0:nn(n,r);return i===void 0?e:i}function rn(n,r){for(var e=-1,i=r.length,f=n.length;++e<i;)n[f+e]=r[e];return n}var K=P?P.isConcatSpreadable:void 0;function Nn(n){return A(n)||z(n)||!!(K&&n&&n[K])}function Kr(n,r,e,i,f){var t=-1,s=n.length;for(e||(e=Nn),f||(f=[]);++t<s;){var u=n[t];e(u)?rn(f,u):i||(f[f.length]=u)}return f}function Un(n,r,e,i){var f=-1,t=n==null?0:n.length;for(i&&t&&(e=n[++f]);++f<t;)e=r(e,n[f],f,n);return e}function en(n,r){for(var e=-1,i=n==null?0:n.length,f=0,t=[];++e<i;){var s=n[e];r(s,e,n)&&(t[f++]=s)}return t}function Bn(){return[]}var Hn=Object.prototype,Kn=Hn.propertyIsEnumerable,q=Object.getOwnPropertySymbols,qn=q?function(n){return n==null?[]:(n=Object(n),en(q(n),function(r){return Kn.call(n,r)}))}:Bn;function Zn(n,r,e){var i=r(n);return A(n)?i:rn(i,e(n))}function Z(n){return Zn(n,M,qn)}var Yn="__lodash_hash_undefined__";function Jn(n){return this.__data__.set(n,Yn),this}function Xn(n){return this.__data__.has(n)}function b(n){var r=-1,e=n==null?0:n.length;for(this.__data__=new pn;++r<e;)this.add(n[r])}b.prototype.add=b.prototype.push=Jn;b.prototype.has=Xn;function Qn(n,r){for(var e=-1,i=n==null?0:n.length;++e<i;)if(r(n[e],e,n))return!0;return!1}function tn(n,r){return n.has(r)}var Wn=1,zn=2;function fn(n,r,e,i,f,t){var s=e&Wn,u=n.length,a=r.length;if(u!=a&&!(s&&a>u))return!1;var h=t.get(n),g=t.get(r);if(h&&g)return h==r&&g==n;var l=-1,d=!0,o=e&zn?new b:void 0;for(t.set(n,r),t.set(r,n);++l<u;){var p=n[l],_=r[l];if(i)var w=s?i(_,p,l,r,n,t):i(p,_,l,n,r,t);if(w!==void 0){if(w)continue;d=!1;break}if(o){if(!Qn(r,function(O,v){if(!tn(o,v)&&(p===O||f(p,O,e,i,t)))return o.push(v)})){d=!1;break}}else if(!(p===_||f(p,_,e,i,t))){d=!1;break}}return t.delete(n),t.delete(r),d}function Vn(n){var r=-1,e=Array(n.size);return n.forEach(function(i,f){e[++r]=[f,i]}),e}function C(n){var r=-1,e=Array(n.size);return n.forEach(function(i){e[++r]=i}),e}var kn=1,jn=2,nr="[object Boolean]",rr="[object Date]",er="[object Error]",ir="[object Map]",tr="[object Number]",fr="[object RegExp]",sr="[object Set]",ur="[object String]",ar="[object Symbol]",lr="[object ArrayBuffer]",gr="[object DataView]",Y=P?P.prototype:void 0,S=Y?Y.valueOf:void 0;function dr(n,r,e,i,f,t,s){switch(e){case gr:if(n.byteLength!=r.byteLength||n.byteOffset!=r.byteOffset)return!1;n=n.buffer,r=r.buffer;case lr:return!(n.byteLength!=r.byteLength||!t(new m(n),new m(r)));case nr:case rr:case tr:return An(+n,+r);case er:return n.name==r.name&&n.message==r.message;case fr:case ur:return n==r+"";case ir:var u=Vn;case sr:var a=i&kn;if(u||(u=C),n.size!=r.size&&!a)return!1;var h=s.get(n);if(h)return h==r;i|=jn,s.set(n,r);var g=fn(u(n),u(r),i,f,t,s);return s.delete(n),g;case ar:if(S)return S.call(n)==S.call(r)}return!1}var hr=1,pr=Object.prototype,Ar=pr.hasOwnProperty;function _r(n,r,e,i,f,t){var s=e&hr,u=Z(n),a=u.length,h=Z(r),g=h.length;if(a!=g&&!s)return!1;for(var l=a;l--;){var d=u[l];if(!(s?d in r:Ar.call(r,d)))return!1}var o=t.get(n),p=t.get(r);if(o&&p)return o==r&&p==n;var _=!0;t.set(n,r),t.set(r,n);for(var w=s;++l<a;){d=u[l];var O=n[d],v=r[d];if(i)var G=s?i(v,O,d,r,n,t):i(O,v,d,n,r,t);if(!(G===void 0?O===v||f(O,v,e,i,t):G)){_=!1;break}w||(w=d=="constructor")}if(_&&!w){var y=n.constructor,E=r.constructor;y!=E&&"constructor"in n&&"constructor"in r&&!(typeof y=="function"&&y instanceof y&&typeof E=="function"&&E instanceof E)&&(_=!1)}return t.delete(n),t.delete(r),_}var or=1,J="[object Arguments]",X="[object Array]",c="[object Object]",wr=Object.prototype,Q=wr.hasOwnProperty;function Or(n,r,e,i,f,t){var s=A(n),u=A(r),a=s?X:N(n),h=u?X:N(r);a=a==J?c:a,h=h==J?c:h;var g=a==c,l=h==c,d=a==h;if(d&&U(n)){if(!U(r))return!1;s=!0,g=!1}if(d&&!g)return t||(t=new T),s||_n(n)?fn(n,r,e,i,f,t):dr(n,r,a,e,i,f,t);if(!(e&or)){var o=g&&Q.call(n,"__wrapped__"),p=l&&Q.call(r,"__wrapped__");if(o||p){var _=o?n.value():n,w=p?r.value():r;return t||(t=new T),f(_,w,e,i,t)}}return d?(t||(t=new T),_r(n,r,e,i,f,t)):!1}function D(n,r,e,i,f){return n===r?!0:n==null||r==null||!L(n)&&!L(r)?n!==n&&r!==r:Or(n,r,e,i,D,f)}var vr=1,Pr=2;function br(n,r,e,i){var f=e.length,t=f;if(n==null)return!t;for(n=Object(n);f--;){var s=e[f];if(s[2]?s[1]!==n[s[0]]:!(s[0]in n))return!1}for(;++f<t;){s=e[f];var u=s[0],a=n[u],h=s[1];if(s[2]){if(a===void 0&&!(u in n))return!1}else{var g=new T,l;if(!(l===void 0?D(h,a,vr|Pr,i,g):l))return!1}}return!0}function sn(n){return n===n&&!on(n)}function yr(n){for(var r=M(n),e=r.length;e--;){var i=r[e],f=n[i];r[e]=[i,f,sn(f)]}return r}function un(n,r){return function(e){return e==null?!1:e[n]===r&&(r!==void 0||n in Object(e))}}function Er(n){var r=yr(n);return r.length==1&&r[0][2]?un(r[0][0],r[0][1]):function(e){return e===n||br(e,n,r)}}function cr(n,r){return n!=null&&r in Object(n)}function Tr(n,r,e){r=j(r,n);for(var i=-1,f=r.length,t=!1;++i<f;){var s=I(r[i]);if(!(t=n!=null&&e(n,s)))break;n=n[s]}return t||++i!=f?t:(f=n==null?0:n.length,!!f&&wn(f)&&On(s,f)&&(A(n)||z(n)))}function Ir(n,r){return n!=null&&Tr(n,r,cr)}var Rr=1,Sr=2;function Lr(n,r){return $(n)&&sn(r)?un(I(n),r):function(e){var i=mn(e,n);return i===void 0&&i===r?Ir(e,n):D(r,i,Rr|Sr)}}function xr(n){return function(r){return r==null?void 0:r[n]}}function Mr(n){return function(r){return nn(r,n)}}function $r(n){return $(n)?xr(I(n)):Mr(n)}function an(n){return typeof n=="function"?n:n==null?V:typeof n=="object"?A(n)?Lr(n[0],n[1]):Er(n):$r(n)}function Cr(n,r){return n&&vn(n,r,M)}function Dr(n,r){return function(e,i){if(e==null)return e;if(!W(e))return n(e,i);for(var f=e.length,t=-1,s=Object(e);++t<f&&i(s[t],t,s)!==!1;);return e}}var F=Dr(Cr);function Fr(n){return typeof n=="function"?n:V}function qr(n,r){var e=A(n)?En:F;return e(n,Fr(r))}function Gr(n,r){var e=[];return F(n,function(i,f,t){r(i,f,t)&&e.push(i)}),e}function Zr(n,r){var e=A(n)?en:Gr;return e(n,an(r))}function mr(n,r,e,i,f){return f(n,function(t,s,u){e=i?(i=!1,t):r(e,t,s,u)}),e}function Yr(n,r,e){var i=A(n)?Un:mr,f=arguments.length<3;return i(n,an(r),e,f,F)}var Nr=1/0,Ur=R&&1/C(new R([,-0]))[1]==Nr?function(n){return new R(n)}:yn,Br=200;function Jr(n,r,e){var i=-1,f=Sn,t=n.length,s=!0,u=[],a=u;if(t>=Br){var h=r?null:Ur(n);if(h)return C(h);s=!1,f=tn,a=new b}else a=r?[]:u;n:for(;++i<t;){var g=n[i],l=r?r(g):g;if(g=g!==0?g:0,s&&l===l){for(var d=a.length;d--;)if(a[d]===l)continue n;r&&a.push(l),u.push(g)}else f(a,l,e)||(a!==u&&a.push(l),u.push(g))}return u}export{F as a,Kr as b,an as c,bn as d,rn as e,Zn as f,qn as g,En as h,x as i,Z as j,M as k,Jr as l,Zr as m,qr as n,cn as o,Fr as p,Cr as q,Yr as r,Bn as s,Tr as t,j as u,I as v,nn as w,Ir as x,Gn as y};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{j as t,r as i}from"./index-D9-cSGu-.js";import{d as r,e as c,C as u,f as d,h as p,M as m}from"./main-
|
|
1
|
+
import{j as t,r as i}from"./index-D9-cSGu-.js";import{d as r,e as c,C as u,f as d,h as p,M as m}from"./main-BHwOPARZ.js";import{S as l}from"./tabs-Y-BEbPyW.js";function g(){var a;const s=r(),e=d(s.connection,s.auth.token,s.auth.clearToken),{open:o,close:n}=e;return i.useEffect(()=>(o(),n),[o,n]),p(!1,e.busy&&((a=e.status)==null?void 0:a.state)==="pending_approval"||!!e.status&&["approved","issuing","issued"].includes(e.status.state)),t.jsx(m,{embedded:!0,controller:e,connectionName:e.connectionName})}function b(){const s=r(),e=new URLSearchParams(c().search).get("section")??"password";return t.jsxs(t.Fragment,{children:[t.jsx(l,{items:[["password","修改密码"],["mobile","连接手机"]],active:e}),e==="mobile"?s.connection?t.jsx(g,{}):t.jsx("p",{children:"请在桌面应用中选择电脑后连接手机。"}):t.jsx(u,{embedded:!0,apiBase:s.apiBase,token:s.auth.token,onAuthExpired:s.auth.clearToken})]})}export{b as default};
|