@eclipse-docks/extension-terminal 0.8.10 → 0.8.12
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/api.d.ts +2 -1
- package/dist/api.d.ts.map +1 -1
- package/dist/api.js +75 -2
- package/dist/api.js.map +1 -0
- package/dist/attached-terminal.d.ts +23 -0
- package/dist/attached-terminal.d.ts.map +1 -0
- package/dist/index.js +1 -1
- package/dist/{js-terminal-backend-DV-i_yft.js → js-terminal-backend-CRxDAwvr.js} +71 -10
- package/dist/js-terminal-backend-CRxDAwvr.js.map +1 -0
- package/dist/js-terminal-backend.d.ts +16 -2
- package/dist/js-terminal-backend.d.ts.map +1 -1
- package/dist/terminal-api.d.ts +3 -1
- package/dist/terminal-api.d.ts.map +1 -1
- package/dist/{terminal-extension-CKb5tCLo.js → terminal-extension-CnPHiXG4.js} +10 -2
- package/dist/{terminal-extension-CKb5tCLo.js.map → terminal-extension-CnPHiXG4.js.map} +1 -1
- package/dist/terminal-extension.d.ts.map +1 -1
- package/dist/terminal-service.d.ts +2 -0
- package/dist/terminal-service.d.ts.map +1 -1
- package/package.json +1 -1
- package/dist/js-terminal-backend-DV-i_yft.js.map +0 -1
package/dist/api.d.ts
CHANGED
|
@@ -3,6 +3,7 @@ export { terminalService, registerTerminalProfile } from './terminal-service';
|
|
|
3
3
|
export { terminalService as terminalTaskRunner } from './terminal-service';
|
|
4
4
|
export { parseTerminalState, serializeTerminalState, emptyTerminalState } from './terminal-persistence';
|
|
5
5
|
export { CommandsBackend } from './commands-backend';
|
|
6
|
-
export { JsReplBackend, JS_REPL_PROFILE_ID } from './js-terminal-backend';
|
|
6
|
+
export { JsReplBackend, JS_REPL_PROFILE_ID, JS_SESSION_PROFILE_ID, createJsSessionBackend, openJsSessionTerminal, unbindJsSession, } from './js-terminal-backend';
|
|
7
|
+
export { AttachedTerminal } from './attached-terminal';
|
|
7
8
|
export { LineInput } from './line-input';
|
|
8
9
|
//# sourceMappingURL=api.d.ts.map
|
package/dist/api.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../src/api.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAC;AAC/B,OAAO,EAAE,eAAe,EAAE,uBAAuB,EAAE,MAAM,oBAAoB,CAAC;AAC9E,OAAO,EAAE,eAAe,IAAI,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAC3E,OAAO,EAAE,kBAAkB,EAAE,sBAAsB,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AACxG,OAAO,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AACrD,OAAO,
|
|
1
|
+
{"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../src/api.ts"],"names":[],"mappings":"AAAA,cAAc,gBAAgB,CAAC;AAC/B,OAAO,EAAE,eAAe,EAAE,uBAAuB,EAAE,MAAM,oBAAoB,CAAC;AAC9E,OAAO,EAAE,eAAe,IAAI,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAC3E,OAAO,EAAE,kBAAkB,EAAE,sBAAsB,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AACxG,OAAO,EAAE,eAAe,EAAE,MAAM,oBAAoB,CAAC;AACrD,OAAO,EACL,aAAa,EACb,kBAAkB,EAClB,qBAAqB,EACrB,sBAAsB,EACtB,qBAAqB,EACrB,eAAe,GAChB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,gBAAgB,EAAE,MAAM,qBAAqB,CAAC;AACvD,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC"}
|
package/dist/api.js
CHANGED
|
@@ -1,2 +1,75 @@
|
|
|
1
|
-
import { _ as
|
|
2
|
-
|
|
1
|
+
import { _ as TERMINAL_PANEL_SETTINGS_KEY, a as openJsSessionTerminal, b as TOPIC_TERMINAL_OPENED, c as LineInput, d as emptyTerminalState, f as parseTerminalState, g as TERMINAL_NEW_DROPDOWN, h as TERMINAL_INSTANCES_TABS_ID, i as createJsSessionBackend, l as registerTerminalProfile, m as TARGET_TERMINAL_PROFILES, n as JS_SESSION_PROFILE_ID, o as unbindJsSession, p as serializeTerminalState, r as JsReplBackend, s as CommandsBackend, t as JS_REPL_PROFILE_ID, u as terminalService, v as TOPIC_TERMINAL_ACTIVE_CHANGED, x as VIEW_TERMINAL, y as TOPIC_TERMINAL_CLOSED } from "./js-terminal-backend-CRxDAwvr.js";
|
|
2
|
+
//#region src/attached-terminal.ts
|
|
3
|
+
/**
|
|
4
|
+
* One terminal tab bound to a caller-owned session.
|
|
5
|
+
* Closing the tab forgets the tab only. release() also drops the session binding.
|
|
6
|
+
*/
|
|
7
|
+
var AttachedTerminal = class {
|
|
8
|
+
constructor(openTerminal, onDiscard) {
|
|
9
|
+
this.openTerminal = openTerminal;
|
|
10
|
+
this.onDiscard = onDiscard;
|
|
11
|
+
this.disposed = false;
|
|
12
|
+
this.generation = 0;
|
|
13
|
+
}
|
|
14
|
+
async show() {
|
|
15
|
+
if (this.disposed) return false;
|
|
16
|
+
if (this.terminal) {
|
|
17
|
+
this.terminal.show();
|
|
18
|
+
return true;
|
|
19
|
+
}
|
|
20
|
+
const generation = this.generation;
|
|
21
|
+
this.opening ??= this.openTerminal();
|
|
22
|
+
try {
|
|
23
|
+
const terminal = await this.opening;
|
|
24
|
+
if (this.disposed || generation !== this.generation) {
|
|
25
|
+
terminal?.dispose({ confirm: false });
|
|
26
|
+
return false;
|
|
27
|
+
}
|
|
28
|
+
const existing = this.currentTerminal();
|
|
29
|
+
if (existing) {
|
|
30
|
+
existing.show();
|
|
31
|
+
return true;
|
|
32
|
+
}
|
|
33
|
+
if (!terminal) return false;
|
|
34
|
+
this.remember(terminal);
|
|
35
|
+
return true;
|
|
36
|
+
} finally {
|
|
37
|
+
if (this.generation === generation) this.opening = void 0;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
release() {
|
|
41
|
+
this.disposed = true;
|
|
42
|
+
this.drop();
|
|
43
|
+
}
|
|
44
|
+
/** Forget the current tab so the next show() attaches the replacement session. */
|
|
45
|
+
reset() {
|
|
46
|
+
this.disposed = false;
|
|
47
|
+
this.drop();
|
|
48
|
+
}
|
|
49
|
+
currentTerminal() {
|
|
50
|
+
return this.terminal;
|
|
51
|
+
}
|
|
52
|
+
remember(terminal) {
|
|
53
|
+
this.terminal = terminal;
|
|
54
|
+
this.unsubscribe = terminalService.onDidCloseTerminal((closed) => {
|
|
55
|
+
if (closed.id !== terminal.id) return;
|
|
56
|
+
this.unsubscribe?.();
|
|
57
|
+
this.unsubscribe = void 0;
|
|
58
|
+
if (this.terminal === terminal) this.terminal = void 0;
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
drop() {
|
|
62
|
+
this.generation += 1;
|
|
63
|
+
this.opening = void 0;
|
|
64
|
+
const terminal = this.terminal;
|
|
65
|
+
this.terminal = void 0;
|
|
66
|
+
this.unsubscribe?.();
|
|
67
|
+
this.unsubscribe = void 0;
|
|
68
|
+
this.onDiscard?.();
|
|
69
|
+
terminal?.dispose({ confirm: false });
|
|
70
|
+
}
|
|
71
|
+
};
|
|
72
|
+
//#endregion
|
|
73
|
+
export { AttachedTerminal, CommandsBackend, JS_REPL_PROFILE_ID, JS_SESSION_PROFILE_ID, JsReplBackend, LineInput, TARGET_TERMINAL_PROFILES, TERMINAL_INSTANCES_TABS_ID, TERMINAL_NEW_DROPDOWN, TERMINAL_PANEL_SETTINGS_KEY, TOPIC_TERMINAL_ACTIVE_CHANGED, TOPIC_TERMINAL_CLOSED, TOPIC_TERMINAL_OPENED, VIEW_TERMINAL, createJsSessionBackend, emptyTerminalState, openJsSessionTerminal, parseTerminalState, registerTerminalProfile, serializeTerminalState, terminalService, terminalService as terminalTaskRunner, unbindJsSession };
|
|
74
|
+
|
|
75
|
+
//# sourceMappingURL=api.js.map
|
package/dist/api.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"api.js","names":[],"sources":["../src/attached-terminal.ts"],"sourcesContent":["import { terminalService } from './terminal-service';\nimport type { Terminal } from './terminal-api';\n\n/**\n * One terminal tab bound to a caller-owned session.\n * Closing the tab forgets the tab only. release() also drops the session binding.\n */\nexport class AttachedTerminal {\n private terminal?: Terminal;\n private unsubscribe?: () => void;\n private opening?: Promise<Terminal | undefined>;\n private disposed = false;\n private generation = 0;\n\n constructor(\n private readonly openTerminal: () => Promise<Terminal | undefined>,\n private readonly onDiscard?: () => void,\n ) {}\n\n async show(): Promise<boolean> {\n if (this.disposed) return false;\n if (this.terminal) {\n this.terminal.show();\n return true;\n }\n\n const generation = this.generation;\n this.opening ??= this.openTerminal();\n try {\n const terminal = await this.opening;\n if (this.disposed || generation !== this.generation) {\n void terminal?.dispose({ confirm: false });\n return false;\n }\n const existing = this.currentTerminal();\n if (existing) {\n existing.show();\n return true;\n }\n if (!terminal) return false;\n this.remember(terminal);\n return true;\n } finally {\n if (this.generation === generation) this.opening = undefined;\n }\n }\n\n release(): void {\n this.disposed = true;\n this.drop();\n }\n\n /** Forget the current tab so the next show() attaches the replacement session. */\n reset(): void {\n this.disposed = false;\n this.drop();\n }\n\n private currentTerminal(): Terminal | undefined {\n return this.terminal;\n }\n\n private remember(terminal: Terminal): void {\n this.terminal = terminal;\n this.unsubscribe = terminalService.onDidCloseTerminal((closed) => {\n if (closed.id !== terminal.id) return;\n this.unsubscribe?.();\n this.unsubscribe = undefined;\n if (this.terminal === terminal) this.terminal = undefined;\n });\n }\n\n private drop(): void {\n this.generation += 1;\n this.opening = undefined;\n const terminal = this.terminal;\n this.terminal = undefined;\n this.unsubscribe?.();\n this.unsubscribe = undefined;\n this.onDiscard?.();\n void terminal?.dispose({ confirm: false });\n }\n}\n"],"mappings":";;;;;;AAOA,IAAa,mBAAb,MAA8B;CAO5B,YACE,cACA,WACA;EAFiB,KAAA,eAAA;EACA,KAAA,YAAA;EALA,KAAA,WAAA;EACE,KAAA,aAAA;CAKlB;CAEH,MAAM,OAAyB;EAC7B,IAAI,KAAK,UAAU,OAAO;EAC1B,IAAI,KAAK,UAAU;GACjB,KAAK,SAAS,KAAK;GACnB,OAAO;EACT;EAEA,MAAM,aAAa,KAAK;EACxB,KAAK,YAAY,KAAK,aAAa;EACnC,IAAI;GACF,MAAM,WAAW,MAAM,KAAK;GAC5B,IAAI,KAAK,YAAY,eAAe,KAAK,YAAY;IACnD,UAAe,QAAQ,EAAE,SAAS,MAAM,CAAC;IACzC,OAAO;GACT;GACA,MAAM,WAAW,KAAK,gBAAgB;GACtC,IAAI,UAAU;IACZ,SAAS,KAAK;IACd,OAAO;GACT;GACA,IAAI,CAAC,UAAU,OAAO;GACtB,KAAK,SAAS,QAAQ;GACtB,OAAO;EACT,UAAU;GACR,IAAI,KAAK,eAAe,YAAY,KAAK,UAAU,KAAA;EACrD;CACF;CAEA,UAAgB;EACd,KAAK,WAAW;EAChB,KAAK,KAAK;CACZ;;CAGA,QAAc;EACZ,KAAK,WAAW;EAChB,KAAK,KAAK;CACZ;CAEA,kBAAgD;EAC9C,OAAO,KAAK;CACd;CAEA,SAAiB,UAA0B;EACzC,KAAK,WAAW;EAChB,KAAK,cAAc,gBAAgB,oBAAoB,WAAW;GAChE,IAAI,OAAO,OAAO,SAAS,IAAI;GAC/B,KAAK,cAAc;GACnB,KAAK,cAAc,KAAA;GACnB,IAAI,KAAK,aAAa,UAAU,KAAK,WAAW,KAAA;EAClD,CAAC;CACH;CAEA,OAAqB;EACnB,KAAK,cAAc;EACnB,KAAK,UAAU,KAAA;EACf,MAAM,WAAW,KAAK;EACtB,KAAK,WAAW,KAAA;EAChB,KAAK,cAAc;EACnB,KAAK,cAAc,KAAA;EACnB,KAAK,YAAY;EACjB,UAAe,QAAQ,EAAE,SAAS,MAAM,CAAC;CAC3C;AACF"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { Terminal } from './terminal-api';
|
|
2
|
+
/**
|
|
3
|
+
* One terminal tab bound to a caller-owned session.
|
|
4
|
+
* Closing the tab forgets the tab only. release() also drops the session binding.
|
|
5
|
+
*/
|
|
6
|
+
export declare class AttachedTerminal {
|
|
7
|
+
private readonly openTerminal;
|
|
8
|
+
private readonly onDiscard?;
|
|
9
|
+
private terminal?;
|
|
10
|
+
private unsubscribe?;
|
|
11
|
+
private opening?;
|
|
12
|
+
private disposed;
|
|
13
|
+
private generation;
|
|
14
|
+
constructor(openTerminal: () => Promise<Terminal | undefined>, onDiscard?: (() => void) | undefined);
|
|
15
|
+
show(): Promise<boolean>;
|
|
16
|
+
release(): void;
|
|
17
|
+
/** Forget the current tab so the next show() attaches the replacement session. */
|
|
18
|
+
reset(): void;
|
|
19
|
+
private currentTerminal;
|
|
20
|
+
private remember;
|
|
21
|
+
private drop;
|
|
22
|
+
}
|
|
23
|
+
//# sourceMappingURL=attached-terminal.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"attached-terminal.d.ts","sourceRoot":"","sources":["../src/attached-terminal.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;AAE/C;;;GAGG;AACH,qBAAa,gBAAgB;IAQzB,OAAO,CAAC,QAAQ,CAAC,YAAY;IAC7B,OAAO,CAAC,QAAQ,CAAC,SAAS,CAAC;IAR7B,OAAO,CAAC,QAAQ,CAAC,CAAW;IAC5B,OAAO,CAAC,WAAW,CAAC,CAAa;IACjC,OAAO,CAAC,OAAO,CAAC,CAAgC;IAChD,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,UAAU,CAAK;gBAGJ,YAAY,EAAE,MAAM,OAAO,CAAC,QAAQ,GAAG,SAAS,CAAC,EACjD,SAAS,CAAC,GAAE,MAAM,IAAI,aAAA;IAGnC,IAAI,IAAI,OAAO,CAAC,OAAO,CAAC;IA4B9B,OAAO,IAAI,IAAI;IAKf,kFAAkF;IAClF,KAAK,IAAI,IAAI;IAKb,OAAO,CAAC,eAAe;IAIvB,OAAO,CAAC,QAAQ;IAUhB,OAAO,CAAC,IAAI;CAUb"}
|
package/dist/index.js
CHANGED
|
@@ -9,7 +9,7 @@ extensionRegistry.registerExtension({
|
|
|
9
9
|
id: pkg.name,
|
|
10
10
|
name: t.EXT_TERMINAL_NAME,
|
|
11
11
|
description: t.EXT_TERMINAL_DESC,
|
|
12
|
-
loader: () => import("./terminal-extension-
|
|
12
|
+
loader: () => import("./terminal-extension-CnPHiXG4.js"),
|
|
13
13
|
icon: "terminal"
|
|
14
14
|
});
|
|
15
15
|
//#endregion
|
|
@@ -86,6 +86,7 @@ var TerminalInstance = class {
|
|
|
86
86
|
constructor(id, name, profileId, creationOptions, groupId) {
|
|
87
87
|
this.hidden = false;
|
|
88
88
|
this.backend = null;
|
|
89
|
+
this.skipCloseConfirm = false;
|
|
89
90
|
this.id = id;
|
|
90
91
|
this.name = name;
|
|
91
92
|
this.profileId = profileId;
|
|
@@ -104,9 +105,13 @@ var TerminalInstance = class {
|
|
|
104
105
|
hide() {
|
|
105
106
|
this.hidden = true;
|
|
106
107
|
}
|
|
107
|
-
async dispose() {
|
|
108
|
+
async dispose(options) {
|
|
109
|
+
if (options?.confirm === false) this.skipCloseConfirm = true;
|
|
108
110
|
await terminalService.disposeTerminal(this.id);
|
|
109
111
|
}
|
|
112
|
+
shouldConfirmClose() {
|
|
113
|
+
return !this.skipCloseConfirm;
|
|
114
|
+
}
|
|
110
115
|
clear() {
|
|
111
116
|
this.clearScreen?.();
|
|
112
117
|
}
|
|
@@ -226,8 +231,12 @@ var TerminalService = class {
|
|
|
226
231
|
terminal.backend = backend;
|
|
227
232
|
terminal.hidden = options.hidden ?? false;
|
|
228
233
|
this.terminals.set(id, terminal);
|
|
234
|
+
if (!terminal.hidden) {
|
|
235
|
+
this.focusTerminalPanel();
|
|
236
|
+
await this.whenTabsHostReady();
|
|
237
|
+
}
|
|
229
238
|
this.openTerminalTab(terminal, profile.icon);
|
|
230
|
-
if (!
|
|
239
|
+
if (!terminal.hidden) {
|
|
231
240
|
this.focusTerminalPanel();
|
|
232
241
|
this.activateTerminal(id);
|
|
233
242
|
}
|
|
@@ -235,6 +244,21 @@ var TerminalService = class {
|
|
|
235
244
|
this.persistState();
|
|
236
245
|
return terminal;
|
|
237
246
|
}
|
|
247
|
+
/** The panel binds its tab host after the bottom panel is shown. */
|
|
248
|
+
whenTabsHostReady() {
|
|
249
|
+
if (this.instanceTabsHost) return Promise.resolve();
|
|
250
|
+
const started = performance.now();
|
|
251
|
+
return new Promise((resolve) => {
|
|
252
|
+
const check = () => {
|
|
253
|
+
if (this.instanceTabsHost || performance.now() - started > 1e3) {
|
|
254
|
+
resolve();
|
|
255
|
+
return;
|
|
256
|
+
}
|
|
257
|
+
requestAnimationFrame(check);
|
|
258
|
+
};
|
|
259
|
+
requestAnimationFrame(check);
|
|
260
|
+
});
|
|
261
|
+
}
|
|
238
262
|
openTerminalTab(terminal, icon) {
|
|
239
263
|
const tabs = this.getInstanceTabs();
|
|
240
264
|
if (!tabs) return;
|
|
@@ -244,7 +268,7 @@ var TerminalService = class {
|
|
|
244
268
|
icon: icon ?? "terminal",
|
|
245
269
|
closable: true,
|
|
246
270
|
toolbar: false,
|
|
247
|
-
beforeClose: async () => confirmKillTerminal(terminal.name),
|
|
271
|
+
beforeClose: async () => terminal.shouldConfirmClose() ? confirmKillTerminal(terminal.name) : true,
|
|
248
272
|
component: (tabId) => html`<docks-terminal-view id="${tabId}" .terminal=${terminal}></docks-terminal-view>`
|
|
249
273
|
};
|
|
250
274
|
if (tabs.has(terminal.id)) {
|
|
@@ -684,7 +708,33 @@ var CommandsBackend = class {
|
|
|
684
708
|
//#endregion
|
|
685
709
|
//#region src/js-terminal-backend.ts
|
|
686
710
|
var JS_REPL_PROFILE_ID = "terminal.javascript-repl";
|
|
711
|
+
var JS_SESSION_PROFILE_ID = "terminal.javascript-session";
|
|
687
712
|
var PROMPT = "> ";
|
|
713
|
+
var sessions = /* @__PURE__ */ new Map();
|
|
714
|
+
function unbindJsSession(sessionId) {
|
|
715
|
+
sessions.delete(sessionId);
|
|
716
|
+
}
|
|
717
|
+
function createJsSessionBackend(options) {
|
|
718
|
+
const sessionId = options?.env?.jsSessionId;
|
|
719
|
+
const runtime = sessionId ? sessions.get(sessionId) : void 0;
|
|
720
|
+
if (!runtime) throw new Error("JavaScript session is no longer available");
|
|
721
|
+
return new JsReplBackend({
|
|
722
|
+
runtime,
|
|
723
|
+
ownsRuntime: false,
|
|
724
|
+
sessionLabel: options?.env?.sessionLabel || "session"
|
|
725
|
+
});
|
|
726
|
+
}
|
|
727
|
+
function openJsSessionTerminal(runtime, sessionId, name, sessionLabel = "session") {
|
|
728
|
+
sessions.set(sessionId, runtime);
|
|
729
|
+
return terminalService.createTerminal({
|
|
730
|
+
profileId: JS_SESSION_PROFILE_ID,
|
|
731
|
+
name,
|
|
732
|
+
env: {
|
|
733
|
+
jsSessionId: sessionId,
|
|
734
|
+
sessionLabel
|
|
735
|
+
}
|
|
736
|
+
});
|
|
737
|
+
}
|
|
688
738
|
function formatJsResult(value) {
|
|
689
739
|
if (value === void 0) return "";
|
|
690
740
|
if (value === null) return "null\r\n";
|
|
@@ -692,11 +742,13 @@ function formatJsResult(value) {
|
|
|
692
742
|
return String(value) + "\r\n";
|
|
693
743
|
}
|
|
694
744
|
var JsReplBackend = class {
|
|
695
|
-
constructor() {
|
|
745
|
+
constructor(options) {
|
|
696
746
|
this.writeCallbacks = /* @__PURE__ */ new Set();
|
|
697
|
-
this.runtime = null;
|
|
698
747
|
this.running = false;
|
|
699
748
|
this.lineInput = new LineInput((data) => this.emit(data));
|
|
749
|
+
this.runtime = options?.runtime ?? null;
|
|
750
|
+
this.ownsRuntime = options?.ownsRuntime ?? !options?.runtime;
|
|
751
|
+
this.sessionLabel = options?.sessionLabel ?? "session";
|
|
700
752
|
}
|
|
701
753
|
onDidWrite(callback) {
|
|
702
754
|
this.writeCallbacks.add(callback);
|
|
@@ -706,14 +758,23 @@ var JsReplBackend = class {
|
|
|
706
758
|
for (const cb of this.writeCallbacks) cb(data);
|
|
707
759
|
}
|
|
708
760
|
getRuntime() {
|
|
709
|
-
if (!this.runtime)
|
|
761
|
+
if (!this.runtime) {
|
|
762
|
+
this.runtime = createJsRuntime();
|
|
763
|
+
this.ownsRuntime = true;
|
|
764
|
+
}
|
|
710
765
|
return this.runtime;
|
|
711
766
|
}
|
|
712
767
|
async open() {
|
|
713
|
-
this.
|
|
768
|
+
if (!this.runtime) {
|
|
769
|
+
this.runtime = createJsRuntime();
|
|
770
|
+
this.ownsRuntime = true;
|
|
771
|
+
this.emit("JavaScript REPL\r\n\r\n> ");
|
|
772
|
+
return;
|
|
773
|
+
}
|
|
774
|
+
this.emit(`JavaScript (${this.sessionLabel})\r\n\r\n> `);
|
|
714
775
|
}
|
|
715
776
|
close() {
|
|
716
|
-
this.runtime?.close();
|
|
777
|
+
if (this.ownsRuntime) this.runtime?.close();
|
|
717
778
|
this.runtime = null;
|
|
718
779
|
this.lineInput.reset();
|
|
719
780
|
}
|
|
@@ -744,6 +805,6 @@ var JsReplBackend = class {
|
|
|
744
805
|
}
|
|
745
806
|
};
|
|
746
807
|
//#endregion
|
|
747
|
-
export {
|
|
808
|
+
export { TERMINAL_PANEL_SETTINGS_KEY as _, openJsSessionTerminal as a, TOPIC_TERMINAL_OPENED as b, LineInput as c, emptyTerminalState as d, parseTerminalState as f, TERMINAL_NEW_DROPDOWN as g, TERMINAL_INSTANCES_TABS_ID as h, createJsSessionBackend as i, registerTerminalProfile as l, TARGET_TERMINAL_PROFILES as m, JS_SESSION_PROFILE_ID as n, unbindJsSession as o, serializeTerminalState as p, JsReplBackend as r, CommandsBackend as s, JS_REPL_PROFILE_ID as t, terminalService as u, TOPIC_TERMINAL_ACTIVE_CHANGED as v, VIEW_TERMINAL as x, TOPIC_TERMINAL_CLOSED as y };
|
|
748
809
|
|
|
749
|
-
//# sourceMappingURL=js-terminal-backend-
|
|
810
|
+
//# sourceMappingURL=js-terminal-backend-CRxDAwvr.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"js-terminal-backend-CRxDAwvr.js","names":[],"sources":["../src/terminal-api.ts","../src/terminal-persistence.ts","../src/terminal-service.ts","../src/shell-parser.ts","../src/line-input.ts","../src/commands-backend.ts","../src/js-terminal-backend.ts"],"sourcesContent":["export const TARGET_TERMINAL_PROFILES = 'system.terminal.profiles';\n\nexport const VIEW_TERMINAL = 'view.terminal';\nexport const TERMINAL_INSTANCES_TABS_ID = 'terminal-instances';\n/** Dropdown target: contributors register items that create a terminal with a profile. */\nexport const TERMINAL_NEW_DROPDOWN = `${TERMINAL_INSTANCES_TABS_ID}-new`;\nexport const TERMINAL_PANEL_SETTINGS_KEY = 'docks-terminal-panel';\n\nexport const TOPIC_TERMINAL_OPENED = 'events/terminal/opened';\nexport const TOPIC_TERMINAL_CLOSED = 'events/terminal/closed';\nexport const TOPIC_TERMINAL_ACTIVE_CHANGED = 'events/terminal/activeChanged';\n\nexport interface TerminalDimensions {\n cols: number;\n rows: number;\n}\n\nexport interface TerminalCreationOptions {\n name?: string;\n profileId?: string;\n cwd?: string;\n env?: Record<string, string>;\n groupId?: string;\n hidden?: boolean;\n}\n\nexport interface TerminalBackend {\n open?(initialDimensions?: TerminalDimensions): void | Promise<void>;\n close?(): void | Promise<void>;\n onDidWrite(callback: (data: string) => void): () => void;\n handleInput(data: string): void;\n setDimensions?(dimensions: TerminalDimensions): void;\n}\n\nexport interface TerminalProfileContribution {\n id: string;\n label: string;\n icon?: string;\n isDefault?: boolean;\n hidden?: boolean;\n /**\n * When false, terminals of this profile are not saved or restored across reloads.\n * Defaults to true.\n */\n persist?: boolean;\n create(options?: TerminalCreationOptions): Promise<TerminalBackend>;\n}\n\nexport interface TerminalTaskPresentation {\n profileId: string;\n reveal?: 'always' | 'silent' | 'never';\n focus?: boolean;\n clear?: boolean;\n}\n\nexport interface Terminal {\n readonly id: string;\n name: string;\n readonly profileId: string;\n readonly creationOptions: TerminalCreationOptions;\n readonly groupId: string;\n hidden: boolean;\n sendText(text: string, addNewLine?: boolean): void;\n show(preserveFocus?: boolean): void;\n hide(): void;\n dispose(options?: { confirm?: boolean }): Promise<void>;\n clear?(): void;\n}\n\n/** Internal terminal handle used by the host UI (not for provider extensions). */\nexport interface TerminalRuntime extends Terminal {\n backend: TerminalBackend | null;\n clearScreen?: () => void;\n}\n\nexport interface TerminalTaskRunner {\n runTask(\n presentation: TerminalTaskPresentation,\n execute: (terminal: Terminal) => Promise<void>\n ): Promise<void>;\n}\n\nexport interface PersistedTerminalState {\n terminals: PersistedTerminalEntry[];\n activeTerminalId: string | null;\n preferredProfileId: string | null;\n}\n\nexport interface PersistedTerminalEntry {\n id: string;\n name: string;\n profileId: string;\n groupId: string;\n creationOptions: TerminalCreationOptions;\n}\n","import type { PersistedTerminalEntry, PersistedTerminalState, TerminalCreationOptions } from './terminal-api';\n\nconst MAX_PERSISTED_ENV_KEYS = 32;\n\nexport function serializeTerminalState(state: PersistedTerminalState): PersistedTerminalState {\n return {\n activeTerminalId: state.activeTerminalId,\n preferredProfileId: state.preferredProfileId,\n terminals: state.terminals.map(serializeTerminalEntry),\n };\n}\n\nfunction serializeTerminalEntry(entry: PersistedTerminalEntry): PersistedTerminalEntry {\n const opts = entry.creationOptions;\n const env = opts.env\n ? Object.fromEntries(Object.entries(opts.env).slice(0, MAX_PERSISTED_ENV_KEYS))\n : undefined;\n return {\n id: entry.id,\n name: entry.name,\n profileId: entry.profileId,\n groupId: entry.groupId,\n creationOptions: {\n name: opts.name,\n profileId: opts.profileId,\n cwd: opts.cwd,\n env,\n groupId: opts.groupId,\n },\n };\n}\n\nexport function parseTerminalState(raw: unknown): PersistedTerminalState | null {\n if (!raw || typeof raw !== 'object') return null;\n const obj = raw as Record<string, unknown>;\n if (!Array.isArray(obj.terminals)) return null;\n\n const terminals: PersistedTerminalEntry[] = [];\n for (const item of obj.terminals) {\n if (!item || typeof item !== 'object') continue;\n const t = item as Record<string, unknown>;\n if (typeof t.id !== 'string' || typeof t.name !== 'string' || typeof t.profileId !== 'string') {\n continue;\n }\n const creationOptions = (t.creationOptions ?? {}) as TerminalCreationOptions;\n terminals.push({\n id: t.id,\n name: t.name,\n profileId: t.profileId,\n groupId: typeof t.groupId === 'string' ? t.groupId : t.id,\n creationOptions,\n });\n }\n\n return {\n terminals,\n activeTerminalId: typeof obj.activeTerminalId === 'string' ? obj.activeTerminalId : null,\n preferredProfileId: typeof obj.preferredProfileId === 'string' ? obj.preferredProfileId : null,\n };\n}\n\nexport function emptyTerminalState(): PersistedTerminalState {\n return { terminals: [], activeTerminalId: null, preferredProfileId: null };\n}\n","import { html } from '@eclipse-docks/core/externals/lit';\nimport {\n confirmDialog,\n contributionRegistry,\n i18n,\n PANEL_BOTTOM,\n publish,\n renderDropdownItem,\n rootContext,\n subscribe,\n unsubscribe,\n type TabContribution,\n} from '@eclipse-docks/core';\nimport {\n TARGET_TERMINAL_PROFILES,\n TERMINAL_NEW_DROPDOWN,\n TOPIC_TERMINAL_ACTIVE_CHANGED,\n TOPIC_TERMINAL_CLOSED,\n TOPIC_TERMINAL_OPENED,\n VIEW_TERMINAL,\n type Terminal,\n type TerminalBackend,\n type TerminalCreationOptions,\n type TerminalProfileContribution,\n type TerminalTaskPresentation,\n type TerminalTaskRunner,\n type PersistedTerminalState,\n type TerminalRuntime,\n} from './terminal-api';\nimport { emptyTerminalState, parseTerminalState, serializeTerminalState } from './terminal-persistence';\n\nconst t = await i18n(import.meta.glob('./i18n*.json'), true);\n\nasync function confirmKillTerminal(name: string): Promise<boolean> {\n return confirmDialog(t.TERMINAL_KILL_CONFIRM({ name }));\n}\n\ninterface TerminalTabsHost {\n has(key: string): boolean;\n activate(key: string): void;\n open(contribution: TabContribution): void;\n closeTab(event: Event, tabName: string): Promise<void>;\n updateTabLabel(tabName: string, label: string): void;\n}\n\nexport type { TerminalTabsHost };\n\nlet terminalCounter = 0;\n\nfunction nextTerminalId(): string {\n terminalCounter += 1;\n return `terminal-${terminalCounter}`;\n}\n\nclass TerminalInstance implements TerminalRuntime {\n readonly id: string;\n name: string;\n readonly profileId: string;\n readonly creationOptions: TerminalCreationOptions;\n readonly groupId: string;\n hidden = false;\n backend: TerminalBackend | null = null;\n clearScreen?: () => void;\n private skipCloseConfirm = false;\n\n constructor(\n id: string,\n name: string,\n profileId: string,\n creationOptions: TerminalCreationOptions,\n groupId: string\n ) {\n this.id = id;\n this.name = name;\n this.profileId = profileId;\n this.creationOptions = creationOptions;\n this.groupId = groupId;\n }\n\n sendText(text: string, addNewLine = true): void {\n if (!this.backend) return;\n this.backend.handleInput(text + (addNewLine ? '\\r' : ''));\n }\n\n show(_preserveFocus?: boolean): void {\n terminalService.focusTerminalPanel();\n terminalService.activateTerminal(this.id);\n this.hidden = false;\n }\n\n hide(): void {\n this.hidden = true;\n }\n\n async dispose(options?: { confirm?: boolean }): Promise<void> {\n if (options?.confirm === false) this.skipCloseConfirm = true;\n await terminalService.disposeTerminal(this.id);\n }\n\n shouldConfirmClose(): boolean {\n return !this.skipCloseConfirm;\n }\n\n clear(): void {\n this.clearScreen?.();\n }\n}\n\nclass TerminalService implements TerminalTaskRunner {\n private terminals = new Map<string, TerminalInstance>();\n private activeTerminalId: string | null = null;\n private preferredProfileId: string | null = null;\n private persistenceHandler: (() => Promise<PersistedTerminalState | null>) | null = null;\n private persistCallback: ((state: PersistedTerminalState) => Promise<void>) | null = null;\n private restoreStarted = false;\n private instanceTabsHost: TerminalTabsHost | null = null;\n\n get activeTerminal(): Terminal | undefined {\n if (!this.activeTerminalId) return undefined;\n return this.terminals.get(this.activeTerminalId);\n }\n\n getTerminals(): Terminal[] {\n return [...this.terminals.values()];\n }\n\n onDidOpenTerminal(callback: (terminal: Terminal) => void): () => void {\n const token = subscribe(TOPIC_TERMINAL_OPENED, callback);\n return () => unsubscribe(token);\n }\n\n onDidCloseTerminal(callback: (terminal: Terminal) => void): () => void {\n const token = subscribe(TOPIC_TERMINAL_CLOSED, callback);\n return () => unsubscribe(token);\n }\n\n onDidChangeActiveTerminal(callback: (terminal: Terminal | undefined) => void): () => void {\n const token = subscribe(TOPIC_TERMINAL_ACTIVE_CHANGED, callback);\n return () => unsubscribe(token);\n }\n\n setPersistenceHandlers(\n load: () => Promise<PersistedTerminalState | null>,\n save: (state: PersistedTerminalState) => Promise<void>\n ): void {\n this.persistenceHandler = load;\n this.persistCallback = save;\n }\n\n async restorePersistedTerminals(): Promise<void> {\n if (this.restoreStarted || !this.persistenceHandler) return;\n this.restoreStarted = true;\n const raw = await this.persistenceHandler();\n const state = raw ? parseTerminalState(raw) : null;\n if (!state || state.terminals.length === 0) return;\n\n this.preferredProfileId = state.preferredProfileId;\n for (const entry of state.terminals) {\n if (!this.isProfilePersistent(entry.profileId)) continue;\n await this.createTerminal({\n ...entry.creationOptions,\n name: entry.name,\n profileId: entry.profileId,\n groupId: entry.groupId,\n }, entry.id);\n }\n if (state.activeTerminalId && this.terminals.has(state.activeTerminalId)) {\n this.setActiveTerminal(state.activeTerminalId);\n }\n }\n\n /** Profiles default to persistent; opt out with `persist: false`. */\n private isProfilePersistent(profileId: string): boolean {\n const profile = this.getProfiles().find((p) => p.id === profileId);\n return profile?.persist !== false;\n }\n\n getProfiles(): TerminalProfileContribution[] {\n return contributionRegistry.getContributions<TerminalProfileContribution>(TARGET_TERMINAL_PROFILES);\n }\n\n resolveDefaultProfileId(): string | null {\n if (this.preferredProfileId) {\n const preferred = this.getProfiles().find((p) => p.id === this.preferredProfileId);\n if (preferred) return preferred.id;\n }\n const profiles = this.getProfiles().filter((p) => !p.hidden);\n const defaultProfile = profiles.find((p) => p.isDefault) ?? profiles[0];\n return defaultProfile?.id ?? null;\n }\n\n setInstanceTabsHost(host: TerminalTabsHost | null): void {\n this.instanceTabsHost = host;\n }\n\n getInstanceTabs(): TerminalTabsHost | null {\n return this.instanceTabsHost;\n }\n\n focusTerminalPanel(): void {\n const panel = document.querySelector(`docks-tabs#${PANEL_BOTTOM}`) as TerminalTabsHost | null;\n panel?.activate(VIEW_TERMINAL);\n }\n\n activateTerminal(id: string): void {\n const tabs = this.getInstanceTabs();\n if (tabs?.has(id)) {\n tabs.activate(id);\n }\n this.setActiveTerminal(id);\n }\n\n private setActiveTerminal(id: string | null): void {\n if (this.activeTerminalId === id) return;\n this.activeTerminalId = id;\n publish(TOPIC_TERMINAL_ACTIVE_CHANGED, id ? this.terminals.get(id) : undefined);\n void this.persistState();\n }\n\n async createTerminal(\n options: TerminalCreationOptions = {},\n forcedId?: string\n ): Promise<Terminal | undefined> {\n const profileId = options.profileId ?? this.resolveDefaultProfileId();\n if (!profileId) return undefined;\n\n const profile = this.getProfiles().find((p) => p.id === profileId);\n if (!profile) return undefined;\n\n const id = forcedId ?? nextTerminalId();\n if (forcedId) syncTerminalCounterFromId(forcedId);\n const groupId = options.groupId ?? id;\n const name = options.name ?? profile.label;\n\n let backend: TerminalBackend;\n try {\n backend = await profile.create({ ...options, profileId, name, groupId });\n } catch {\n return undefined;\n }\n\n const terminal = new TerminalInstance(id, name, profileId, { ...options, profileId, name, groupId }, groupId);\n terminal.backend = backend;\n terminal.hidden = options.hidden ?? false;\n\n this.terminals.set(id, terminal);\n if (!terminal.hidden) {\n this.focusTerminalPanel();\n await this.whenTabsHostReady();\n }\n this.openTerminalTab(terminal, profile.icon);\n\n if (!terminal.hidden) {\n this.focusTerminalPanel();\n this.activateTerminal(id);\n }\n\n publish(TOPIC_TERMINAL_OPENED, terminal);\n void this.persistState();\n return terminal;\n }\n\n /** The panel binds its tab host after the bottom panel is shown. */\n private whenTabsHostReady(): Promise<void> {\n if (this.instanceTabsHost) return Promise.resolve();\n const started = performance.now();\n return new Promise((resolve) => {\n const check = () => {\n if (this.instanceTabsHost || performance.now() - started > 1000) {\n resolve();\n return;\n }\n requestAnimationFrame(check);\n };\n requestAnimationFrame(check);\n });\n }\n\n private openTerminalTab(terminal: TerminalInstance, icon?: string): void {\n const tabs = this.getInstanceTabs();\n if (!tabs) return;\n\n const contribution: TabContribution = {\n name: terminal.id,\n label: terminal.name,\n icon: icon ?? 'terminal',\n closable: true,\n toolbar: false,\n beforeClose: async () => terminal.shouldConfirmClose() ? confirmKillTerminal(terminal.name) : true,\n component: (tabId: string) =>\n html`<docks-terminal-view id=\"${tabId}\" .terminal=${terminal}></docks-terminal-view>`,\n };\n\n if (tabs.has(terminal.id)) {\n tabs.activate(terminal.id);\n return;\n }\n tabs.open(contribution);\n }\n\n async disposeTerminal(id: string, options?: { skipTabRemoval?: boolean }): Promise<void> {\n const terminal = this.terminals.get(id);\n if (!terminal) return;\n\n if (!options?.skipTabRemoval) {\n const tabs = this.getInstanceTabs();\n if (tabs?.has(id)) {\n await tabs.closeTab(new Event('close'), id);\n return;\n }\n }\n\n await terminal.backend?.close?.();\n terminal.backend = null;\n this.terminals.delete(id);\n\n if (this.activeTerminalId === id) {\n const remaining = [...this.terminals.keys()];\n this.setActiveTerminal(remaining.length > 0 ? remaining[remaining.length - 1] : null);\n }\n\n publish(TOPIC_TERMINAL_CLOSED, terminal);\n void this.persistState();\n }\n\n async killAll(): Promise<void> {\n const tabs = this.getInstanceTabs();\n const ids = [...this.terminals.keys()];\n for (const id of ids) {\n if (tabs?.has(id)) {\n await tabs.closeTab(new Event('close'), id);\n } else {\n await this.disposeTerminal(id, { skipTabRemoval: true });\n }\n }\n }\n\n renameActiveTerminal(name: string): void {\n const active = this.activeTerminal;\n if (!active || !(active instanceof TerminalInstance)) return;\n active.name = name;\n this.getInstanceTabs()?.updateTabLabel(active.id, name);\n void this.persistState();\n }\n\n setPreferredProfile(profileId: string): void {\n this.preferredProfileId = profileId;\n void this.persistState();\n }\n\n clearActiveTerminal(): void {\n this.activeTerminal?.clear?.();\n }\n\n async runTask(\n presentation: TerminalTaskPresentation,\n execute: (terminal: Terminal) => Promise<void>\n ): Promise<void> {\n let terminal = this.getTerminals().find((t) => t.profileId === presentation.profileId);\n if (!terminal) {\n terminal = await this.createTerminal({ profileId: presentation.profileId });\n }\n if (!terminal) return;\n\n if (presentation.reveal !== 'never') {\n if (presentation.focus !== false) {\n terminal.show();\n } else {\n this.focusTerminalPanel();\n }\n }\n if (presentation.clear) {\n terminal.clear?.();\n }\n await execute(terminal);\n }\n\n private async persistState(): Promise<void> {\n if (!this.persistCallback) return;\n const terminals = [...this.terminals.values()]\n .filter((t) => this.isProfilePersistent(t.profileId))\n .map((t) => ({\n id: t.id,\n name: t.name,\n profileId: t.profileId,\n groupId: t.groupId,\n creationOptions: t.creationOptions,\n }));\n const ids = new Set(terminals.map((t) => t.id));\n const state: PersistedTerminalState = {\n activeTerminalId:\n this.activeTerminalId && ids.has(this.activeTerminalId) ? this.activeTerminalId : null,\n preferredProfileId: this.preferredProfileId,\n terminals,\n };\n await this.persistCallback(serializeTerminalState(state));\n }\n\n handleTabActivated(tabName: string): void {\n if (this.terminals.has(tabName)) {\n this.setActiveTerminal(tabName);\n }\n }\n\n handleTabClosed(tabName: string): void {\n if (this.terminals.has(tabName)) {\n void this.disposeTerminal(tabName, { skipTabRemoval: true });\n }\n }\n}\n\nfunction syncTerminalCounterFromId(id: string): void {\n const match = /^terminal-(\\d+)$/.exec(id);\n if (!match) return;\n const n = Number.parseInt(match[1], 10);\n if (n > terminalCounter) terminalCounter = n;\n}\n\nexport const terminalService = new TerminalService();\nrootContext.put('terminalService', terminalService);\n\nexport function registerTerminalProfile(contribution: TerminalProfileContribution): void {\n contributionRegistry.registerContribution(TARGET_TERMINAL_PROFILES, contribution);\n if (contribution.hidden) return;\n const profileId = contribution.id;\n contributionRegistry.registerContribution(TERMINAL_NEW_DROPDOWN, {\n label: contribution.label,\n icon: contribution.icon ?? 'terminal',\n component: () => renderDropdownItem({\n icon: contribution.icon ?? 'terminal',\n label: contribution.label,\n title: contribution.label,\n action: () => {\n terminalService.setPreferredProfile(profileId);\n void terminalService.createTerminal({ profileId });\n },\n }),\n });\n}\n","import type { CommandRegistry, Command } from '@eclipse-docks/core';\n\nexport interface ParsedCommand {\n commandId: string;\n params: Record<string, string | boolean>;\n}\n\nexport interface ParsedSegment {\n command: ParsedCommand;\n operator: '&&' | '|' | null;\n}\n\nconst NAMED_PARAM_REGEX = /^[a-zA-Z_][a-zA-Z0-9_]*=.*$/;\n\nfunction tokenize(segment: string): string[] {\n const tokens: string[] = [];\n let i = 0;\n const len = segment.length;\n\n while (i < len) {\n while (i < len && /\\s/.test(segment[i])) i++;\n if (i >= len) break;\n\n if (segment[i] === '\"') {\n let end = i + 1;\n while (end < len && segment[end] !== '\"') {\n if (segment[end] === '\\\\') end++;\n end++;\n }\n tokens.push(segment.slice(i + 1, end).replace(/\\\\\"/g, '\"'));\n i = end + 1;\n } else {\n let start = i;\n while (i < len && !/\\s/.test(segment[i]) && segment[i] !== '\"') i++;\n if (i > start) {\n tokens.push(segment.slice(start, i));\n }\n }\n }\n return tokens;\n}\n\nfunction splitChain(line: string): { segment: string; operator: '&&' | '|' | null }[] {\n const result: { segment: string; operator: '&&' | '|' | null }[] = [];\n const regex = /(\\s*&&\\s*|\\s*\\|\\s*)/g;\n let lastIndex = 0;\n let match: RegExpExecArray | null;\n\n while ((match = regex.exec(line)) !== null) {\n const segment = line.slice(lastIndex, match.index).trim();\n if (segment) {\n const op = match[0].includes('|') ? ('|' as const) : ('&&' as const);\n result.push({ segment, operator: op });\n }\n lastIndex = regex.lastIndex;\n }\n const tail = line.slice(lastIndex).trim();\n if (tail) {\n result.push({ segment: tail, operator: null });\n }\n return result;\n}\n\nfunction resolveParams(\n tokens: string[],\n command: Command | undefined\n): Record<string, string | boolean> {\n const params: Record<string, string | boolean> = {};\n const positionals: string[] = [];\n const paramNames = command?.parameters?.map((p) => p.name) ?? [];\n\n for (const token of tokens) {\n if (NAMED_PARAM_REGEX.test(token)) {\n const eqIdx = token.indexOf('=');\n const name = token.slice(0, eqIdx);\n const value = token.slice(eqIdx + 1);\n params[name] = value === 'true' || value === 'false' ? value === 'true' : value;\n } else {\n positionals.push(token);\n }\n }\n\n paramNames.forEach((name, i) => {\n if (positionals[i] !== undefined && !(name in params)) {\n params[name] = positionals[i];\n }\n });\n\n return params;\n}\n\nexport function parseShellLine(line: string, commandRegistry: CommandRegistry): ParsedSegment[] {\n const segments = splitChain(line);\n return segments.map(({ segment, operator }) => {\n const tokens = tokenize(segment);\n if (tokens.length === 0) {\n return { command: { commandId: '', params: {} }, operator };\n }\n const commandId = tokens[0];\n const command = commandRegistry.hasCommand(commandId)\n ? commandRegistry.getCommand(commandId)\n : undefined;\n const params = resolveParams(tokens.slice(1), command);\n return { command: { commandId, params }, operator };\n });\n}\n","/** Minimal readline-style editor for xterm-backed REPL backends. */\nexport class LineInput {\n private buffer = '';\n private cursor = 0;\n private history: string[] = [];\n private historyDraft = '';\n private historyIndex = 0;\n\n constructor(private write: (data: string) => void) {}\n\n reset(): void {\n this.buffer = '';\n this.cursor = 0;\n this.historyDraft = '';\n this.historyIndex = this.history.length;\n }\n\n /** Returns the submitted line on Enter, otherwise null. */\n feed(data: string): string | null {\n if (data === '\\r') {\n const line = this.buffer;\n this.pushHistory(line);\n this.buffer = '';\n this.cursor = 0;\n this.write('\\r\\n');\n return line;\n }\n\n if (data === '\\u007f' || data === '\\b') {\n this.deleteBackward();\n return null;\n }\n\n if (data === '\\x1b[D' || data === '\\x1bOD') {\n this.move(-1);\n return null;\n }\n if (data === '\\x1b[C' || data === '\\x1bOC') {\n this.move(1);\n return null;\n }\n if (data === '\\x1b[A' || data === '\\x1bOA') {\n this.historyPrev();\n return null;\n }\n if (data === '\\x1b[B' || data === '\\x1bOB') {\n this.historyNext();\n return null;\n }\n if (data === '\\x1b[3~') {\n this.deleteForward();\n return null;\n }\n if (data === '\\x1b[H' || data === '\\x1bOH') {\n this.cursorHome();\n return null;\n }\n if (data === '\\x1b[F' || data === '\\x1bOF') {\n this.cursorEnd();\n return null;\n }\n\n if (data.startsWith('\\x1b')) return null;\n\n for (const char of data) {\n if (char < ' ') continue;\n this.insert(char);\n }\n return null;\n }\n\n private move(delta: number): void {\n const next = this.cursor + delta;\n if (next < 0 || next > this.buffer.length) return;\n const steps = Math.abs(delta);\n this.cursor = next;\n this.write(delta < 0 ? `\\x1b[${steps}D` : `\\x1b[${steps}C`);\n }\n\n private cursorHome(): void {\n if (this.cursor === 0) return;\n this.write(`\\x1b[${this.cursor}D`);\n this.cursor = 0;\n }\n\n private cursorEnd(): void {\n const steps = this.buffer.length - this.cursor;\n if (steps <= 0) return;\n this.write(`\\x1b[${steps}C`);\n this.cursor = this.buffer.length;\n }\n\n private insert(char: string): void {\n if (this.cursor === this.buffer.length) {\n this.buffer += char;\n this.cursor++;\n this.write(char);\n return;\n }\n const tail = this.buffer.slice(this.cursor);\n this.buffer = this.buffer.slice(0, this.cursor) + char + tail;\n this.cursor++;\n this.write(char + tail + `\\x1b[${tail.length}D`);\n }\n\n private deleteBackward(): void {\n if (this.cursor === 0) return;\n if (this.cursor === this.buffer.length) {\n this.buffer = this.buffer.slice(0, -1);\n this.cursor--;\n this.write('\\b \\b');\n return;\n }\n const after = this.buffer.slice(this.cursor);\n this.buffer = this.buffer.slice(0, this.cursor - 1) + after;\n this.cursor--;\n this.write(`\\b${after} ` + `\\x1b[${after.length + 1}D`);\n }\n\n private deleteForward(): void {\n if (this.cursor >= this.buffer.length) return;\n const after = this.buffer.slice(this.cursor + 1);\n this.write(`${after} ` + `\\x1b[${after.length + 1}D`);\n this.buffer = this.buffer.slice(0, this.cursor) + after;\n }\n\n private replaceBuffer(next: string): void {\n if (this.cursor > 0) this.write(`\\x1b[${this.cursor}D`);\n if (this.buffer.length > 0) this.write('\\x1b[K');\n this.buffer = next;\n this.cursor = next.length;\n if (next) this.write(next);\n }\n\n private historyPrev(): void {\n if (this.history.length === 0) return;\n if (this.historyIndex === this.history.length) {\n this.historyDraft = this.buffer;\n }\n if (this.historyIndex === 0) return;\n this.historyIndex--;\n this.replaceBuffer(this.history[this.historyIndex]);\n }\n\n private historyNext(): void {\n if (this.historyIndex >= this.history.length) return;\n this.historyIndex++;\n if (this.historyIndex === this.history.length) {\n this.replaceBuffer(this.historyDraft);\n this.historyDraft = '';\n return;\n }\n this.replaceBuffer(this.history[this.historyIndex]);\n }\n\n private pushHistory(line: string): void {\n if (line.length > 0 && this.history[this.history.length - 1] !== line) {\n this.history.push(line);\n }\n this.historyIndex = this.history.length;\n this.historyDraft = '';\n }\n}\n","import { commandRegistry, type CommandRegistry, type Command } from '@eclipse-docks/core';\nimport { parseShellLine } from './shell-parser';\nimport { LineInput } from './line-input';\n\nexport interface RunResult {\n success: boolean;\n results: unknown[];\n error?: string;\n}\n\nfunction mapOutputToParams(\n output: unknown,\n producerCommand: Command | undefined\n): Record<string, unknown> {\n if (output == null) return {};\n if (typeof output === 'object' && !Array.isArray(output)) {\n return output as Record<string, unknown>;\n }\n const firstOutput = producerCommand?.output?.[0];\n if (firstOutput) {\n return { [firstOutput.name]: output };\n }\n return {};\n}\n\nexport async function runShellLine(\n line: string,\n registry: CommandRegistry = commandRegistry\n): Promise<RunResult> {\n const segments = parseShellLine(line, registry);\n const results: unknown[] = [];\n let pipedOutput: Record<string, unknown> | null = null;\n let lastProducerCommand: Command | undefined;\n\n for (let i = 0; i < segments.length; i++) {\n const { command, operator } = segments[i];\n if (!command.commandId) continue;\n\n const cmd = registry.hasCommand(command.commandId)\n ? registry.getCommand(command.commandId)\n : undefined;\n if (!cmd) {\n return {\n success: false,\n results,\n error: `Command not found: ${command.commandId}`,\n };\n }\n\n const mergedParams = {\n ...mapOutputToParams(pipedOutput ?? undefined, lastProducerCommand),\n ...command.params,\n };\n\n const context = registry.createExecutionContext(mergedParams);\n\n try {\n const result = registry.execute(command.commandId, context);\n const resolved = result instanceof Promise ? await result : result;\n results.push(resolved);\n\n if (operator === '|') {\n pipedOutput = mapOutputToParams(resolved, cmd) as Record<string, unknown>;\n lastProducerCommand = cmd;\n } else {\n pipedOutput = null;\n lastProducerCommand = undefined;\n }\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n return { success: false, results, error: msg };\n }\n }\n\n return { success: true, results };\n}\n\nfunction formatResult(result: RunResult): string {\n if (result.error) return `\\r\\n\\x1b[31m${result.error}\\x1b[0m\\r\\n`;\n if (result.results.length === 0) return '';\n const last = result.results[result.results.length - 1];\n if (last == null) return '';\n if (typeof last === 'object') return JSON.stringify(last, null, 2) + '\\r\\n';\n return String(last) + '\\r\\n';\n}\n\nexport class CommandsBackend {\n private writeCallbacks = new Set<(data: string) => void>();\n private lineInput: LineInput;\n private prompt = '> ';\n\n constructor() {\n this.lineInput = new LineInput((data) => this.emit(data));\n }\n\n onDidWrite(callback: (data: string) => void): () => void {\n this.writeCallbacks.add(callback);\n return () => this.writeCallbacks.delete(callback);\n }\n\n private emit(data: string): void {\n for (const cb of this.writeCallbacks) cb(data);\n }\n\n async open(): Promise<void> {\n this.emit('Commands\\r\\nType commands (supports && and |)\\r\\n\\r\\n' + this.prompt);\n }\n\n close(): void {\n this.lineInput.reset();\n }\n\n setDimensions(_dimensions: { cols: number; rows: number }): void {}\n\n handleInput(data: string): void {\n const line = this.lineInput.feed(data);\n if (line === null) return;\n void this.runLine(line);\n }\n\n private async runLine(line: string): Promise<void> {\n const trimmed = line.trim();\n if (!trimmed) {\n this.emit(this.prompt);\n return;\n }\n const result = await runShellLine(trimmed);\n this.emit(formatResult(result));\n this.emit(this.prompt);\n }\n}\n","import { createJsRuntime, type JsRuntime } from '@eclipse-docks/core';\nimport { terminalService } from './terminal-service';\nimport type { Terminal, TerminalBackend, TerminalCreationOptions } from './terminal-api';\nimport { LineInput } from './line-input';\n\nexport const JS_REPL_PROFILE_ID = 'terminal.javascript-repl';\nexport const JS_SESSION_PROFILE_ID = 'terminal.javascript-session';\n\nconst PROMPT = '> ';\n\nconst sessions = new Map<string, JsRuntime>();\n\nexport function unbindJsSession(sessionId: string): void {\n sessions.delete(sessionId);\n}\n\nexport function createJsSessionBackend(options?: TerminalCreationOptions): JsReplBackend {\n const sessionId = options?.env?.jsSessionId;\n const runtime = sessionId ? sessions.get(sessionId) : undefined;\n if (!runtime) throw new Error('JavaScript session is no longer available');\n return new JsReplBackend({\n runtime,\n ownsRuntime: false,\n sessionLabel: options?.env?.sessionLabel || 'session',\n });\n}\n\nexport function openJsSessionTerminal(\n runtime: JsRuntime,\n sessionId: string,\n name: string,\n sessionLabel = 'session',\n): Promise<Terminal | undefined> {\n sessions.set(sessionId, runtime);\n return terminalService.createTerminal({\n profileId: JS_SESSION_PROFILE_ID,\n name,\n env: { jsSessionId: sessionId, sessionLabel },\n });\n}\n\ninterface JsReplBackendOptions {\n runtime?: JsRuntime;\n /** When false, closing the terminal leaves the runtime running. */\n ownsRuntime?: boolean;\n sessionLabel?: string;\n}\n\nfunction formatJsResult(value: unknown): string {\n if (value === undefined) return '';\n if (value === null) return 'null\\r\\n';\n if (typeof value === 'object') return JSON.stringify(value, null, 2) + '\\r\\n';\n return String(value) + '\\r\\n';\n}\n\nexport class JsReplBackend implements TerminalBackend {\n private writeCallbacks = new Set<(data: string) => void>();\n private lineInput: LineInput;\n private runtime: JsRuntime | null;\n private ownsRuntime: boolean;\n private sessionLabel: string;\n private running = false;\n\n constructor(options?: JsReplBackendOptions) {\n this.lineInput = new LineInput((data) => this.emit(data));\n this.runtime = options?.runtime ?? null;\n this.ownsRuntime = options?.ownsRuntime ?? !options?.runtime;\n this.sessionLabel = options?.sessionLabel ?? 'session';\n }\n\n onDidWrite(callback: (data: string) => void): () => void {\n this.writeCallbacks.add(callback);\n return () => this.writeCallbacks.delete(callback);\n }\n\n private emit(data: string): void {\n for (const cb of this.writeCallbacks) cb(data);\n }\n\n private getRuntime(): JsRuntime {\n if (!this.runtime) {\n this.runtime = createJsRuntime();\n this.ownsRuntime = true;\n }\n return this.runtime;\n }\n\n async open(): Promise<void> {\n if (!this.runtime) {\n this.runtime = createJsRuntime();\n this.ownsRuntime = true;\n this.emit('JavaScript REPL\\r\\n\\r\\n' + PROMPT);\n return;\n }\n this.emit(`JavaScript (${this.sessionLabel})\\r\\n\\r\\n` + PROMPT);\n }\n\n close(): void {\n if (this.ownsRuntime) this.runtime?.close();\n this.runtime = null;\n this.lineInput.reset();\n }\n\n setDimensions(_dimensions: { cols: number; rows: number }): void {}\n\n handleInput(data: string): void {\n if (this.running) return;\n const line = this.lineInput.feed(data);\n if (line === null) return;\n void this.runLine(line);\n }\n\n private async runLine(line: string): Promise<void> {\n const trimmed = line.trim();\n if (!trimmed) {\n this.emit(PROMPT);\n return;\n }\n\n this.running = true;\n try {\n const result = await this.getRuntime().execute(trimmed);\n const output = formatJsResult(result);\n if (output) this.emit(output);\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n this.emit(`\\x1b[31m${msg}\\x1b[0m\\r\\n`);\n } finally {\n this.running = false;\n this.emit(PROMPT);\n }\n }\n}\n"],"mappings":";;;AAAA,IAAa,2BAA2B;AAExC,IAAa,gBAAgB;AAC7B,IAAa,6BAA6B;;AAE1C,IAAa,wBAAwB,GAAG,2BAA2B;AACnE,IAAa,8BAA8B;AAE3C,IAAa,wBAAwB;AACrC,IAAa,wBAAwB;AACrC,IAAa,gCAAgC;;;ACR7C,IAAM,yBAAyB;AAE/B,SAAgB,uBAAuB,OAAuD;CAC5F,OAAO;EACL,kBAAkB,MAAM;EACxB,oBAAoB,MAAM;EAC1B,WAAW,MAAM,UAAU,IAAI,sBAAsB;CACvD;AACF;AAEA,SAAS,uBAAuB,OAAuD;CACrF,MAAM,OAAO,MAAM;CACnB,MAAM,MAAM,KAAK,MACb,OAAO,YAAY,OAAO,QAAQ,KAAK,GAAG,CAAC,CAAC,MAAM,GAAG,sBAAsB,CAAC,IAC5E,KAAA;CACJ,OAAO;EACL,IAAI,MAAM;EACV,MAAM,MAAM;EACZ,WAAW,MAAM;EACjB,SAAS,MAAM;EACf,iBAAiB;GACf,MAAM,KAAK;GACX,WAAW,KAAK;GAChB,KAAK,KAAK;GACV;GACA,SAAS,KAAK;EAChB;CACF;AACF;AAEA,SAAgB,mBAAmB,KAA6C;CAC9E,IAAI,CAAC,OAAO,OAAO,QAAQ,UAAU,OAAO;CAC5C,MAAM,MAAM;CACZ,IAAI,CAAC,MAAM,QAAQ,IAAI,SAAS,GAAG,OAAO;CAE1C,MAAM,YAAsC,CAAC;CAC7C,KAAK,MAAM,QAAQ,IAAI,WAAW;EAChC,IAAI,CAAC,QAAQ,OAAO,SAAS,UAAU;EACvC,MAAM,IAAI;EACV,IAAI,OAAO,EAAE,OAAO,YAAY,OAAO,EAAE,SAAS,YAAY,OAAO,EAAE,cAAc,UACnF;EAEF,MAAM,kBAAmB,EAAE,mBAAmB,CAAC;EAC/C,UAAU,KAAK;GACb,IAAI,EAAE;GACN,MAAM,EAAE;GACR,WAAW,EAAE;GACb,SAAS,OAAO,EAAE,YAAY,WAAW,EAAE,UAAU,EAAE;GACvD;EACF,CAAC;CACH;CAEA,OAAO;EACL;EACA,kBAAkB,OAAO,IAAI,qBAAqB,WAAW,IAAI,mBAAmB;EACpF,oBAAoB,OAAO,IAAI,uBAAuB,WAAW,IAAI,qBAAqB;CAC5F;AACF;AAEA,SAAgB,qBAA6C;CAC3D,OAAO;EAAE,WAAW,CAAC;EAAG,kBAAkB;EAAM,oBAAoB;CAAK;AAC3E;;;AChCA,IAAM,IAAI,MAAM,KAAK,uBAAA,OAAA;CAAA,wBAAA,OAAA;CAAA,wBAAA,OAAA;AAAA,CAAA,GAAkC,IAAI;AAE3D,eAAe,oBAAoB,MAAgC;CACjE,OAAO,cAAc,EAAE,sBAAsB,EAAE,KAAK,CAAC,CAAC;AACxD;AAYA,IAAI,kBAAkB;AAEtB,SAAS,iBAAyB;CAChC,mBAAmB;CACnB,OAAO,YAAY;AACrB;AAEA,IAAM,mBAAN,MAAkD;CAWhD,YACE,IACA,MACA,WACA,iBACA,SACA;EAXO,KAAA,SAAA;EACyB,KAAA,UAAA;EAEP,KAAA,mBAAA;EASzB,KAAK,KAAK;EACV,KAAK,OAAO;EACZ,KAAK,YAAY;EACjB,KAAK,kBAAkB;EACvB,KAAK,UAAU;CACjB;CAEA,SAAS,MAAc,aAAa,MAAY;EAC9C,IAAI,CAAC,KAAK,SAAS;EACnB,KAAK,QAAQ,YAAY,QAAQ,aAAa,OAAO,GAAG;CAC1D;CAEA,KAAK,gBAAgC;EACnC,gBAAgB,mBAAmB;EACnC,gBAAgB,iBAAiB,KAAK,EAAE;EACxC,KAAK,SAAS;CAChB;CAEA,OAAa;EACX,KAAK,SAAS;CAChB;CAEA,MAAM,QAAQ,SAAgD;EAC5D,IAAI,SAAS,YAAY,OAAO,KAAK,mBAAmB;EACxD,MAAM,gBAAgB,gBAAgB,KAAK,EAAE;CAC/C;CAEA,qBAA8B;EAC5B,OAAO,CAAC,KAAK;CACf;CAEA,QAAc;EACZ,KAAK,cAAc;CACrB;AACF;AAEA,IAAM,kBAAN,MAAoD;;EAC9B,KAAA,4BAAA,IAAI,IAA8B;EACZ,KAAA,mBAAA;EACE,KAAA,qBAAA;EACwC,KAAA,qBAAA;EACC,KAAA,kBAAA;EAC5D,KAAA,iBAAA;EAC2B,KAAA,mBAAA;;CAEpD,IAAI,iBAAuC;EACzC,IAAI,CAAC,KAAK,kBAAkB,OAAO,KAAA;EACnC,OAAO,KAAK,UAAU,IAAI,KAAK,gBAAgB;CACjD;CAEA,eAA2B;EACzB,OAAO,CAAC,GAAG,KAAK,UAAU,OAAO,CAAC;CACpC;CAEA,kBAAkB,UAAoD;EACpE,MAAM,QAAQ,UAAU,uBAAuB,QAAQ;EACvD,aAAa,YAAY,KAAK;CAChC;CAEA,mBAAmB,UAAoD;EACrE,MAAM,QAAQ,UAAU,uBAAuB,QAAQ;EACvD,aAAa,YAAY,KAAK;CAChC;CAEA,0BAA0B,UAAgE;EACxF,MAAM,QAAQ,UAAU,+BAA+B,QAAQ;EAC/D,aAAa,YAAY,KAAK;CAChC;CAEA,uBACE,MACA,MACM;EACN,KAAK,qBAAqB;EAC1B,KAAK,kBAAkB;CACzB;CAEA,MAAM,4BAA2C;EAC/C,IAAI,KAAK,kBAAkB,CAAC,KAAK,oBAAoB;EACrD,KAAK,iBAAiB;EACtB,MAAM,MAAM,MAAM,KAAK,mBAAmB;EAC1C,MAAM,QAAQ,MAAM,mBAAmB,GAAG,IAAI;EAC9C,IAAI,CAAC,SAAS,MAAM,UAAU,WAAW,GAAG;EAE5C,KAAK,qBAAqB,MAAM;EAChC,KAAK,MAAM,SAAS,MAAM,WAAW;GACnC,IAAI,CAAC,KAAK,oBAAoB,MAAM,SAAS,GAAG;GAChD,MAAM,KAAK,eAAe;IACxB,GAAG,MAAM;IACT,MAAM,MAAM;IACZ,WAAW,MAAM;IACjB,SAAS,MAAM;GACjB,GAAG,MAAM,EAAE;EACb;EACA,IAAI,MAAM,oBAAoB,KAAK,UAAU,IAAI,MAAM,gBAAgB,GACrE,KAAK,kBAAkB,MAAM,gBAAgB;CAEjD;;CAGA,oBAA4B,WAA4B;EAEtD,OADgB,KAAK,YAAY,CAAC,CAAC,MAAM,MAAM,EAAE,OAAO,SACjD,CAAA,EAAS,YAAY;CAC9B;CAEA,cAA6C;EAC3C,OAAO,qBAAqB,iBAA8C,wBAAwB;CACpG;CAEA,0BAAyC;EACvC,IAAI,KAAK,oBAAoB;GAC3B,MAAM,YAAY,KAAK,YAAY,CAAC,CAAC,MAAM,MAAM,EAAE,OAAO,KAAK,kBAAkB;GACjF,IAAI,WAAW,OAAO,UAAU;EAClC;EACA,MAAM,WAAW,KAAK,YAAY,CAAC,CAAC,QAAQ,MAAM,CAAC,EAAE,MAAM;EAE3D,QADuB,SAAS,MAAM,MAAM,EAAE,SAAS,KAAK,SAAS,GAAA,EAC9C,MAAM;CAC/B;CAEA,oBAAoB,MAAqC;EACvD,KAAK,mBAAmB;CAC1B;CAEA,kBAA2C;EACzC,OAAO,KAAK;CACd;CAEA,qBAA2B;EAEzB,SADuB,cAAc,cAAc,cACnD,CAAA,EAAO,SAAS,aAAa;CAC/B;CAEA,iBAAiB,IAAkB;EACjC,MAAM,OAAO,KAAK,gBAAgB;EAClC,IAAI,MAAM,IAAI,EAAE,GACd,KAAK,SAAS,EAAE;EAElB,KAAK,kBAAkB,EAAE;CAC3B;CAEA,kBAA0B,IAAyB;EACjD,IAAI,KAAK,qBAAqB,IAAI;EAClC,KAAK,mBAAmB;EACxB,QAAQ,+BAA+B,KAAK,KAAK,UAAU,IAAI,EAAE,IAAI,KAAA,CAAS;EAC9E,KAAU,aAAa;CACzB;CAEA,MAAM,eACJ,UAAmC,CAAC,GACpC,UAC+B;EAC/B,MAAM,YAAY,QAAQ,aAAa,KAAK,wBAAwB;EACpE,IAAI,CAAC,WAAW,OAAO,KAAA;EAEvB,MAAM,UAAU,KAAK,YAAY,CAAC,CAAC,MAAM,MAAM,EAAE,OAAO,SAAS;EACjE,IAAI,CAAC,SAAS,OAAO,KAAA;EAErB,MAAM,KAAK,YAAY,eAAe;EACtC,IAAI,UAAU,0BAA0B,QAAQ;EAChD,MAAM,UAAU,QAAQ,WAAW;EACnC,MAAM,OAAO,QAAQ,QAAQ,QAAQ;EAErC,IAAI;EACJ,IAAI;GACF,UAAU,MAAM,QAAQ,OAAO;IAAE,GAAG;IAAS;IAAW;IAAM;GAAQ,CAAC;EACzE,QAAQ;GACN;EACF;EAEA,MAAM,WAAW,IAAI,iBAAiB,IAAI,MAAM,WAAW;GAAE,GAAG;GAAS;GAAW;GAAM;EAAQ,GAAG,OAAO;EAC5G,SAAS,UAAU;EACnB,SAAS,SAAS,QAAQ,UAAU;EAEpC,KAAK,UAAU,IAAI,IAAI,QAAQ;EAC/B,IAAI,CAAC,SAAS,QAAQ;GACpB,KAAK,mBAAmB;GACxB,MAAM,KAAK,kBAAkB;EAC/B;EACA,KAAK,gBAAgB,UAAU,QAAQ,IAAI;EAE3C,IAAI,CAAC,SAAS,QAAQ;GACpB,KAAK,mBAAmB;GACxB,KAAK,iBAAiB,EAAE;EAC1B;EAEA,QAAQ,uBAAuB,QAAQ;EACvC,KAAU,aAAa;EACvB,OAAO;CACT;;CAGA,oBAA2C;EACzC,IAAI,KAAK,kBAAkB,OAAO,QAAQ,QAAQ;EAClD,MAAM,UAAU,YAAY,IAAI;EAChC,OAAO,IAAI,SAAS,YAAY;GAC9B,MAAM,cAAc;IAClB,IAAI,KAAK,oBAAoB,YAAY,IAAI,IAAI,UAAU,KAAM;KAC/D,QAAQ;KACR;IACF;IACA,sBAAsB,KAAK;GAC7B;GACA,sBAAsB,KAAK;EAC7B,CAAC;CACH;CAEA,gBAAwB,UAA4B,MAAqB;EACvE,MAAM,OAAO,KAAK,gBAAgB;EAClC,IAAI,CAAC,MAAM;EAEX,MAAM,eAAgC;GACpC,MAAM,SAAS;GACf,OAAO,SAAS;GAChB,MAAM,QAAQ;GACd,UAAU;GACV,SAAS;GACT,aAAa,YAAY,SAAS,mBAAmB,IAAI,oBAAoB,SAAS,IAAI,IAAI;GAC9F,YAAY,UACV,IAAI,4BAA4B,MAAM,cAAc,SAAS;EACjE;EAEA,IAAI,KAAK,IAAI,SAAS,EAAE,GAAG;GACzB,KAAK,SAAS,SAAS,EAAE;GACzB;EACF;EACA,KAAK,KAAK,YAAY;CACxB;CAEA,MAAM,gBAAgB,IAAY,SAAuD;EACvF,MAAM,WAAW,KAAK,UAAU,IAAI,EAAE;EACtC,IAAI,CAAC,UAAU;EAEf,IAAI,CAAC,SAAS,gBAAgB;GAC5B,MAAM,OAAO,KAAK,gBAAgB;GAClC,IAAI,MAAM,IAAI,EAAE,GAAG;IACjB,MAAM,KAAK,SAAS,IAAI,MAAM,OAAO,GAAG,EAAE;IAC1C;GACF;EACF;EAEA,MAAM,SAAS,SAAS,QAAQ;EAChC,SAAS,UAAU;EACnB,KAAK,UAAU,OAAO,EAAE;EAExB,IAAI,KAAK,qBAAqB,IAAI;GAChC,MAAM,YAAY,CAAC,GAAG,KAAK,UAAU,KAAK,CAAC;GAC3C,KAAK,kBAAkB,UAAU,SAAS,IAAI,UAAU,UAAU,SAAS,KAAK,IAAI;EACtF;EAEA,QAAQ,uBAAuB,QAAQ;EACvC,KAAU,aAAa;CACzB;CAEA,MAAM,UAAyB;EAC7B,MAAM,OAAO,KAAK,gBAAgB;EAClC,MAAM,MAAM,CAAC,GAAG,KAAK,UAAU,KAAK,CAAC;EACrC,KAAK,MAAM,MAAM,KACf,IAAI,MAAM,IAAI,EAAE,GACd,MAAM,KAAK,SAAS,IAAI,MAAM,OAAO,GAAG,EAAE;OAE1C,MAAM,KAAK,gBAAgB,IAAI,EAAE,gBAAgB,KAAK,CAAC;CAG7D;CAEA,qBAAqB,MAAoB;EACvC,MAAM,SAAS,KAAK;EACpB,IAAI,CAAC,UAAU,EAAE,kBAAkB,mBAAmB;EACtD,OAAO,OAAO;EACd,KAAK,gBAAgB,CAAC,EAAE,eAAe,OAAO,IAAI,IAAI;EACtD,KAAU,aAAa;CACzB;CAEA,oBAAoB,WAAyB;EAC3C,KAAK,qBAAqB;EAC1B,KAAU,aAAa;CACzB;CAEA,sBAA4B;EAC1B,KAAK,gBAAgB,QAAQ;CAC/B;CAEA,MAAM,QACJ,cACA,SACe;EACf,IAAI,WAAW,KAAK,aAAa,CAAC,CAAC,MAAM,MAAM,EAAE,cAAc,aAAa,SAAS;EACrF,IAAI,CAAC,UACH,WAAW,MAAM,KAAK,eAAe,EAAE,WAAW,aAAa,UAAU,CAAC;EAE5E,IAAI,CAAC,UAAU;EAEf,IAAI,aAAa,WAAW,SAAS;GACnC,IAAI,aAAa,UAAU,OACzB,SAAS,KAAK;QAEd,KAAK,mBAAmB;EAE5B;EACA,IAAI,aAAa,OACf,SAAS,QAAQ;EAEnB,MAAM,QAAQ,QAAQ;CACxB;CAEA,MAAc,eAA8B;EAC1C,IAAI,CAAC,KAAK,iBAAiB;EAC3B,MAAM,YAAY,CAAC,GAAG,KAAK,UAAU,OAAO,CAAC,CAAC,CAC3C,QAAQ,MAAM,KAAK,oBAAoB,EAAE,SAAS,CAAC,CAAC,CACpD,KAAK,OAAO;GACX,IAAI,EAAE;GACN,MAAM,EAAE;GACR,WAAW,EAAE;GACb,SAAS,EAAE;GACX,iBAAiB,EAAE;EACrB,EAAE;EACJ,MAAM,MAAM,IAAI,IAAI,UAAU,KAAK,MAAM,EAAE,EAAE,CAAC;EAC9C,MAAM,QAAgC;GACpC,kBACE,KAAK,oBAAoB,IAAI,IAAI,KAAK,gBAAgB,IAAI,KAAK,mBAAmB;GACpF,oBAAoB,KAAK;GACzB;EACF;EACA,MAAM,KAAK,gBAAgB,uBAAuB,KAAK,CAAC;CAC1D;CAEA,mBAAmB,SAAuB;EACxC,IAAI,KAAK,UAAU,IAAI,OAAO,GAC5B,KAAK,kBAAkB,OAAO;CAElC;CAEA,gBAAgB,SAAuB;EACrC,IAAI,KAAK,UAAU,IAAI,OAAO,GAC5B,KAAU,gBAAgB,SAAS,EAAE,gBAAgB,KAAK,CAAC;CAE/D;AACF;AAEA,SAAS,0BAA0B,IAAkB;CACnD,MAAM,QAAQ,mBAAmB,KAAK,EAAE;CACxC,IAAI,CAAC,OAAO;CACZ,MAAM,IAAI,OAAO,SAAS,MAAM,IAAI,EAAE;CACtC,IAAI,IAAI,iBAAiB,kBAAkB;AAC7C;AAEA,IAAa,kBAAkB,IAAI,gBAAgB;AACnD,YAAY,IAAI,mBAAmB,eAAe;AAElD,SAAgB,wBAAwB,cAAiD;CACvF,qBAAqB,qBAAqB,0BAA0B,YAAY;CAChF,IAAI,aAAa,QAAQ;CACzB,MAAM,YAAY,aAAa;CAC/B,qBAAqB,qBAAqB,uBAAuB;EAC/D,OAAO,aAAa;EACpB,MAAM,aAAa,QAAQ;EAC3B,iBAAiB,mBAAmB;GAClC,MAAM,aAAa,QAAQ;GAC3B,OAAO,aAAa;GACpB,OAAO,aAAa;GACpB,cAAc;IACZ,gBAAgB,oBAAoB,SAAS;IAC7C,gBAAqB,eAAe,EAAE,UAAU,CAAC;GACnD;EACF,CAAC;CACH,CAAC;AACH;;;AC1aA,IAAM,oBAAoB;AAE1B,SAAS,SAAS,SAA2B;CAC3C,MAAM,SAAmB,CAAC;CAC1B,IAAI,IAAI;CACR,MAAM,MAAM,QAAQ;CAEpB,OAAO,IAAI,KAAK;EACd,OAAO,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,GAAG;EACzC,IAAI,KAAK,KAAK;EAEd,IAAI,QAAQ,OAAO,MAAK;GACtB,IAAI,MAAM,IAAI;GACd,OAAO,MAAM,OAAO,QAAQ,SAAS,MAAK;IACxC,IAAI,QAAQ,SAAS,MAAM;IAC3B;GACF;GACA,OAAO,KAAK,QAAQ,MAAM,IAAI,GAAG,GAAG,CAAC,CAAC,QAAQ,QAAQ,IAAG,CAAC;GAC1D,IAAI,MAAM;EACZ,OAAO;GACL,IAAI,QAAQ;GACZ,OAAO,IAAI,OAAO,CAAC,KAAK,KAAK,QAAQ,EAAE,KAAK,QAAQ,OAAO,MAAK;GAChE,IAAI,IAAI,OACN,OAAO,KAAK,QAAQ,MAAM,OAAO,CAAC,CAAC;EAEvC;CACF;CACA,OAAO;AACT;AAEA,SAAS,WAAW,MAAkE;CACpF,MAAM,SAA6D,CAAC;CACpE,MAAM,QAAQ;CACd,IAAI,YAAY;CAChB,IAAI;CAEJ,QAAQ,QAAQ,MAAM,KAAK,IAAI,OAAO,MAAM;EAC1C,MAAM,UAAU,KAAK,MAAM,WAAW,MAAM,KAAK,CAAC,CAAC,KAAK;EACxD,IAAI,SAAS;GACX,MAAM,KAAK,MAAM,EAAE,CAAC,SAAS,GAAG,IAAK,MAAiB;GACtD,OAAO,KAAK;IAAE;IAAS,UAAU;GAAG,CAAC;EACvC;EACA,YAAY,MAAM;CACpB;CACA,MAAM,OAAO,KAAK,MAAM,SAAS,CAAC,CAAC,KAAK;CACxC,IAAI,MACF,OAAO,KAAK;EAAE,SAAS;EAAM,UAAU;CAAK,CAAC;CAE/C,OAAO;AACT;AAEA,SAAS,cACP,QACA,SACkC;CAClC,MAAM,SAA2C,CAAC;CAClD,MAAM,cAAwB,CAAC;CAC/B,MAAM,aAAa,SAAS,YAAY,KAAK,MAAM,EAAE,IAAI,KAAK,CAAC;CAE/D,KAAK,MAAM,SAAS,QAClB,IAAI,kBAAkB,KAAK,KAAK,GAAG;EACjC,MAAM,QAAQ,MAAM,QAAQ,GAAG;EAC/B,MAAM,OAAO,MAAM,MAAM,GAAG,KAAK;EACjC,MAAM,QAAQ,MAAM,MAAM,QAAQ,CAAC;EACnC,OAAO,QAAQ,UAAU,UAAU,UAAU,UAAU,UAAU,SAAS;CAC5E,OACE,YAAY,KAAK,KAAK;CAI1B,WAAW,SAAS,MAAM,MAAM;EAC9B,IAAI,YAAY,OAAO,KAAA,KAAa,EAAE,QAAQ,SAC5C,OAAO,QAAQ,YAAY;CAE/B,CAAC;CAED,OAAO;AACT;AAEA,SAAgB,eAAe,MAAc,iBAAmD;CAE9F,OADiB,WAAW,IACrB,CAAA,CAAS,KAAK,EAAE,SAAS,eAAe;EAC7C,MAAM,SAAS,SAAS,OAAO;EAC/B,IAAI,OAAO,WAAW,GACpB,OAAO;GAAE,SAAS;IAAE,WAAW;IAAI,QAAQ,CAAC;GAAE;GAAG;EAAS;EAE5D,MAAM,YAAY,OAAO;EACzB,MAAM,UAAU,gBAAgB,WAAW,SAAS,IAChD,gBAAgB,WAAW,SAAS,IACpC,KAAA;EAEJ,OAAO;GAAE,SAAS;IAAE;IAAW,QADhB,cAAc,OAAO,MAAM,CAAC,GAAG,OACf;GAAO;GAAG;EAAS;CACpD,CAAC;AACH;;;;ACxGA,IAAa,YAAb,MAAuB;CAOrB,YAAY,OAAuC;EAA/B,KAAA,QAAA;EANH,KAAA,SAAA;EACA,KAAA,SAAA;EACW,KAAA,UAAA,CAAC;EACN,KAAA,eAAA;EACA,KAAA,eAAA;CAE6B;CAEpD,QAAc;EACZ,KAAK,SAAS;EACd,KAAK,SAAS;EACd,KAAK,eAAe;EACpB,KAAK,eAAe,KAAK,QAAQ;CACnC;;CAGA,KAAK,MAA6B;EAChC,IAAI,SAAS,MAAM;GACjB,MAAM,OAAO,KAAK;GAClB,KAAK,YAAY,IAAI;GACrB,KAAK,SAAS;GACd,KAAK,SAAS;GACd,KAAK,MAAM,MAAM;GACjB,OAAO;EACT;EAEA,IAAI,SAAS,OAAY,SAAS,MAAM;GACtC,KAAK,eAAe;GACpB,OAAO;EACT;EAEA,IAAI,SAAS,YAAY,SAAS,UAAU;GAC1C,KAAK,KAAK,EAAE;GACZ,OAAO;EACT;EACA,IAAI,SAAS,YAAY,SAAS,UAAU;GAC1C,KAAK,KAAK,CAAC;GACX,OAAO;EACT;EACA,IAAI,SAAS,YAAY,SAAS,UAAU;GAC1C,KAAK,YAAY;GACjB,OAAO;EACT;EACA,IAAI,SAAS,YAAY,SAAS,UAAU;GAC1C,KAAK,YAAY;GACjB,OAAO;EACT;EACA,IAAI,SAAS,WAAW;GACtB,KAAK,cAAc;GACnB,OAAO;EACT;EACA,IAAI,SAAS,YAAY,SAAS,UAAU;GAC1C,KAAK,WAAW;GAChB,OAAO;EACT;EACA,IAAI,SAAS,YAAY,SAAS,UAAU;GAC1C,KAAK,UAAU;GACf,OAAO;EACT;EAEA,IAAI,KAAK,WAAW,MAAM,GAAG,OAAO;EAEpC,KAAK,MAAM,QAAQ,MAAM;GACvB,IAAI,OAAO,KAAK;GAChB,KAAK,OAAO,IAAI;EAClB;EACA,OAAO;CACT;CAEA,KAAa,OAAqB;EAChC,MAAM,OAAO,KAAK,SAAS;EAC3B,IAAI,OAAO,KAAK,OAAO,KAAK,OAAO,QAAQ;EAC3C,MAAM,QAAQ,KAAK,IAAI,KAAK;EAC5B,KAAK,SAAS;EACd,KAAK,MAAM,QAAQ,IAAI,QAAQ,MAAM,KAAK,QAAQ,MAAM,EAAE;CAC5D;CAEA,aAA2B;EACzB,IAAI,KAAK,WAAW,GAAG;EACvB,KAAK,MAAM,QAAQ,KAAK,OAAO,EAAE;EACjC,KAAK,SAAS;CAChB;CAEA,YAA0B;EACxB,MAAM,QAAQ,KAAK,OAAO,SAAS,KAAK;EACxC,IAAI,SAAS,GAAG;EAChB,KAAK,MAAM,QAAQ,MAAM,EAAE;EAC3B,KAAK,SAAS,KAAK,OAAO;CAC5B;CAEA,OAAe,MAAoB;EACjC,IAAI,KAAK,WAAW,KAAK,OAAO,QAAQ;GACtC,KAAK,UAAU;GACf,KAAK;GACL,KAAK,MAAM,IAAI;GACf;EACF;EACA,MAAM,OAAO,KAAK,OAAO,MAAM,KAAK,MAAM;EAC1C,KAAK,SAAS,KAAK,OAAO,MAAM,GAAG,KAAK,MAAM,IAAI,OAAO;EACzD,KAAK;EACL,KAAK,MAAM,OAAO,OAAO,QAAQ,KAAK,OAAO,EAAE;CACjD;CAEA,iBAA+B;EAC7B,IAAI,KAAK,WAAW,GAAG;EACvB,IAAI,KAAK,WAAW,KAAK,OAAO,QAAQ;GACtC,KAAK,SAAS,KAAK,OAAO,MAAM,GAAG,EAAE;GACrC,KAAK;GACL,KAAK,MAAM,OAAO;GAClB;EACF;EACA,MAAM,QAAQ,KAAK,OAAO,MAAM,KAAK,MAAM;EAC3C,KAAK,SAAS,KAAK,OAAO,MAAM,GAAG,KAAK,SAAS,CAAC,IAAI;EACtD,KAAK;EACL,KAAK,MAAM,KAAK,MAAM,QAAa,MAAM,SAAS,EAAE,EAAE;CACxD;CAEA,gBAA8B;EAC5B,IAAI,KAAK,UAAU,KAAK,OAAO,QAAQ;EACvC,MAAM,QAAQ,KAAK,OAAO,MAAM,KAAK,SAAS,CAAC;EAC/C,KAAK,MAAM,GAAG,MAAM,QAAa,MAAM,SAAS,EAAE,EAAE;EACpD,KAAK,SAAS,KAAK,OAAO,MAAM,GAAG,KAAK,MAAM,IAAI;CACpD;CAEA,cAAsB,MAAoB;EACxC,IAAI,KAAK,SAAS,GAAG,KAAK,MAAM,QAAQ,KAAK,OAAO,EAAE;EACtD,IAAI,KAAK,OAAO,SAAS,GAAG,KAAK,MAAM,QAAQ;EAC/C,KAAK,SAAS;EACd,KAAK,SAAS,KAAK;EACnB,IAAI,MAAM,KAAK,MAAM,IAAI;CAC3B;CAEA,cAA4B;EAC1B,IAAI,KAAK,QAAQ,WAAW,GAAG;EAC/B,IAAI,KAAK,iBAAiB,KAAK,QAAQ,QACrC,KAAK,eAAe,KAAK;EAE3B,IAAI,KAAK,iBAAiB,GAAG;EAC7B,KAAK;EACL,KAAK,cAAc,KAAK,QAAQ,KAAK,aAAa;CACpD;CAEA,cAA4B;EAC1B,IAAI,KAAK,gBAAgB,KAAK,QAAQ,QAAQ;EAC9C,KAAK;EACL,IAAI,KAAK,iBAAiB,KAAK,QAAQ,QAAQ;GAC7C,KAAK,cAAc,KAAK,YAAY;GACpC,KAAK,eAAe;GACpB;EACF;EACA,KAAK,cAAc,KAAK,QAAQ,KAAK,aAAa;CACpD;CAEA,YAAoB,MAAoB;EACtC,IAAI,KAAK,SAAS,KAAK,KAAK,QAAQ,KAAK,QAAQ,SAAS,OAAO,MAC/D,KAAK,QAAQ,KAAK,IAAI;EAExB,KAAK,eAAe,KAAK,QAAQ;EACjC,KAAK,eAAe;CACtB;AACF;;;ACxJA,SAAS,kBACP,QACA,iBACyB;CACzB,IAAI,UAAU,MAAM,OAAO,CAAC;CAC5B,IAAI,OAAO,WAAW,YAAY,CAAC,MAAM,QAAQ,MAAM,GACrD,OAAO;CAET,MAAM,cAAc,iBAAiB,SAAS;CAC9C,IAAI,aACF,OAAO,GAAG,YAAY,OAAO,OAAO;CAEtC,OAAO,CAAC;AACV;AAEA,eAAsB,aACpB,MACA,WAA4B,iBACR;CACpB,MAAM,WAAW,eAAe,MAAM,QAAQ;CAC9C,MAAM,UAAqB,CAAC;CAC5B,IAAI,cAA8C;CAClD,IAAI;CAEJ,KAAK,IAAI,IAAI,GAAG,IAAI,SAAS,QAAQ,KAAK;EACxC,MAAM,EAAE,SAAS,aAAa,SAAS;EACvC,IAAI,CAAC,QAAQ,WAAW;EAExB,MAAM,MAAM,SAAS,WAAW,QAAQ,SAAS,IAC7C,SAAS,WAAW,QAAQ,SAAS,IACrC,KAAA;EACJ,IAAI,CAAC,KACH,OAAO;GACL,SAAS;GACT;GACA,OAAO,sBAAsB,QAAQ;EACvC;EAGF,MAAM,eAAe;GACnB,GAAG,kBAAkB,eAAe,KAAA,GAAW,mBAAmB;GAClE,GAAG,QAAQ;EACb;EAEA,MAAM,UAAU,SAAS,uBAAuB,YAAY;EAE5D,IAAI;GACF,MAAM,SAAS,SAAS,QAAQ,QAAQ,WAAW,OAAO;GAC1D,MAAM,WAAW,kBAAkB,UAAU,MAAM,SAAS;GAC5D,QAAQ,KAAK,QAAQ;GAErB,IAAI,aAAa,KAAK;IACpB,cAAc,kBAAkB,UAAU,GAAG;IAC7C,sBAAsB;GACxB,OAAO;IACL,cAAc;IACd,sBAAsB,KAAA;GACxB;EACF,SAAS,KAAK;GAEZ,OAAO;IAAE,SAAS;IAAO;IAAS,OADtB,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG;GACd;EAC/C;CACF;CAEA,OAAO;EAAE,SAAS;EAAM;CAAQ;AAClC;AAEA,SAAS,aAAa,QAA2B;CAC/C,IAAI,OAAO,OAAO,OAAO,eAAe,OAAO,MAAM;CACrD,IAAI,OAAO,QAAQ,WAAW,GAAG,OAAO;CACxC,MAAM,OAAO,OAAO,QAAQ,OAAO,QAAQ,SAAS;CACpD,IAAI,QAAQ,MAAM,OAAO;CACzB,IAAI,OAAO,SAAS,UAAU,OAAO,KAAK,UAAU,MAAM,MAAM,CAAC,IAAI;CACrE,OAAO,OAAO,IAAI,IAAI;AACxB;AAEA,IAAa,kBAAb,MAA6B;CAK3B,cAAc;EAJW,KAAA,iCAAA,IAAI,IAA4B;EAExC,KAAA,SAAA;EAGf,KAAK,YAAY,IAAI,WAAW,SAAS,KAAK,KAAK,IAAI,CAAC;CAC1D;CAEA,WAAW,UAA8C;EACvD,KAAK,eAAe,IAAI,QAAQ;EAChC,aAAa,KAAK,eAAe,OAAO,QAAQ;CAClD;CAEA,KAAa,MAAoB;EAC/B,KAAK,MAAM,MAAM,KAAK,gBAAgB,GAAG,IAAI;CAC/C;CAEA,MAAM,OAAsB;EAC1B,KAAK,KAAK,0DAA0D,KAAK,MAAM;CACjF;CAEA,QAAc;EACZ,KAAK,UAAU,MAAM;CACvB;CAEA,cAAc,aAAmD,CAAC;CAElE,YAAY,MAAoB;EAC9B,MAAM,OAAO,KAAK,UAAU,KAAK,IAAI;EACrC,IAAI,SAAS,MAAM;EACnB,KAAU,QAAQ,IAAI;CACxB;CAEA,MAAc,QAAQ,MAA6B;EACjD,MAAM,UAAU,KAAK,KAAK;EAC1B,IAAI,CAAC,SAAS;GACZ,KAAK,KAAK,KAAK,MAAM;GACrB;EACF;EACA,MAAM,SAAS,MAAM,aAAa,OAAO;EACzC,KAAK,KAAK,aAAa,MAAM,CAAC;EAC9B,KAAK,KAAK,KAAK,MAAM;CACvB;AACF;;;AC7HA,IAAa,qBAAqB;AAClC,IAAa,wBAAwB;AAErC,IAAM,SAAS;AAEf,IAAM,2BAAW,IAAI,IAAuB;AAE5C,SAAgB,gBAAgB,WAAyB;CACvD,SAAS,OAAO,SAAS;AAC3B;AAEA,SAAgB,uBAAuB,SAAkD;CACvF,MAAM,YAAY,SAAS,KAAK;CAChC,MAAM,UAAU,YAAY,SAAS,IAAI,SAAS,IAAI,KAAA;CACtD,IAAI,CAAC,SAAS,MAAM,IAAI,MAAM,2CAA2C;CACzE,OAAO,IAAI,cAAc;EACvB;EACA,aAAa;EACb,cAAc,SAAS,KAAK,gBAAgB;CAC9C,CAAC;AACH;AAEA,SAAgB,sBACd,SACA,WACA,MACA,eAAe,WACgB;CAC/B,SAAS,IAAI,WAAW,OAAO;CAC/B,OAAO,gBAAgB,eAAe;EACpC,WAAW;EACX;EACA,KAAK;GAAE,aAAa;GAAW;EAAa;CAC9C,CAAC;AACH;AASA,SAAS,eAAe,OAAwB;CAC9C,IAAI,UAAU,KAAA,GAAW,OAAO;CAChC,IAAI,UAAU,MAAM,OAAO;CAC3B,IAAI,OAAO,UAAU,UAAU,OAAO,KAAK,UAAU,OAAO,MAAM,CAAC,IAAI;CACvE,OAAO,OAAO,KAAK,IAAI;AACzB;AAEA,IAAa,gBAAb,MAAsD;CAQpD,YAAY,SAAgC;EAPnB,KAAA,iCAAA,IAAI,IAA4B;EAKvC,KAAA,UAAA;EAGhB,KAAK,YAAY,IAAI,WAAW,SAAS,KAAK,KAAK,IAAI,CAAC;EACxD,KAAK,UAAU,SAAS,WAAW;EACnC,KAAK,cAAc,SAAS,eAAe,CAAC,SAAS;EACrD,KAAK,eAAe,SAAS,gBAAgB;CAC/C;CAEA,WAAW,UAA8C;EACvD,KAAK,eAAe,IAAI,QAAQ;EAChC,aAAa,KAAK,eAAe,OAAO,QAAQ;CAClD;CAEA,KAAa,MAAoB;EAC/B,KAAK,MAAM,MAAM,KAAK,gBAAgB,GAAG,IAAI;CAC/C;CAEA,aAAgC;EAC9B,IAAI,CAAC,KAAK,SAAS;GACjB,KAAK,UAAU,gBAAgB;GAC/B,KAAK,cAAc;EACrB;EACA,OAAO,KAAK;CACd;CAEA,MAAM,OAAsB;EAC1B,IAAI,CAAC,KAAK,SAAS;GACjB,KAAK,UAAU,gBAAgB;GAC/B,KAAK,cAAc;GACnB,KAAK,KAAK,2BAAkC;GAC5C;EACF;EACA,KAAK,KAAK,eAAe,KAAK,aAAa,YAAmB;CAChE;CAEA,QAAc;EACZ,IAAI,KAAK,aAAa,KAAK,SAAS,MAAM;EAC1C,KAAK,UAAU;EACf,KAAK,UAAU,MAAM;CACvB;CAEA,cAAc,aAAmD,CAAC;CAElE,YAAY,MAAoB;EAC9B,IAAI,KAAK,SAAS;EAClB,MAAM,OAAO,KAAK,UAAU,KAAK,IAAI;EACrC,IAAI,SAAS,MAAM;EACnB,KAAU,QAAQ,IAAI;CACxB;CAEA,MAAc,QAAQ,MAA6B;EACjD,MAAM,UAAU,KAAK,KAAK;EAC1B,IAAI,CAAC,SAAS;GACZ,KAAK,KAAK,MAAM;GAChB;EACF;EAEA,KAAK,UAAU;EACf,IAAI;GAEF,MAAM,SAAS,eAAe,MADT,KAAK,WAAW,CAAC,CAAC,QAAQ,OAAO,CAClB;GACpC,IAAI,QAAQ,KAAK,KAAK,MAAM;EAC9B,SAAS,KAAK;GACZ,MAAM,MAAM,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG;GAC3D,KAAK,KAAK,WAAW,IAAI,YAAY;EACvC,UAAU;GACR,KAAK,UAAU;GACf,KAAK,KAAK,MAAM;EAClB;CACF;AACF"}
|
|
@@ -1,11 +1,24 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { JsRuntime } from '@eclipse-docks/core';
|
|
2
|
+
import { Terminal, TerminalBackend, TerminalCreationOptions } from './terminal-api';
|
|
2
3
|
export declare const JS_REPL_PROFILE_ID = "terminal.javascript-repl";
|
|
4
|
+
export declare const JS_SESSION_PROFILE_ID = "terminal.javascript-session";
|
|
5
|
+
export declare function unbindJsSession(sessionId: string): void;
|
|
6
|
+
export declare function createJsSessionBackend(options?: TerminalCreationOptions): JsReplBackend;
|
|
7
|
+
export declare function openJsSessionTerminal(runtime: JsRuntime, sessionId: string, name: string, sessionLabel?: string): Promise<Terminal | undefined>;
|
|
8
|
+
interface JsReplBackendOptions {
|
|
9
|
+
runtime?: JsRuntime;
|
|
10
|
+
/** When false, closing the terminal leaves the runtime running. */
|
|
11
|
+
ownsRuntime?: boolean;
|
|
12
|
+
sessionLabel?: string;
|
|
13
|
+
}
|
|
3
14
|
export declare class JsReplBackend implements TerminalBackend {
|
|
4
15
|
private writeCallbacks;
|
|
5
16
|
private lineInput;
|
|
6
17
|
private runtime;
|
|
18
|
+
private ownsRuntime;
|
|
19
|
+
private sessionLabel;
|
|
7
20
|
private running;
|
|
8
|
-
constructor();
|
|
21
|
+
constructor(options?: JsReplBackendOptions);
|
|
9
22
|
onDidWrite(callback: (data: string) => void): () => void;
|
|
10
23
|
private emit;
|
|
11
24
|
private getRuntime;
|
|
@@ -18,4 +31,5 @@ export declare class JsReplBackend implements TerminalBackend {
|
|
|
18
31
|
handleInput(data: string): void;
|
|
19
32
|
private runLine;
|
|
20
33
|
}
|
|
34
|
+
export {};
|
|
21
35
|
//# sourceMappingURL=js-terminal-backend.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"js-terminal-backend.d.ts","sourceRoot":"","sources":["../src/js-terminal-backend.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"js-terminal-backend.d.ts","sourceRoot":"","sources":["../src/js-terminal-backend.ts"],"names":[],"mappings":"AAAA,OAAO,EAAmB,KAAK,SAAS,EAAE,MAAM,qBAAqB,CAAC;AAEtE,OAAO,KAAK,EAAE,QAAQ,EAAE,eAAe,EAAE,uBAAuB,EAAE,MAAM,gBAAgB,CAAC;AAGzF,eAAO,MAAM,kBAAkB,6BAA6B,CAAC;AAC7D,eAAO,MAAM,qBAAqB,gCAAgC,CAAC;AAMnE,wBAAgB,eAAe,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,CAEvD;AAED,wBAAgB,sBAAsB,CAAC,OAAO,CAAC,EAAE,uBAAuB,GAAG,aAAa,CASvF;AAED,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,SAAS,EAClB,SAAS,EAAE,MAAM,EACjB,IAAI,EAAE,MAAM,EACZ,YAAY,SAAY,GACvB,OAAO,CAAC,QAAQ,GAAG,SAAS,CAAC,CAO/B;AAED,UAAU,oBAAoB;IAC5B,OAAO,CAAC,EAAE,SAAS,CAAC;IACpB,mEAAmE;IACnE,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AASD,qBAAa,aAAc,YAAW,eAAe;IACnD,OAAO,CAAC,cAAc,CAAqC;IAC3D,OAAO,CAAC,SAAS,CAAY;IAC7B,OAAO,CAAC,OAAO,CAAmB;IAClC,OAAO,CAAC,WAAW,CAAU;IAC7B,OAAO,CAAC,YAAY,CAAS;IAC7B,OAAO,CAAC,OAAO,CAAS;gBAEZ,OAAO,CAAC,EAAE,oBAAoB;IAO1C,UAAU,CAAC,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,GAAG,MAAM,IAAI;IAKxD,OAAO,CAAC,IAAI;IAIZ,OAAO,CAAC,UAAU;IAQZ,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAU3B,KAAK,IAAI,IAAI;IAMb,aAAa,CAAC,WAAW,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI;IAEhE,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI;YAOjB,OAAO;CAoBtB"}
|
package/dist/terminal-api.d.ts
CHANGED
|
@@ -55,7 +55,9 @@ export interface Terminal {
|
|
|
55
55
|
sendText(text: string, addNewLine?: boolean): void;
|
|
56
56
|
show(preserveFocus?: boolean): void;
|
|
57
57
|
hide(): void;
|
|
58
|
-
dispose(
|
|
58
|
+
dispose(options?: {
|
|
59
|
+
confirm?: boolean;
|
|
60
|
+
}): Promise<void>;
|
|
59
61
|
clear?(): void;
|
|
60
62
|
}
|
|
61
63
|
/** Internal terminal handle used by the host UI (not for provider extensions). */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"terminal-api.d.ts","sourceRoot":"","sources":["../src/terminal-api.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,wBAAwB,6BAA6B,CAAC;AAEnE,eAAO,MAAM,aAAa,kBAAkB,CAAC;AAC7C,eAAO,MAAM,0BAA0B,uBAAuB,CAAC;AAC/D,0FAA0F;AAC1F,eAAO,MAAM,qBAAqB,2BAAsC,CAAC;AACzE,eAAO,MAAM,2BAA2B,yBAAyB,CAAC;AAElE,eAAO,MAAM,qBAAqB,2BAA2B,CAAC;AAC9D,eAAO,MAAM,qBAAqB,2BAA2B,CAAC;AAC9D,eAAO,MAAM,6BAA6B,kCAAkC,CAAC;AAE7E,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd;AAED,MAAM,WAAW,uBAAuB;IACtC,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,GAAG,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IAC7B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,WAAW,eAAe;IAC9B,IAAI,CAAC,CAAC,iBAAiB,CAAC,EAAE,kBAAkB,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACpE,KAAK,CAAC,IAAI,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAC/B,UAAU,CAAC,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,GAAG,MAAM,IAAI,CAAC;IACzD,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,aAAa,CAAC,CAAC,UAAU,EAAE,kBAAkB,GAAG,IAAI,CAAC;CACtD;AAED,MAAM,WAAW,2BAA2B;IAC1C,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB;;;OAGG;IACH,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,MAAM,CAAC,OAAO,CAAC,EAAE,uBAAuB,GAAG,OAAO,CAAC,eAAe,CAAC,CAAC;CACrE;AAED,MAAM,WAAW,wBAAwB;IACvC,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,QAAQ,GAAG,QAAQ,GAAG,OAAO,CAAC;IACvC,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB;AAED,MAAM,WAAW,QAAQ;IACvB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,eAAe,EAAE,uBAAuB,CAAC;IAClD,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,MAAM,EAAE,OAAO,CAAC;IAChB,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,UAAU,CAAC,EAAE,OAAO,GAAG,IAAI,CAAC;IACnD,IAAI,CAAC,aAAa,CAAC,EAAE,OAAO,GAAG,IAAI,CAAC;IACpC,IAAI,IAAI,IAAI,CAAC;IACb,OAAO,
|
|
1
|
+
{"version":3,"file":"terminal-api.d.ts","sourceRoot":"","sources":["../src/terminal-api.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { _ as
|
|
1
|
+
import { _ as TERMINAL_PANEL_SETTINGS_KEY, b as TOPIC_TERMINAL_OPENED, d as emptyTerminalState, f as parseTerminalState, g as TERMINAL_NEW_DROPDOWN, h as TERMINAL_INSTANCES_TABS_ID, i as createJsSessionBackend, l as registerTerminalProfile, n as JS_SESSION_PROFILE_ID, r as JsReplBackend, s as CommandsBackend, t as JS_REPL_PROFILE_ID, u as terminalService, v as TOPIC_TERMINAL_ACTIVE_CHANGED, x as VIEW_TERMINAL, y as TOPIC_TERMINAL_CLOSED } from "./js-terminal-backend-CRxDAwvr.js";
|
|
2
2
|
import { DocksPart, PANEL_BOTTOM, appSettings, contributionRegistry, promptDialog, subscribe, unsubscribe } from "@eclipse-docks/core";
|
|
3
3
|
import { createRef, css, customElement, html, property, ref, unsafeCSS } from "@eclipse-docks/core/externals/lit";
|
|
4
4
|
import { Terminal } from "@xterm/xterm";
|
|
@@ -427,6 +427,14 @@ async function activate() {
|
|
|
427
427
|
icon: "code",
|
|
428
428
|
create: async () => new JsReplBackend()
|
|
429
429
|
});
|
|
430
|
+
registerTerminalProfile({
|
|
431
|
+
id: JS_SESSION_PROFILE_ID,
|
|
432
|
+
label: "JavaScript",
|
|
433
|
+
icon: "code",
|
|
434
|
+
hidden: true,
|
|
435
|
+
persist: false,
|
|
436
|
+
create: async (options) => createJsSessionBackend(options)
|
|
437
|
+
});
|
|
430
438
|
contributionRegistry.registerContribution(PANEL_BOTTOM, {
|
|
431
439
|
name: VIEW_TERMINAL,
|
|
432
440
|
label: "Terminal",
|
|
@@ -437,4 +445,4 @@ async function activate() {
|
|
|
437
445
|
//#endregion
|
|
438
446
|
export { activate as default };
|
|
439
447
|
|
|
440
|
-
//# sourceMappingURL=terminal-extension-
|
|
448
|
+
//# sourceMappingURL=terminal-extension-CnPHiXG4.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"terminal-extension-CKb5tCLo.js","names":[],"sources":["../src/terminal-theme.ts","../src/terminal-view.ts","../src/terminal-panel.ts","../src/terminal-extension.ts"],"sourcesContent":["import type { ITheme } from '@xterm/xterm';\n\nfunction cssVar(name: string, fallback: string): string {\n const value = getComputedStyle(document.documentElement).getPropertyValue(name).trim();\n return value || fallback;\n}\n\nexport function isDarkTheme(): boolean {\n const root = document.documentElement;\n if (root.classList.contains('wa-dark')) return true;\n if (root.classList.contains('wa-light')) return false;\n return true;\n}\n\nexport function getTerminalTheme(): ITheme {\n const dark = isDarkTheme();\n return {\n background: cssVar('--wa-color-surface-lowered', dark ? '#1e1e1e' : '#f3f3f3'),\n foreground: cssVar('--wa-color-text-normal', dark ? '#d4d4d4' : '#1e1e1e'),\n cursor: cssVar('--wa-color-text-normal', dark ? '#d4d4d4' : '#1e1e1e'),\n cursorAccent: cssVar('--wa-color-surface-lowered', dark ? '#1e1e1e' : '#f3f3f3'),\n selectionBackground: cssVar('--wa-color-brand-fill-quiet', dark ? '#264f7840' : '#add6ff80'),\n selectionForeground: cssVar('--wa-color-text-normal', dark ? '#d4d4d4' : '#1e1e1e'),\n black: cssVar('--wa-color-neutral-10', dark ? '#000000' : '#1e1e1e'),\n red: cssVar('--wa-color-danger-fill-loud', '#cd3131'),\n green: cssVar('--wa-color-success-fill-loud', '#0dbc79'),\n yellow: cssVar('--wa-color-warning-fill-loud', '#e5e510'),\n blue: cssVar('--wa-color-brand-fill-loud', '#2472c8'),\n magenta: cssVar('--wa-color-purple-50', '#bc3fbc'),\n cyan: cssVar('--wa-color-cyan-50', '#11a8cd'),\n white: cssVar('--wa-color-neutral-90', dark ? '#e5e5e5' : '#ffffff'),\n brightBlack: cssVar('--wa-color-neutral-50', '#666666'),\n brightRed: cssVar('--wa-color-danger-50', '#f14c4c'),\n brightGreen: cssVar('--wa-color-success-50', '#23d18b'),\n brightYellow: cssVar('--wa-color-warning-50', '#f5f543'),\n brightBlue: cssVar('--wa-color-brand-50', '#3b8eea'),\n brightMagenta: cssVar('--wa-color-purple-40', '#d670d6'),\n brightCyan: cssVar('--wa-color-cyan-40', '#29b8db'),\n brightWhite: cssVar('--wa-color-neutral-95', '#ffffff'),\n };\n}\n\n/** Watches `wa-dark` / `wa-light` on `<html>`, same pattern as docks-monaco-widget. */\nexport function observeTerminalTheme(onChange: () => void): () => void {\n const root = document.documentElement;\n let dark = isDarkTheme();\n\n const observer = new MutationObserver(() => {\n const next = isDarkTheme();\n if (next === dark) return;\n dark = next;\n onChange();\n });\n\n observer.observe(root, { attributes: true, attributeFilter: ['class'] });\n return () => observer.disconnect();\n}\n","import { css, createRef, customElement, html, property, ref, unsafeCSS, type Ref } from '@eclipse-docks/core/externals/lit';\nimport { Terminal } from '@xterm/xterm';\nimport { FitAddon } from '@xterm/addon-fit';\nimport { DocksPart } from '@eclipse-docks/core';\nimport { terminalService } from './terminal-service';\nimport type { TerminalRuntime } from './terminal-api';\nimport { getTerminalTheme, observeTerminalTheme } from './terminal-theme';\nimport xtermStyles from '@xterm/xterm/css/xterm.css?raw';\n\n@customElement('docks-terminal-view')\nexport class DocksTerminalView extends DocksPart {\n protected scrollMode: 'scroller' | 'native' | 'none' = 'none';\n\n @property({ attribute: false })\n terminal?: TerminalRuntime;\n\n private xtermRef: Ref<HTMLDivElement> = createRef();\n private xterm: Terminal | null = null;\n private fitAddon: FitAddon | null = null;\n private unsubscribeWrite: (() => void) | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private tabsHost: Element | null = null;\n private tabPanelName: string | null = null;\n private onTabShow: ((event: Event) => void) | null = null;\n private backendOpened = false;\n private unobserveTheme: (() => void) | null = null;\n\n connectedCallback(): void {\n super.connectedCallback();\n void this.initTerminal();\n }\n\n disconnectedCallback(): void {\n this.teardownTerminal();\n super.disconnectedCallback();\n }\n\n close(): void {\n if (this.terminal) {\n terminalService.handleTabClosed(this.terminal.id);\n }\n this.teardownTerminal();\n }\n\n private findTabContext(): { panelName: string; tabPanel: HTMLElement; tabsHost: Element } | null {\n let panelName: string | null = null;\n let tabPanel: HTMLElement | null = null;\n let tabsHost: Element | null = null;\n let el: Element | null = this;\n\n while (el) {\n const tag = el.tagName?.toLowerCase();\n if (tag === 'wa-tab-panel' && !tabPanel) {\n tabPanel = el as HTMLElement;\n panelName = el.getAttribute('name');\n }\n if (tag === 'docks-tabs') {\n tabsHost = el;\n break;\n }\n const parent: Element | null = el.parentElement;\n if (parent) {\n el = parent;\n } else {\n const root = el.getRootNode();\n el = root instanceof ShadowRoot ? (root.host as Element) : null;\n }\n }\n\n if (!tabsHost || !tabPanel || !panelName) return null;\n return { panelName, tabPanel, tabsHost };\n }\n\n private isTabPanelActive(tabPanel: HTMLElement): boolean {\n return tabPanel.hasAttribute('active');\n }\n\n private attachTabVisibilityHandling(context: {\n panelName: string;\n tabsHost: Element;\n }): void {\n this.tabsHost = context.tabsHost;\n this.tabPanelName = context.panelName;\n this.onTabShow = (event: Event) => {\n const name = (event as CustomEvent<{ name?: string }>).detail?.name;\n if (name !== context.panelName) return;\n this.onTabShown();\n };\n context.tabsHost.addEventListener('wa-tab-show', this.onTabShow);\n }\n\n private detachTabVisibilityHandling(): void {\n if (this.tabsHost && this.onTabShow) {\n this.tabsHost.removeEventListener('wa-tab-show', this.onTabShow);\n }\n this.tabsHost = null;\n this.tabPanelName = null;\n this.onTabShow = null;\n }\n\n private scheduleFit(focus = false): void {\n requestAnimationFrame(() => {\n requestAnimationFrame(() => {\n this.applyFit();\n if (focus) this.xterm?.focus();\n });\n });\n }\n\n private async openBackendIfNeeded(): Promise<void> {\n if (this.backendOpened || !this.terminal?.backend) return;\n this.backendOpened = true;\n await this.terminal.backend.open?.(this.getDimensions());\n }\n\n private onTabShown(): void {\n this.scheduleFit(true);\n void this.openBackendIfNeeded();\n }\n\n private async initTerminal(): Promise<void> {\n if (!this.terminal?.backend) return;\n await this.updateComplete;\n\n const container = this.xtermRef.value;\n if (!container) return;\n\n this.xterm = new Terminal({\n cursorBlink: true,\n fontFamily: 'var(--wa-font-mono, monospace)',\n fontSize: 13,\n theme: getTerminalTheme(),\n });\n this.fitAddon = new FitAddon();\n this.xterm.loadAddon(this.fitAddon);\n this.xterm.open(container);\n\n const backend = this.terminal.backend;\n this.unsubscribeWrite = backend.onDidWrite((data) => {\n this.xterm?.write(data);\n });\n\n this.xterm.onData((data) => {\n backend.handleInput(data);\n });\n\n this.terminal.clearScreen = () => {\n this.xterm?.clear();\n };\n\n this.unobserveTheme = observeTerminalTheme(() => {\n if (!this.xterm) return;\n this.xterm.options.theme = getTerminalTheme();\n });\n\n this.resizeObserver = new ResizeObserver(() => {\n if (!this.isVisible()) return;\n this.scheduleFit();\n });\n this.resizeObserver.observe(container);\n this.resizeObserver.observe(this);\n this.observeAncestorResizableGrids(container);\n\n const tabContext = this.findTabContext();\n if (tabContext) {\n this.attachTabVisibilityHandling(tabContext);\n }\n\n if (!tabContext || this.isTabPanelActive(tabContext.tabPanel)) {\n this.scheduleFit(true);\n void this.openBackendIfNeeded();\n }\n }\n\n private observeAncestorResizableGrids(from: Element): void {\n if (!this.resizeObserver) return;\n let el: Element | null = from;\n while (el) {\n if (el.tagName?.toLowerCase() === 'docks-resizable-grid') {\n this.resizeObserver.observe(el);\n }\n const parent: Element | null = el.parentElement;\n if (parent) {\n el = parent;\n } else {\n const root = el.getRootNode();\n el = root instanceof ShadowRoot ? (root.host as Element) : null;\n }\n }\n }\n\n private isVisible(): boolean {\n if (!this.tabPanelName) return true;\n return this.offsetParent !== null;\n }\n\n private applyFit(): void {\n if (!this.fitAddon || !this.xterm || !this.isVisible()) return;\n try {\n this.fitAddon.fit();\n } catch {\n return;\n }\n const dims = this.getDimensions();\n this.terminal?.backend?.setDimensions?.(dims);\n }\n\n private getDimensions(): { cols: number; rows: number } {\n return {\n cols: this.xterm?.cols ?? 80,\n rows: this.xterm?.rows ?? 24,\n };\n }\n\n private teardownTerminal(): void {\n this.detachTabVisibilityHandling();\n this.unobserveTheme?.();\n this.unobserveTheme = null;\n this.backendOpened = false;\n this.resizeObserver?.disconnect();\n this.resizeObserver = null;\n this.unsubscribeWrite?.();\n this.unsubscribeWrite = null;\n this.xterm?.dispose();\n this.xterm = null;\n this.fitAddon = null;\n }\n\n protected renderContent() {\n return html`<div class=\"terminal-host\" ${ref(this.xtermRef)}></div>`;\n }\n\n static styles = [\n unsafeCSS(xtermStyles),\n css`\n :host {\n display: flex;\n flex-direction: column;\n height: 100%;\n width: 100%;\n min-height: 0;\n }\n\n .part-shell {\n display: flex;\n flex-direction: column;\n flex: 1;\n min-height: 0;\n height: 100%;\n }\n\n .part-content {\n flex: 1;\n min-height: 0;\n display: flex;\n flex-direction: column;\n }\n\n .part-content-inner {\n flex: 1;\n min-height: 0;\n height: 100%;\n display: flex;\n flex-direction: column;\n }\n\n .terminal-host {\n flex: 1;\n min-height: 0;\n height: 100%;\n width: 100%;\n overflow: hidden;\n background: var(--wa-color-surface-lowered);\n padding-left: var(--wa-space-s);\n box-sizing: border-box;\n }\n\n .terminal-host .xterm {\n height: 100%;\n }\n `,\n ];\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'docks-terminal-view': DocksTerminalView;\n }\n}\n","import { css, customElement, html } from '@eclipse-docks/core/externals/lit';\nimport {\n DocksPart,\n appSettings,\n promptDialog,\n subscribe,\n unsubscribe,\n} from '@eclipse-docks/core';\nimport {\n TERMINAL_INSTANCES_TABS_ID,\n TERMINAL_NEW_DROPDOWN,\n TERMINAL_PANEL_SETTINGS_KEY,\n TOPIC_TERMINAL_ACTIVE_CHANGED,\n TOPIC_TERMINAL_CLOSED,\n TOPIC_TERMINAL_OPENED,\n type PersistedTerminalState,\n} from './terminal-api';\nimport { emptyTerminalState, parseTerminalState } from './terminal-persistence';\nimport { terminalService, type TerminalTabsHost } from './terminal-service';\nimport './terminal-view';\n\n@customElement('docks-terminal-panel')\nexport class DocksTerminalPanel extends DocksPart {\n protected scrollMode: 'scroller' | 'native' | 'none' = 'none';\n\n private unsubscribeTerminalEvents: (() => void)[] = [];\n\n connectedCallback(): void {\n super.connectedCallback();\n terminalService.setPersistenceHandlers(\n () => this.loadPersistedState(),\n (state) => this.savePersistedState(state)\n );\n for (const topic of [TOPIC_TERMINAL_ACTIVE_CHANGED, TOPIC_TERMINAL_OPENED, TOPIC_TERMINAL_CLOSED]) {\n const token = subscribe(topic, () => this.requestUpdate());\n this.unsubscribeTerminalEvents.push(() => unsubscribe(token));\n }\n this.updateComplete.then(() => {\n this.bindInstanceTabsHost();\n this.attachTabActivationListener();\n void terminalService.restorePersistedTerminals();\n });\n }\n\n private bindInstanceTabsHost(): void {\n const tabs = this.renderRoot.querySelector(\n `docks-tabs#${TERMINAL_INSTANCES_TABS_ID}`\n ) as TerminalTabsHost | null;\n terminalService.setInstanceTabsHost(tabs);\n }\n\n private attachTabActivationListener(): void {\n const tabs = this.renderRoot.querySelector('docks-tabs');\n if (!tabs) return;\n tabs.addEventListener('wa-tab-show', (event: Event) => {\n const name = (event as CustomEvent<{ name?: string }>).detail?.name;\n if (name) terminalService.handleTabActivated(name);\n });\n }\n\n disconnectedCallback(): void {\n for (const off of this.unsubscribeTerminalEvents) off();\n this.unsubscribeTerminalEvents = [];\n terminalService.setInstanceTabsHost(null);\n super.disconnectedCallback();\n }\n\n private async loadPersistedState(): Promise<PersistedTerminalState | null> {\n const raw = await appSettings.getDialogSetting(TERMINAL_PANEL_SETTINGS_KEY);\n return parseTerminalState(raw) ?? emptyTerminalState();\n }\n\n private async savePersistedState(state: PersistedTerminalState): Promise<void> {\n await appSettings.setDialogSetting(TERMINAL_PANEL_SETTINGS_KEY, state);\n }\n\n protected renderToolbar() {\n const hasActive = !!terminalService.activeTerminal;\n return html`\n <docks-command\n icon=\"plus\"\n title=\"New Terminal\"\n dropdown=\"${TERMINAL_NEW_DROPDOWN}\"\n .action=${() => void terminalService.createTerminal()}\n >\n </docks-command>\n <docks-command\n icon=\"xmark\"\n title=\"Kill Terminal\"\n ?disabled=${!hasActive}\n .action=${async () => {\n await terminalService.activeTerminal?.dispose();\n }}\n ></docks-command>\n <docks-command\n icon=\"eraser\"\n title=\"Clear\"\n ?disabled=${!hasActive}\n .action=${() => {\n terminalService.activeTerminal?.clear?.();\n }}\n ></docks-command>\n <docks-command\n icon=\"pen\"\n title=\"Rename\"\n ?disabled=${!hasActive}\n .action=${async () => {\n const active = terminalService.activeTerminal;\n if (!active) return;\n const name = await promptDialog('Terminal name', active.name);\n if (name?.trim()) terminalService.renameActiveTerminal(name.trim());\n }}\n ></docks-command>\n `;\n }\n\n protected renderContent() {\n return html`\n <docks-tabs\n id=\"${TERMINAL_INSTANCES_TABS_ID}\"\n placement=\"start\"\n item-size=\"s\"\n ></docks-tabs>\n `;\n }\n\n static styles = css`\n :host {\n display: flex;\n flex-direction: column;\n height: 100%;\n width: 100%;\n min-height: 0;\n }\n\n docks-tabs {\n flex: 1;\n min-height: 0;\n }\n `;\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'docks-terminal-panel': DocksTerminalPanel;\n }\n}\n","import { html } from '@eclipse-docks/core/externals/lit';\nimport { contributionRegistry, PANEL_BOTTOM, registerAll } from '@eclipse-docks/core';\nimport { VIEW_TERMINAL } from './terminal-api';\nimport { CommandsBackend } from './commands-backend';\nimport { JsReplBackend, JS_REPL_PROFILE_ID } from './js-terminal-backend';\nimport { registerTerminalProfile, terminalService } from './terminal-service';\nimport './terminal-panel';\n\nconst COMMANDS_PROFILE_ID = 'terminal.javascript-shell';\n\nexport default async function activate() {\n registerTerminalProfile({\n id: COMMANDS_PROFILE_ID,\n label: 'Commands',\n icon: 'terminal',\n isDefault: true,\n create: async () => new CommandsBackend(),\n });\n\n registerTerminalProfile({\n id: JS_REPL_PROFILE_ID,\n label: 'JavaScript',\n icon: 'code',\n create: async () => new JsReplBackend(),\n });\n\n contributionRegistry.registerContribution(PANEL_BOTTOM, {\n name: VIEW_TERMINAL,\n label: 'Terminal',\n icon: 'terminal',\n component: (id: string) => html`<docks-terminal-panel id=\"${id}\"></docks-terminal-panel>`,\n });\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"terminal-extension-CnPHiXG4.js","names":[],"sources":["../src/terminal-theme.ts","../src/terminal-view.ts","../src/terminal-panel.ts","../src/terminal-extension.ts"],"sourcesContent":["import type { ITheme } from '@xterm/xterm';\n\nfunction cssVar(name: string, fallback: string): string {\n const value = getComputedStyle(document.documentElement).getPropertyValue(name).trim();\n return value || fallback;\n}\n\nexport function isDarkTheme(): boolean {\n const root = document.documentElement;\n if (root.classList.contains('wa-dark')) return true;\n if (root.classList.contains('wa-light')) return false;\n return true;\n}\n\nexport function getTerminalTheme(): ITheme {\n const dark = isDarkTheme();\n return {\n background: cssVar('--wa-color-surface-lowered', dark ? '#1e1e1e' : '#f3f3f3'),\n foreground: cssVar('--wa-color-text-normal', dark ? '#d4d4d4' : '#1e1e1e'),\n cursor: cssVar('--wa-color-text-normal', dark ? '#d4d4d4' : '#1e1e1e'),\n cursorAccent: cssVar('--wa-color-surface-lowered', dark ? '#1e1e1e' : '#f3f3f3'),\n selectionBackground: cssVar('--wa-color-brand-fill-quiet', dark ? '#264f7840' : '#add6ff80'),\n selectionForeground: cssVar('--wa-color-text-normal', dark ? '#d4d4d4' : '#1e1e1e'),\n black: cssVar('--wa-color-neutral-10', dark ? '#000000' : '#1e1e1e'),\n red: cssVar('--wa-color-danger-fill-loud', '#cd3131'),\n green: cssVar('--wa-color-success-fill-loud', '#0dbc79'),\n yellow: cssVar('--wa-color-warning-fill-loud', '#e5e510'),\n blue: cssVar('--wa-color-brand-fill-loud', '#2472c8'),\n magenta: cssVar('--wa-color-purple-50', '#bc3fbc'),\n cyan: cssVar('--wa-color-cyan-50', '#11a8cd'),\n white: cssVar('--wa-color-neutral-90', dark ? '#e5e5e5' : '#ffffff'),\n brightBlack: cssVar('--wa-color-neutral-50', '#666666'),\n brightRed: cssVar('--wa-color-danger-50', '#f14c4c'),\n brightGreen: cssVar('--wa-color-success-50', '#23d18b'),\n brightYellow: cssVar('--wa-color-warning-50', '#f5f543'),\n brightBlue: cssVar('--wa-color-brand-50', '#3b8eea'),\n brightMagenta: cssVar('--wa-color-purple-40', '#d670d6'),\n brightCyan: cssVar('--wa-color-cyan-40', '#29b8db'),\n brightWhite: cssVar('--wa-color-neutral-95', '#ffffff'),\n };\n}\n\n/** Watches `wa-dark` / `wa-light` on `<html>`, same pattern as docks-monaco-widget. */\nexport function observeTerminalTheme(onChange: () => void): () => void {\n const root = document.documentElement;\n let dark = isDarkTheme();\n\n const observer = new MutationObserver(() => {\n const next = isDarkTheme();\n if (next === dark) return;\n dark = next;\n onChange();\n });\n\n observer.observe(root, { attributes: true, attributeFilter: ['class'] });\n return () => observer.disconnect();\n}\n","import { css, createRef, customElement, html, property, ref, unsafeCSS, type Ref } from '@eclipse-docks/core/externals/lit';\nimport { Terminal } from '@xterm/xterm';\nimport { FitAddon } from '@xterm/addon-fit';\nimport { DocksPart } from '@eclipse-docks/core';\nimport { terminalService } from './terminal-service';\nimport type { TerminalRuntime } from './terminal-api';\nimport { getTerminalTheme, observeTerminalTheme } from './terminal-theme';\nimport xtermStyles from '@xterm/xterm/css/xterm.css?raw';\n\n@customElement('docks-terminal-view')\nexport class DocksTerminalView extends DocksPart {\n protected scrollMode: 'scroller' | 'native' | 'none' = 'none';\n\n @property({ attribute: false })\n terminal?: TerminalRuntime;\n\n private xtermRef: Ref<HTMLDivElement> = createRef();\n private xterm: Terminal | null = null;\n private fitAddon: FitAddon | null = null;\n private unsubscribeWrite: (() => void) | null = null;\n private resizeObserver: ResizeObserver | null = null;\n private tabsHost: Element | null = null;\n private tabPanelName: string | null = null;\n private onTabShow: ((event: Event) => void) | null = null;\n private backendOpened = false;\n private unobserveTheme: (() => void) | null = null;\n\n connectedCallback(): void {\n super.connectedCallback();\n void this.initTerminal();\n }\n\n disconnectedCallback(): void {\n this.teardownTerminal();\n super.disconnectedCallback();\n }\n\n close(): void {\n if (this.terminal) {\n terminalService.handleTabClosed(this.terminal.id);\n }\n this.teardownTerminal();\n }\n\n private findTabContext(): { panelName: string; tabPanel: HTMLElement; tabsHost: Element } | null {\n let panelName: string | null = null;\n let tabPanel: HTMLElement | null = null;\n let tabsHost: Element | null = null;\n let el: Element | null = this;\n\n while (el) {\n const tag = el.tagName?.toLowerCase();\n if (tag === 'wa-tab-panel' && !tabPanel) {\n tabPanel = el as HTMLElement;\n panelName = el.getAttribute('name');\n }\n if (tag === 'docks-tabs') {\n tabsHost = el;\n break;\n }\n const parent: Element | null = el.parentElement;\n if (parent) {\n el = parent;\n } else {\n const root = el.getRootNode();\n el = root instanceof ShadowRoot ? (root.host as Element) : null;\n }\n }\n\n if (!tabsHost || !tabPanel || !panelName) return null;\n return { panelName, tabPanel, tabsHost };\n }\n\n private isTabPanelActive(tabPanel: HTMLElement): boolean {\n return tabPanel.hasAttribute('active');\n }\n\n private attachTabVisibilityHandling(context: {\n panelName: string;\n tabsHost: Element;\n }): void {\n this.tabsHost = context.tabsHost;\n this.tabPanelName = context.panelName;\n this.onTabShow = (event: Event) => {\n const name = (event as CustomEvent<{ name?: string }>).detail?.name;\n if (name !== context.panelName) return;\n this.onTabShown();\n };\n context.tabsHost.addEventListener('wa-tab-show', this.onTabShow);\n }\n\n private detachTabVisibilityHandling(): void {\n if (this.tabsHost && this.onTabShow) {\n this.tabsHost.removeEventListener('wa-tab-show', this.onTabShow);\n }\n this.tabsHost = null;\n this.tabPanelName = null;\n this.onTabShow = null;\n }\n\n private scheduleFit(focus = false): void {\n requestAnimationFrame(() => {\n requestAnimationFrame(() => {\n this.applyFit();\n if (focus) this.xterm?.focus();\n });\n });\n }\n\n private async openBackendIfNeeded(): Promise<void> {\n if (this.backendOpened || !this.terminal?.backend) return;\n this.backendOpened = true;\n await this.terminal.backend.open?.(this.getDimensions());\n }\n\n private onTabShown(): void {\n this.scheduleFit(true);\n void this.openBackendIfNeeded();\n }\n\n private async initTerminal(): Promise<void> {\n if (!this.terminal?.backend) return;\n await this.updateComplete;\n\n const container = this.xtermRef.value;\n if (!container) return;\n\n this.xterm = new Terminal({\n cursorBlink: true,\n fontFamily: 'var(--wa-font-mono, monospace)',\n fontSize: 13,\n theme: getTerminalTheme(),\n });\n this.fitAddon = new FitAddon();\n this.xterm.loadAddon(this.fitAddon);\n this.xterm.open(container);\n\n const backend = this.terminal.backend;\n this.unsubscribeWrite = backend.onDidWrite((data) => {\n this.xterm?.write(data);\n });\n\n this.xterm.onData((data) => {\n backend.handleInput(data);\n });\n\n this.terminal.clearScreen = () => {\n this.xterm?.clear();\n };\n\n this.unobserveTheme = observeTerminalTheme(() => {\n if (!this.xterm) return;\n this.xterm.options.theme = getTerminalTheme();\n });\n\n this.resizeObserver = new ResizeObserver(() => {\n if (!this.isVisible()) return;\n this.scheduleFit();\n });\n this.resizeObserver.observe(container);\n this.resizeObserver.observe(this);\n this.observeAncestorResizableGrids(container);\n\n const tabContext = this.findTabContext();\n if (tabContext) {\n this.attachTabVisibilityHandling(tabContext);\n }\n\n if (!tabContext || this.isTabPanelActive(tabContext.tabPanel)) {\n this.scheduleFit(true);\n void this.openBackendIfNeeded();\n }\n }\n\n private observeAncestorResizableGrids(from: Element): void {\n if (!this.resizeObserver) return;\n let el: Element | null = from;\n while (el) {\n if (el.tagName?.toLowerCase() === 'docks-resizable-grid') {\n this.resizeObserver.observe(el);\n }\n const parent: Element | null = el.parentElement;\n if (parent) {\n el = parent;\n } else {\n const root = el.getRootNode();\n el = root instanceof ShadowRoot ? (root.host as Element) : null;\n }\n }\n }\n\n private isVisible(): boolean {\n if (!this.tabPanelName) return true;\n return this.offsetParent !== null;\n }\n\n private applyFit(): void {\n if (!this.fitAddon || !this.xterm || !this.isVisible()) return;\n try {\n this.fitAddon.fit();\n } catch {\n return;\n }\n const dims = this.getDimensions();\n this.terminal?.backend?.setDimensions?.(dims);\n }\n\n private getDimensions(): { cols: number; rows: number } {\n return {\n cols: this.xterm?.cols ?? 80,\n rows: this.xterm?.rows ?? 24,\n };\n }\n\n private teardownTerminal(): void {\n this.detachTabVisibilityHandling();\n this.unobserveTheme?.();\n this.unobserveTheme = null;\n this.backendOpened = false;\n this.resizeObserver?.disconnect();\n this.resizeObserver = null;\n this.unsubscribeWrite?.();\n this.unsubscribeWrite = null;\n this.xterm?.dispose();\n this.xterm = null;\n this.fitAddon = null;\n }\n\n protected renderContent() {\n return html`<div class=\"terminal-host\" ${ref(this.xtermRef)}></div>`;\n }\n\n static styles = [\n unsafeCSS(xtermStyles),\n css`\n :host {\n display: flex;\n flex-direction: column;\n height: 100%;\n width: 100%;\n min-height: 0;\n }\n\n .part-shell {\n display: flex;\n flex-direction: column;\n flex: 1;\n min-height: 0;\n height: 100%;\n }\n\n .part-content {\n flex: 1;\n min-height: 0;\n display: flex;\n flex-direction: column;\n }\n\n .part-content-inner {\n flex: 1;\n min-height: 0;\n height: 100%;\n display: flex;\n flex-direction: column;\n }\n\n .terminal-host {\n flex: 1;\n min-height: 0;\n height: 100%;\n width: 100%;\n overflow: hidden;\n background: var(--wa-color-surface-lowered);\n padding-left: var(--wa-space-s);\n box-sizing: border-box;\n }\n\n .terminal-host .xterm {\n height: 100%;\n }\n `,\n ];\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'docks-terminal-view': DocksTerminalView;\n }\n}\n","import { css, customElement, html } from '@eclipse-docks/core/externals/lit';\nimport {\n DocksPart,\n appSettings,\n promptDialog,\n subscribe,\n unsubscribe,\n} from '@eclipse-docks/core';\nimport {\n TERMINAL_INSTANCES_TABS_ID,\n TERMINAL_NEW_DROPDOWN,\n TERMINAL_PANEL_SETTINGS_KEY,\n TOPIC_TERMINAL_ACTIVE_CHANGED,\n TOPIC_TERMINAL_CLOSED,\n TOPIC_TERMINAL_OPENED,\n type PersistedTerminalState,\n} from './terminal-api';\nimport { emptyTerminalState, parseTerminalState } from './terminal-persistence';\nimport { terminalService, type TerminalTabsHost } from './terminal-service';\nimport './terminal-view';\n\n@customElement('docks-terminal-panel')\nexport class DocksTerminalPanel extends DocksPart {\n protected scrollMode: 'scroller' | 'native' | 'none' = 'none';\n\n private unsubscribeTerminalEvents: (() => void)[] = [];\n\n connectedCallback(): void {\n super.connectedCallback();\n terminalService.setPersistenceHandlers(\n () => this.loadPersistedState(),\n (state) => this.savePersistedState(state)\n );\n for (const topic of [TOPIC_TERMINAL_ACTIVE_CHANGED, TOPIC_TERMINAL_OPENED, TOPIC_TERMINAL_CLOSED]) {\n const token = subscribe(topic, () => this.requestUpdate());\n this.unsubscribeTerminalEvents.push(() => unsubscribe(token));\n }\n this.updateComplete.then(() => {\n this.bindInstanceTabsHost();\n this.attachTabActivationListener();\n void terminalService.restorePersistedTerminals();\n });\n }\n\n private bindInstanceTabsHost(): void {\n const tabs = this.renderRoot.querySelector(\n `docks-tabs#${TERMINAL_INSTANCES_TABS_ID}`\n ) as TerminalTabsHost | null;\n terminalService.setInstanceTabsHost(tabs);\n }\n\n private attachTabActivationListener(): void {\n const tabs = this.renderRoot.querySelector('docks-tabs');\n if (!tabs) return;\n tabs.addEventListener('wa-tab-show', (event: Event) => {\n const name = (event as CustomEvent<{ name?: string }>).detail?.name;\n if (name) terminalService.handleTabActivated(name);\n });\n }\n\n disconnectedCallback(): void {\n for (const off of this.unsubscribeTerminalEvents) off();\n this.unsubscribeTerminalEvents = [];\n terminalService.setInstanceTabsHost(null);\n super.disconnectedCallback();\n }\n\n private async loadPersistedState(): Promise<PersistedTerminalState | null> {\n const raw = await appSettings.getDialogSetting(TERMINAL_PANEL_SETTINGS_KEY);\n return parseTerminalState(raw) ?? emptyTerminalState();\n }\n\n private async savePersistedState(state: PersistedTerminalState): Promise<void> {\n await appSettings.setDialogSetting(TERMINAL_PANEL_SETTINGS_KEY, state);\n }\n\n protected renderToolbar() {\n const hasActive = !!terminalService.activeTerminal;\n return html`\n <docks-command\n icon=\"plus\"\n title=\"New Terminal\"\n dropdown=\"${TERMINAL_NEW_DROPDOWN}\"\n .action=${() => void terminalService.createTerminal()}\n >\n </docks-command>\n <docks-command\n icon=\"xmark\"\n title=\"Kill Terminal\"\n ?disabled=${!hasActive}\n .action=${async () => {\n await terminalService.activeTerminal?.dispose();\n }}\n ></docks-command>\n <docks-command\n icon=\"eraser\"\n title=\"Clear\"\n ?disabled=${!hasActive}\n .action=${() => {\n terminalService.activeTerminal?.clear?.();\n }}\n ></docks-command>\n <docks-command\n icon=\"pen\"\n title=\"Rename\"\n ?disabled=${!hasActive}\n .action=${async () => {\n const active = terminalService.activeTerminal;\n if (!active) return;\n const name = await promptDialog('Terminal name', active.name);\n if (name?.trim()) terminalService.renameActiveTerminal(name.trim());\n }}\n ></docks-command>\n `;\n }\n\n protected renderContent() {\n return html`\n <docks-tabs\n id=\"${TERMINAL_INSTANCES_TABS_ID}\"\n placement=\"start\"\n item-size=\"s\"\n ></docks-tabs>\n `;\n }\n\n static styles = css`\n :host {\n display: flex;\n flex-direction: column;\n height: 100%;\n width: 100%;\n min-height: 0;\n }\n\n docks-tabs {\n flex: 1;\n min-height: 0;\n }\n `;\n}\n\ndeclare global {\n interface HTMLElementTagNameMap {\n 'docks-terminal-panel': DocksTerminalPanel;\n }\n}\n","import { html } from '@eclipse-docks/core/externals/lit';\nimport { contributionRegistry, PANEL_BOTTOM, registerAll } from '@eclipse-docks/core';\nimport { VIEW_TERMINAL } from './terminal-api';\nimport { CommandsBackend } from './commands-backend';\nimport { createJsSessionBackend, JsReplBackend, JS_REPL_PROFILE_ID, JS_SESSION_PROFILE_ID } from './js-terminal-backend';\nimport { registerTerminalProfile, terminalService } from './terminal-service';\nimport './terminal-panel';\n\nconst COMMANDS_PROFILE_ID = 'terminal.javascript-shell';\n\nexport default async function activate() {\n registerTerminalProfile({\n id: COMMANDS_PROFILE_ID,\n label: 'Commands',\n icon: 'terminal',\n isDefault: true,\n create: async () => new CommandsBackend(),\n });\n\n registerTerminalProfile({\n id: JS_REPL_PROFILE_ID,\n label: 'JavaScript',\n icon: 'code',\n create: async () => new JsReplBackend(),\n });\n\n registerTerminalProfile({\n id: JS_SESSION_PROFILE_ID,\n label: 'JavaScript',\n icon: 'code',\n hidden: true,\n persist: false,\n create: async (options) => createJsSessionBackend(options),\n });\n\n contributionRegistry.registerContribution(PANEL_BOTTOM, {\n name: VIEW_TERMINAL,\n label: 'Terminal',\n icon: 'terminal',\n component: (id: string) => html`<docks-terminal-panel id=\"${id}\"></docks-terminal-panel>`,\n });\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"terminal-extension.d.ts","sourceRoot":"","sources":["../src/terminal-extension.ts"],"names":[],"mappings":"AAMA,OAAO,kBAAkB,CAAC;AAI1B,wBAA8B,QAAQ,
|
|
1
|
+
{"version":3,"file":"terminal-extension.d.ts","sourceRoot":"","sources":["../src/terminal-extension.ts"],"names":[],"mappings":"AAMA,OAAO,kBAAkB,CAAC;AAI1B,wBAA8B,QAAQ,kBA+BrC"}
|
|
@@ -33,6 +33,8 @@ declare class TerminalService implements TerminalTaskRunner {
|
|
|
33
33
|
activateTerminal(id: string): void;
|
|
34
34
|
private setActiveTerminal;
|
|
35
35
|
createTerminal(options?: TerminalCreationOptions, forcedId?: string): Promise<Terminal | undefined>;
|
|
36
|
+
/** The panel binds its tab host after the bottom panel is shown. */
|
|
37
|
+
private whenTabsHostReady;
|
|
36
38
|
private openTerminalTab;
|
|
37
39
|
disposeTerminal(id: string, options?: {
|
|
38
40
|
skipTabRemoval?: boolean;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"terminal-service.d.ts","sourceRoot":"","sources":["../src/terminal-service.ts"],"names":[],"mappings":"AACA,OAAO,EAUL,KAAK,eAAe,EACrB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAOL,KAAK,QAAQ,EAEb,KAAK,uBAAuB,EAC5B,KAAK,2BAA2B,EAChC,KAAK,wBAAwB,EAC7B,KAAK,kBAAkB,EACvB,KAAK,sBAAsB,EAE5B,MAAM,gBAAgB,CAAC;AASxB,UAAU,gBAAgB;IACxB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;IAC1B,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,IAAI,CAAC,YAAY,EAAE,eAAe,GAAG,IAAI,CAAC;IAC1C,QAAQ,CAAC,KAAK,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACvD,cAAc,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;CACtD;AAED,YAAY,EAAE,gBAAgB,EAAE,CAAC;
|
|
1
|
+
{"version":3,"file":"terminal-service.d.ts","sourceRoot":"","sources":["../src/terminal-service.ts"],"names":[],"mappings":"AACA,OAAO,EAUL,KAAK,eAAe,EACrB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAOL,KAAK,QAAQ,EAEb,KAAK,uBAAuB,EAC5B,KAAK,2BAA2B,EAChC,KAAK,wBAAwB,EAC7B,KAAK,kBAAkB,EACvB,KAAK,sBAAsB,EAE5B,MAAM,gBAAgB,CAAC;AASxB,UAAU,gBAAgB;IACxB,GAAG,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;IAC1B,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,IAAI,CAAC,YAAY,EAAE,eAAe,GAAG,IAAI,CAAC;IAC1C,QAAQ,CAAC,KAAK,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACvD,cAAc,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;CACtD;AAED,YAAY,EAAE,gBAAgB,EAAE,CAAC;AA+DjC,cAAM,eAAgB,YAAW,kBAAkB;IACjD,OAAO,CAAC,SAAS,CAAuC;IACxD,OAAO,CAAC,gBAAgB,CAAuB;IAC/C,OAAO,CAAC,kBAAkB,CAAuB;IACjD,OAAO,CAAC,kBAAkB,CAA+D;IACzF,OAAO,CAAC,eAAe,CAAmE;IAC1F,OAAO,CAAC,cAAc,CAAS;IAC/B,OAAO,CAAC,gBAAgB,CAAiC;IAEzD,IAAI,cAAc,IAAI,QAAQ,GAAG,SAAS,CAGzC;IAED,YAAY,IAAI,QAAQ,EAAE;IAI1B,iBAAiB,CAAC,QAAQ,EAAE,CAAC,QAAQ,EAAE,QAAQ,KAAK,IAAI,GAAG,MAAM,IAAI;IAKrE,kBAAkB,CAAC,QAAQ,EAAE,CAAC,QAAQ,EAAE,QAAQ,KAAK,IAAI,GAAG,MAAM,IAAI;IAKtE,yBAAyB,CAAC,QAAQ,EAAE,CAAC,QAAQ,EAAE,QAAQ,GAAG,SAAS,KAAK,IAAI,GAAG,MAAM,IAAI;IAKzF,sBAAsB,CACpB,IAAI,EAAE,MAAM,OAAO,CAAC,sBAAsB,GAAG,IAAI,CAAC,EAClD,IAAI,EAAE,CAAC,KAAK,EAAE,sBAAsB,KAAK,OAAO,CAAC,IAAI,CAAC,GACrD,IAAI;IAKD,yBAAyB,IAAI,OAAO,CAAC,IAAI,CAAC;IAsBhD,qEAAqE;IACrE,OAAO,CAAC,mBAAmB;IAK3B,WAAW,IAAI,2BAA2B,EAAE;IAI5C,uBAAuB,IAAI,MAAM,GAAG,IAAI;IAUxC,mBAAmB,CAAC,IAAI,EAAE,gBAAgB,GAAG,IAAI,GAAG,IAAI;IAIxD,eAAe,IAAI,gBAAgB,GAAG,IAAI;IAI1C,kBAAkB,IAAI,IAAI;IAK1B,gBAAgB,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI;IAQlC,OAAO,CAAC,iBAAiB;IAOnB,cAAc,CAClB,OAAO,GAAE,uBAA4B,EACrC,QAAQ,CAAC,EAAE,MAAM,GAChB,OAAO,CAAC,QAAQ,GAAG,SAAS,CAAC;IAwChC,oEAAoE;IACpE,OAAO,CAAC,iBAAiB;IAezB,OAAO,CAAC,eAAe;IAsBjB,eAAe,CAAC,EAAE,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE;QAAE,cAAc,CAAC,EAAE,OAAO,CAAA;KAAE,GAAG,OAAO,CAAC,IAAI,CAAC;IAyBlF,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAY9B,oBAAoB,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI;IAQxC,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI;IAK5C,mBAAmB,IAAI,IAAI;IAIrB,OAAO,CACX,YAAY,EAAE,wBAAwB,EACtC,OAAO,EAAE,CAAC,QAAQ,EAAE,QAAQ,KAAK,OAAO,CAAC,IAAI,CAAC,GAC7C,OAAO,CAAC,IAAI,CAAC;YAoBF,YAAY;IAqB1B,kBAAkB,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI;IAMzC,eAAe,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI;CAKvC;AASD,eAAO,MAAM,eAAe,iBAAwB,CAAC;AAGrD,wBAAgB,uBAAuB,CAAC,YAAY,EAAE,2BAA2B,GAAG,IAAI,CAiBvF"}
|
package/package.json
CHANGED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"js-terminal-backend-DV-i_yft.js","names":[],"sources":["../src/terminal-api.ts","../src/terminal-persistence.ts","../src/terminal-service.ts","../src/shell-parser.ts","../src/line-input.ts","../src/commands-backend.ts","../src/js-terminal-backend.ts"],"sourcesContent":["export const TARGET_TERMINAL_PROFILES = 'system.terminal.profiles';\n\nexport const VIEW_TERMINAL = 'view.terminal';\nexport const TERMINAL_INSTANCES_TABS_ID = 'terminal-instances';\n/** Dropdown target: contributors register items that create a terminal with a profile. */\nexport const TERMINAL_NEW_DROPDOWN = `${TERMINAL_INSTANCES_TABS_ID}-new`;\nexport const TERMINAL_PANEL_SETTINGS_KEY = 'docks-terminal-panel';\n\nexport const TOPIC_TERMINAL_OPENED = 'events/terminal/opened';\nexport const TOPIC_TERMINAL_CLOSED = 'events/terminal/closed';\nexport const TOPIC_TERMINAL_ACTIVE_CHANGED = 'events/terminal/activeChanged';\n\nexport interface TerminalDimensions {\n cols: number;\n rows: number;\n}\n\nexport interface TerminalCreationOptions {\n name?: string;\n profileId?: string;\n cwd?: string;\n env?: Record<string, string>;\n groupId?: string;\n hidden?: boolean;\n}\n\nexport interface TerminalBackend {\n open?(initialDimensions?: TerminalDimensions): void | Promise<void>;\n close?(): void | Promise<void>;\n onDidWrite(callback: (data: string) => void): () => void;\n handleInput(data: string): void;\n setDimensions?(dimensions: TerminalDimensions): void;\n}\n\nexport interface TerminalProfileContribution {\n id: string;\n label: string;\n icon?: string;\n isDefault?: boolean;\n hidden?: boolean;\n /**\n * When false, terminals of this profile are not saved or restored across reloads.\n * Defaults to true.\n */\n persist?: boolean;\n create(options?: TerminalCreationOptions): Promise<TerminalBackend>;\n}\n\nexport interface TerminalTaskPresentation {\n profileId: string;\n reveal?: 'always' | 'silent' | 'never';\n focus?: boolean;\n clear?: boolean;\n}\n\nexport interface Terminal {\n readonly id: string;\n name: string;\n readonly profileId: string;\n readonly creationOptions: TerminalCreationOptions;\n readonly groupId: string;\n hidden: boolean;\n sendText(text: string, addNewLine?: boolean): void;\n show(preserveFocus?: boolean): void;\n hide(): void;\n dispose(): Promise<void>;\n clear?(): void;\n}\n\n/** Internal terminal handle used by the host UI (not for provider extensions). */\nexport interface TerminalRuntime extends Terminal {\n backend: TerminalBackend | null;\n clearScreen?: () => void;\n}\n\nexport interface TerminalTaskRunner {\n runTask(\n presentation: TerminalTaskPresentation,\n execute: (terminal: Terminal) => Promise<void>\n ): Promise<void>;\n}\n\nexport interface PersistedTerminalState {\n terminals: PersistedTerminalEntry[];\n activeTerminalId: string | null;\n preferredProfileId: string | null;\n}\n\nexport interface PersistedTerminalEntry {\n id: string;\n name: string;\n profileId: string;\n groupId: string;\n creationOptions: TerminalCreationOptions;\n}\n","import type { PersistedTerminalEntry, PersistedTerminalState, TerminalCreationOptions } from './terminal-api';\n\nconst MAX_PERSISTED_ENV_KEYS = 32;\n\nexport function serializeTerminalState(state: PersistedTerminalState): PersistedTerminalState {\n return {\n activeTerminalId: state.activeTerminalId,\n preferredProfileId: state.preferredProfileId,\n terminals: state.terminals.map(serializeTerminalEntry),\n };\n}\n\nfunction serializeTerminalEntry(entry: PersistedTerminalEntry): PersistedTerminalEntry {\n const opts = entry.creationOptions;\n const env = opts.env\n ? Object.fromEntries(Object.entries(opts.env).slice(0, MAX_PERSISTED_ENV_KEYS))\n : undefined;\n return {\n id: entry.id,\n name: entry.name,\n profileId: entry.profileId,\n groupId: entry.groupId,\n creationOptions: {\n name: opts.name,\n profileId: opts.profileId,\n cwd: opts.cwd,\n env,\n groupId: opts.groupId,\n },\n };\n}\n\nexport function parseTerminalState(raw: unknown): PersistedTerminalState | null {\n if (!raw || typeof raw !== 'object') return null;\n const obj = raw as Record<string, unknown>;\n if (!Array.isArray(obj.terminals)) return null;\n\n const terminals: PersistedTerminalEntry[] = [];\n for (const item of obj.terminals) {\n if (!item || typeof item !== 'object') continue;\n const t = item as Record<string, unknown>;\n if (typeof t.id !== 'string' || typeof t.name !== 'string' || typeof t.profileId !== 'string') {\n continue;\n }\n const creationOptions = (t.creationOptions ?? {}) as TerminalCreationOptions;\n terminals.push({\n id: t.id,\n name: t.name,\n profileId: t.profileId,\n groupId: typeof t.groupId === 'string' ? t.groupId : t.id,\n creationOptions,\n });\n }\n\n return {\n terminals,\n activeTerminalId: typeof obj.activeTerminalId === 'string' ? obj.activeTerminalId : null,\n preferredProfileId: typeof obj.preferredProfileId === 'string' ? obj.preferredProfileId : null,\n };\n}\n\nexport function emptyTerminalState(): PersistedTerminalState {\n return { terminals: [], activeTerminalId: null, preferredProfileId: null };\n}\n","import { html } from '@eclipse-docks/core/externals/lit';\nimport {\n confirmDialog,\n contributionRegistry,\n i18n,\n PANEL_BOTTOM,\n publish,\n renderDropdownItem,\n rootContext,\n subscribe,\n unsubscribe,\n type TabContribution,\n} from '@eclipse-docks/core';\nimport {\n TARGET_TERMINAL_PROFILES,\n TERMINAL_NEW_DROPDOWN,\n TOPIC_TERMINAL_ACTIVE_CHANGED,\n TOPIC_TERMINAL_CLOSED,\n TOPIC_TERMINAL_OPENED,\n VIEW_TERMINAL,\n type Terminal,\n type TerminalBackend,\n type TerminalCreationOptions,\n type TerminalProfileContribution,\n type TerminalTaskPresentation,\n type TerminalTaskRunner,\n type PersistedTerminalState,\n type TerminalRuntime,\n} from './terminal-api';\nimport { emptyTerminalState, parseTerminalState, serializeTerminalState } from './terminal-persistence';\n\nconst t = await i18n(import.meta.glob('./i18n*.json'), true);\n\nasync function confirmKillTerminal(name: string): Promise<boolean> {\n return confirmDialog(t.TERMINAL_KILL_CONFIRM({ name }));\n}\n\ninterface TerminalTabsHost {\n has(key: string): boolean;\n activate(key: string): void;\n open(contribution: TabContribution): void;\n closeTab(event: Event, tabName: string): Promise<void>;\n updateTabLabel(tabName: string, label: string): void;\n}\n\nexport type { TerminalTabsHost };\n\nlet terminalCounter = 0;\n\nfunction nextTerminalId(): string {\n terminalCounter += 1;\n return `terminal-${terminalCounter}`;\n}\n\nclass TerminalInstance implements TerminalRuntime {\n readonly id: string;\n name: string;\n readonly profileId: string;\n readonly creationOptions: TerminalCreationOptions;\n readonly groupId: string;\n hidden = false;\n backend: TerminalBackend | null = null;\n clearScreen?: () => void;\n\n constructor(\n id: string,\n name: string,\n profileId: string,\n creationOptions: TerminalCreationOptions,\n groupId: string\n ) {\n this.id = id;\n this.name = name;\n this.profileId = profileId;\n this.creationOptions = creationOptions;\n this.groupId = groupId;\n }\n\n sendText(text: string, addNewLine = true): void {\n if (!this.backend) return;\n this.backend.handleInput(text + (addNewLine ? '\\r' : ''));\n }\n\n show(_preserveFocus?: boolean): void {\n terminalService.focusTerminalPanel();\n terminalService.activateTerminal(this.id);\n this.hidden = false;\n }\n\n hide(): void {\n this.hidden = true;\n }\n\n async dispose(): Promise<void> {\n await terminalService.disposeTerminal(this.id);\n }\n\n clear(): void {\n this.clearScreen?.();\n }\n}\n\nclass TerminalService implements TerminalTaskRunner {\n private terminals = new Map<string, TerminalInstance>();\n private activeTerminalId: string | null = null;\n private preferredProfileId: string | null = null;\n private persistenceHandler: (() => Promise<PersistedTerminalState | null>) | null = null;\n private persistCallback: ((state: PersistedTerminalState) => Promise<void>) | null = null;\n private restoreStarted = false;\n private instanceTabsHost: TerminalTabsHost | null = null;\n\n get activeTerminal(): Terminal | undefined {\n if (!this.activeTerminalId) return undefined;\n return this.terminals.get(this.activeTerminalId);\n }\n\n getTerminals(): Terminal[] {\n return [...this.terminals.values()];\n }\n\n onDidOpenTerminal(callback: (terminal: Terminal) => void): () => void {\n const token = subscribe(TOPIC_TERMINAL_OPENED, callback);\n return () => unsubscribe(token);\n }\n\n onDidCloseTerminal(callback: (terminal: Terminal) => void): () => void {\n const token = subscribe(TOPIC_TERMINAL_CLOSED, callback);\n return () => unsubscribe(token);\n }\n\n onDidChangeActiveTerminal(callback: (terminal: Terminal | undefined) => void): () => void {\n const token = subscribe(TOPIC_TERMINAL_ACTIVE_CHANGED, callback);\n return () => unsubscribe(token);\n }\n\n setPersistenceHandlers(\n load: () => Promise<PersistedTerminalState | null>,\n save: (state: PersistedTerminalState) => Promise<void>\n ): void {\n this.persistenceHandler = load;\n this.persistCallback = save;\n }\n\n async restorePersistedTerminals(): Promise<void> {\n if (this.restoreStarted || !this.persistenceHandler) return;\n this.restoreStarted = true;\n const raw = await this.persistenceHandler();\n const state = raw ? parseTerminalState(raw) : null;\n if (!state || state.terminals.length === 0) return;\n\n this.preferredProfileId = state.preferredProfileId;\n for (const entry of state.terminals) {\n if (!this.isProfilePersistent(entry.profileId)) continue;\n await this.createTerminal({\n ...entry.creationOptions,\n name: entry.name,\n profileId: entry.profileId,\n groupId: entry.groupId,\n }, entry.id);\n }\n if (state.activeTerminalId && this.terminals.has(state.activeTerminalId)) {\n this.setActiveTerminal(state.activeTerminalId);\n }\n }\n\n /** Profiles default to persistent; opt out with `persist: false`. */\n private isProfilePersistent(profileId: string): boolean {\n const profile = this.getProfiles().find((p) => p.id === profileId);\n return profile?.persist !== false;\n }\n\n getProfiles(): TerminalProfileContribution[] {\n return contributionRegistry.getContributions<TerminalProfileContribution>(TARGET_TERMINAL_PROFILES);\n }\n\n resolveDefaultProfileId(): string | null {\n if (this.preferredProfileId) {\n const preferred = this.getProfiles().find((p) => p.id === this.preferredProfileId);\n if (preferred) return preferred.id;\n }\n const profiles = this.getProfiles().filter((p) => !p.hidden);\n const defaultProfile = profiles.find((p) => p.isDefault) ?? profiles[0];\n return defaultProfile?.id ?? null;\n }\n\n setInstanceTabsHost(host: TerminalTabsHost | null): void {\n this.instanceTabsHost = host;\n }\n\n getInstanceTabs(): TerminalTabsHost | null {\n return this.instanceTabsHost;\n }\n\n focusTerminalPanel(): void {\n const panel = document.querySelector(`docks-tabs#${PANEL_BOTTOM}`) as TerminalTabsHost | null;\n panel?.activate(VIEW_TERMINAL);\n }\n\n activateTerminal(id: string): void {\n const tabs = this.getInstanceTabs();\n if (tabs?.has(id)) {\n tabs.activate(id);\n }\n this.setActiveTerminal(id);\n }\n\n private setActiveTerminal(id: string | null): void {\n if (this.activeTerminalId === id) return;\n this.activeTerminalId = id;\n publish(TOPIC_TERMINAL_ACTIVE_CHANGED, id ? this.terminals.get(id) : undefined);\n void this.persistState();\n }\n\n async createTerminal(\n options: TerminalCreationOptions = {},\n forcedId?: string\n ): Promise<Terminal | undefined> {\n const profileId = options.profileId ?? this.resolveDefaultProfileId();\n if (!profileId) return undefined;\n\n const profile = this.getProfiles().find((p) => p.id === profileId);\n if (!profile) return undefined;\n\n const id = forcedId ?? nextTerminalId();\n if (forcedId) syncTerminalCounterFromId(forcedId);\n const groupId = options.groupId ?? id;\n const name = options.name ?? profile.label;\n\n let backend: TerminalBackend;\n try {\n backend = await profile.create({ ...options, profileId, name, groupId });\n } catch {\n return undefined;\n }\n\n const terminal = new TerminalInstance(id, name, profileId, { ...options, profileId, name, groupId }, groupId);\n terminal.backend = backend;\n terminal.hidden = options.hidden ?? false;\n\n this.terminals.set(id, terminal);\n this.openTerminalTab(terminal, profile.icon);\n\n if (!options.hidden) {\n this.focusTerminalPanel();\n this.activateTerminal(id);\n }\n\n publish(TOPIC_TERMINAL_OPENED, terminal);\n void this.persistState();\n return terminal;\n }\n\n private openTerminalTab(terminal: TerminalInstance, icon?: string): void {\n const tabs = this.getInstanceTabs();\n if (!tabs) return;\n\n const contribution: TabContribution = {\n name: terminal.id,\n label: terminal.name,\n icon: icon ?? 'terminal',\n closable: true,\n toolbar: false,\n beforeClose: async () => confirmKillTerminal(terminal.name),\n component: (tabId: string) =>\n html`<docks-terminal-view id=\"${tabId}\" .terminal=${terminal}></docks-terminal-view>`,\n };\n\n if (tabs.has(terminal.id)) {\n tabs.activate(terminal.id);\n return;\n }\n tabs.open(contribution);\n }\n\n async disposeTerminal(id: string, options?: { skipTabRemoval?: boolean }): Promise<void> {\n const terminal = this.terminals.get(id);\n if (!terminal) return;\n\n if (!options?.skipTabRemoval) {\n const tabs = this.getInstanceTabs();\n if (tabs?.has(id)) {\n await tabs.closeTab(new Event('close'), id);\n return;\n }\n }\n\n await terminal.backend?.close?.();\n terminal.backend = null;\n this.terminals.delete(id);\n\n if (this.activeTerminalId === id) {\n const remaining = [...this.terminals.keys()];\n this.setActiveTerminal(remaining.length > 0 ? remaining[remaining.length - 1] : null);\n }\n\n publish(TOPIC_TERMINAL_CLOSED, terminal);\n void this.persistState();\n }\n\n async killAll(): Promise<void> {\n const tabs = this.getInstanceTabs();\n const ids = [...this.terminals.keys()];\n for (const id of ids) {\n if (tabs?.has(id)) {\n await tabs.closeTab(new Event('close'), id);\n } else {\n await this.disposeTerminal(id, { skipTabRemoval: true });\n }\n }\n }\n\n renameActiveTerminal(name: string): void {\n const active = this.activeTerminal;\n if (!active || !(active instanceof TerminalInstance)) return;\n active.name = name;\n this.getInstanceTabs()?.updateTabLabel(active.id, name);\n void this.persistState();\n }\n\n setPreferredProfile(profileId: string): void {\n this.preferredProfileId = profileId;\n void this.persistState();\n }\n\n clearActiveTerminal(): void {\n this.activeTerminal?.clear?.();\n }\n\n async runTask(\n presentation: TerminalTaskPresentation,\n execute: (terminal: Terminal) => Promise<void>\n ): Promise<void> {\n let terminal = this.getTerminals().find((t) => t.profileId === presentation.profileId);\n if (!terminal) {\n terminal = await this.createTerminal({ profileId: presentation.profileId });\n }\n if (!terminal) return;\n\n if (presentation.reveal !== 'never') {\n if (presentation.focus !== false) {\n terminal.show();\n } else {\n this.focusTerminalPanel();\n }\n }\n if (presentation.clear) {\n terminal.clear?.();\n }\n await execute(terminal);\n }\n\n private async persistState(): Promise<void> {\n if (!this.persistCallback) return;\n const terminals = [...this.terminals.values()]\n .filter((t) => this.isProfilePersistent(t.profileId))\n .map((t) => ({\n id: t.id,\n name: t.name,\n profileId: t.profileId,\n groupId: t.groupId,\n creationOptions: t.creationOptions,\n }));\n const ids = new Set(terminals.map((t) => t.id));\n const state: PersistedTerminalState = {\n activeTerminalId:\n this.activeTerminalId && ids.has(this.activeTerminalId) ? this.activeTerminalId : null,\n preferredProfileId: this.preferredProfileId,\n terminals,\n };\n await this.persistCallback(serializeTerminalState(state));\n }\n\n handleTabActivated(tabName: string): void {\n if (this.terminals.has(tabName)) {\n this.setActiveTerminal(tabName);\n }\n }\n\n handleTabClosed(tabName: string): void {\n if (this.terminals.has(tabName)) {\n void this.disposeTerminal(tabName, { skipTabRemoval: true });\n }\n }\n}\n\nfunction syncTerminalCounterFromId(id: string): void {\n const match = /^terminal-(\\d+)$/.exec(id);\n if (!match) return;\n const n = Number.parseInt(match[1], 10);\n if (n > terminalCounter) terminalCounter = n;\n}\n\nexport const terminalService = new TerminalService();\nrootContext.put('terminalService', terminalService);\n\nexport function registerTerminalProfile(contribution: TerminalProfileContribution): void {\n contributionRegistry.registerContribution(TARGET_TERMINAL_PROFILES, contribution);\n if (contribution.hidden) return;\n const profileId = contribution.id;\n contributionRegistry.registerContribution(TERMINAL_NEW_DROPDOWN, {\n label: contribution.label,\n icon: contribution.icon ?? 'terminal',\n component: () => renderDropdownItem({\n icon: contribution.icon ?? 'terminal',\n label: contribution.label,\n title: contribution.label,\n action: () => {\n terminalService.setPreferredProfile(profileId);\n void terminalService.createTerminal({ profileId });\n },\n }),\n });\n}\n","import type { CommandRegistry, Command } from '@eclipse-docks/core';\n\nexport interface ParsedCommand {\n commandId: string;\n params: Record<string, string | boolean>;\n}\n\nexport interface ParsedSegment {\n command: ParsedCommand;\n operator: '&&' | '|' | null;\n}\n\nconst NAMED_PARAM_REGEX = /^[a-zA-Z_][a-zA-Z0-9_]*=.*$/;\n\nfunction tokenize(segment: string): string[] {\n const tokens: string[] = [];\n let i = 0;\n const len = segment.length;\n\n while (i < len) {\n while (i < len && /\\s/.test(segment[i])) i++;\n if (i >= len) break;\n\n if (segment[i] === '\"') {\n let end = i + 1;\n while (end < len && segment[end] !== '\"') {\n if (segment[end] === '\\\\') end++;\n end++;\n }\n tokens.push(segment.slice(i + 1, end).replace(/\\\\\"/g, '\"'));\n i = end + 1;\n } else {\n let start = i;\n while (i < len && !/\\s/.test(segment[i]) && segment[i] !== '\"') i++;\n if (i > start) {\n tokens.push(segment.slice(start, i));\n }\n }\n }\n return tokens;\n}\n\nfunction splitChain(line: string): { segment: string; operator: '&&' | '|' | null }[] {\n const result: { segment: string; operator: '&&' | '|' | null }[] = [];\n const regex = /(\\s*&&\\s*|\\s*\\|\\s*)/g;\n let lastIndex = 0;\n let match: RegExpExecArray | null;\n\n while ((match = regex.exec(line)) !== null) {\n const segment = line.slice(lastIndex, match.index).trim();\n if (segment) {\n const op = match[0].includes('|') ? ('|' as const) : ('&&' as const);\n result.push({ segment, operator: op });\n }\n lastIndex = regex.lastIndex;\n }\n const tail = line.slice(lastIndex).trim();\n if (tail) {\n result.push({ segment: tail, operator: null });\n }\n return result;\n}\n\nfunction resolveParams(\n tokens: string[],\n command: Command | undefined\n): Record<string, string | boolean> {\n const params: Record<string, string | boolean> = {};\n const positionals: string[] = [];\n const paramNames = command?.parameters?.map((p) => p.name) ?? [];\n\n for (const token of tokens) {\n if (NAMED_PARAM_REGEX.test(token)) {\n const eqIdx = token.indexOf('=');\n const name = token.slice(0, eqIdx);\n const value = token.slice(eqIdx + 1);\n params[name] = value === 'true' || value === 'false' ? value === 'true' : value;\n } else {\n positionals.push(token);\n }\n }\n\n paramNames.forEach((name, i) => {\n if (positionals[i] !== undefined && !(name in params)) {\n params[name] = positionals[i];\n }\n });\n\n return params;\n}\n\nexport function parseShellLine(line: string, commandRegistry: CommandRegistry): ParsedSegment[] {\n const segments = splitChain(line);\n return segments.map(({ segment, operator }) => {\n const tokens = tokenize(segment);\n if (tokens.length === 0) {\n return { command: { commandId: '', params: {} }, operator };\n }\n const commandId = tokens[0];\n const command = commandRegistry.hasCommand(commandId)\n ? commandRegistry.getCommand(commandId)\n : undefined;\n const params = resolveParams(tokens.slice(1), command);\n return { command: { commandId, params }, operator };\n });\n}\n","/** Minimal readline-style editor for xterm-backed REPL backends. */\nexport class LineInput {\n private buffer = '';\n private cursor = 0;\n private history: string[] = [];\n private historyDraft = '';\n private historyIndex = 0;\n\n constructor(private write: (data: string) => void) {}\n\n reset(): void {\n this.buffer = '';\n this.cursor = 0;\n this.historyDraft = '';\n this.historyIndex = this.history.length;\n }\n\n /** Returns the submitted line on Enter, otherwise null. */\n feed(data: string): string | null {\n if (data === '\\r') {\n const line = this.buffer;\n this.pushHistory(line);\n this.buffer = '';\n this.cursor = 0;\n this.write('\\r\\n');\n return line;\n }\n\n if (data === '\\u007f' || data === '\\b') {\n this.deleteBackward();\n return null;\n }\n\n if (data === '\\x1b[D' || data === '\\x1bOD') {\n this.move(-1);\n return null;\n }\n if (data === '\\x1b[C' || data === '\\x1bOC') {\n this.move(1);\n return null;\n }\n if (data === '\\x1b[A' || data === '\\x1bOA') {\n this.historyPrev();\n return null;\n }\n if (data === '\\x1b[B' || data === '\\x1bOB') {\n this.historyNext();\n return null;\n }\n if (data === '\\x1b[3~') {\n this.deleteForward();\n return null;\n }\n if (data === '\\x1b[H' || data === '\\x1bOH') {\n this.cursorHome();\n return null;\n }\n if (data === '\\x1b[F' || data === '\\x1bOF') {\n this.cursorEnd();\n return null;\n }\n\n if (data.startsWith('\\x1b')) return null;\n\n for (const char of data) {\n if (char < ' ') continue;\n this.insert(char);\n }\n return null;\n }\n\n private move(delta: number): void {\n const next = this.cursor + delta;\n if (next < 0 || next > this.buffer.length) return;\n const steps = Math.abs(delta);\n this.cursor = next;\n this.write(delta < 0 ? `\\x1b[${steps}D` : `\\x1b[${steps}C`);\n }\n\n private cursorHome(): void {\n if (this.cursor === 0) return;\n this.write(`\\x1b[${this.cursor}D`);\n this.cursor = 0;\n }\n\n private cursorEnd(): void {\n const steps = this.buffer.length - this.cursor;\n if (steps <= 0) return;\n this.write(`\\x1b[${steps}C`);\n this.cursor = this.buffer.length;\n }\n\n private insert(char: string): void {\n if (this.cursor === this.buffer.length) {\n this.buffer += char;\n this.cursor++;\n this.write(char);\n return;\n }\n const tail = this.buffer.slice(this.cursor);\n this.buffer = this.buffer.slice(0, this.cursor) + char + tail;\n this.cursor++;\n this.write(char + tail + `\\x1b[${tail.length}D`);\n }\n\n private deleteBackward(): void {\n if (this.cursor === 0) return;\n if (this.cursor === this.buffer.length) {\n this.buffer = this.buffer.slice(0, -1);\n this.cursor--;\n this.write('\\b \\b');\n return;\n }\n const after = this.buffer.slice(this.cursor);\n this.buffer = this.buffer.slice(0, this.cursor - 1) + after;\n this.cursor--;\n this.write(`\\b${after} ` + `\\x1b[${after.length + 1}D`);\n }\n\n private deleteForward(): void {\n if (this.cursor >= this.buffer.length) return;\n const after = this.buffer.slice(this.cursor + 1);\n this.write(`${after} ` + `\\x1b[${after.length + 1}D`);\n this.buffer = this.buffer.slice(0, this.cursor) + after;\n }\n\n private replaceBuffer(next: string): void {\n if (this.cursor > 0) this.write(`\\x1b[${this.cursor}D`);\n if (this.buffer.length > 0) this.write('\\x1b[K');\n this.buffer = next;\n this.cursor = next.length;\n if (next) this.write(next);\n }\n\n private historyPrev(): void {\n if (this.history.length === 0) return;\n if (this.historyIndex === this.history.length) {\n this.historyDraft = this.buffer;\n }\n if (this.historyIndex === 0) return;\n this.historyIndex--;\n this.replaceBuffer(this.history[this.historyIndex]);\n }\n\n private historyNext(): void {\n if (this.historyIndex >= this.history.length) return;\n this.historyIndex++;\n if (this.historyIndex === this.history.length) {\n this.replaceBuffer(this.historyDraft);\n this.historyDraft = '';\n return;\n }\n this.replaceBuffer(this.history[this.historyIndex]);\n }\n\n private pushHistory(line: string): void {\n if (line.length > 0 && this.history[this.history.length - 1] !== line) {\n this.history.push(line);\n }\n this.historyIndex = this.history.length;\n this.historyDraft = '';\n }\n}\n","import { commandRegistry, type CommandRegistry, type Command } from '@eclipse-docks/core';\nimport { parseShellLine } from './shell-parser';\nimport { LineInput } from './line-input';\n\nexport interface RunResult {\n success: boolean;\n results: unknown[];\n error?: string;\n}\n\nfunction mapOutputToParams(\n output: unknown,\n producerCommand: Command | undefined\n): Record<string, unknown> {\n if (output == null) return {};\n if (typeof output === 'object' && !Array.isArray(output)) {\n return output as Record<string, unknown>;\n }\n const firstOutput = producerCommand?.output?.[0];\n if (firstOutput) {\n return { [firstOutput.name]: output };\n }\n return {};\n}\n\nexport async function runShellLine(\n line: string,\n registry: CommandRegistry = commandRegistry\n): Promise<RunResult> {\n const segments = parseShellLine(line, registry);\n const results: unknown[] = [];\n let pipedOutput: Record<string, unknown> | null = null;\n let lastProducerCommand: Command | undefined;\n\n for (let i = 0; i < segments.length; i++) {\n const { command, operator } = segments[i];\n if (!command.commandId) continue;\n\n const cmd = registry.hasCommand(command.commandId)\n ? registry.getCommand(command.commandId)\n : undefined;\n if (!cmd) {\n return {\n success: false,\n results,\n error: `Command not found: ${command.commandId}`,\n };\n }\n\n const mergedParams = {\n ...mapOutputToParams(pipedOutput ?? undefined, lastProducerCommand),\n ...command.params,\n };\n\n const context = registry.createExecutionContext(mergedParams);\n\n try {\n const result = registry.execute(command.commandId, context);\n const resolved = result instanceof Promise ? await result : result;\n results.push(resolved);\n\n if (operator === '|') {\n pipedOutput = mapOutputToParams(resolved, cmd) as Record<string, unknown>;\n lastProducerCommand = cmd;\n } else {\n pipedOutput = null;\n lastProducerCommand = undefined;\n }\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n return { success: false, results, error: msg };\n }\n }\n\n return { success: true, results };\n}\n\nfunction formatResult(result: RunResult): string {\n if (result.error) return `\\r\\n\\x1b[31m${result.error}\\x1b[0m\\r\\n`;\n if (result.results.length === 0) return '';\n const last = result.results[result.results.length - 1];\n if (last == null) return '';\n if (typeof last === 'object') return JSON.stringify(last, null, 2) + '\\r\\n';\n return String(last) + '\\r\\n';\n}\n\nexport class CommandsBackend {\n private writeCallbacks = new Set<(data: string) => void>();\n private lineInput: LineInput;\n private prompt = '> ';\n\n constructor() {\n this.lineInput = new LineInput((data) => this.emit(data));\n }\n\n onDidWrite(callback: (data: string) => void): () => void {\n this.writeCallbacks.add(callback);\n return () => this.writeCallbacks.delete(callback);\n }\n\n private emit(data: string): void {\n for (const cb of this.writeCallbacks) cb(data);\n }\n\n async open(): Promise<void> {\n this.emit('Commands\\r\\nType commands (supports && and |)\\r\\n\\r\\n' + this.prompt);\n }\n\n close(): void {\n this.lineInput.reset();\n }\n\n setDimensions(_dimensions: { cols: number; rows: number }): void {}\n\n handleInput(data: string): void {\n const line = this.lineInput.feed(data);\n if (line === null) return;\n void this.runLine(line);\n }\n\n private async runLine(line: string): Promise<void> {\n const trimmed = line.trim();\n if (!trimmed) {\n this.emit(this.prompt);\n return;\n }\n const result = await runShellLine(trimmed);\n this.emit(formatResult(result));\n this.emit(this.prompt);\n }\n}\n","import { createJsRuntime, type JsRuntime } from '@eclipse-docks/core';\nimport type { TerminalBackend } from './terminal-api';\nimport { LineInput } from './line-input';\n\nexport const JS_REPL_PROFILE_ID = 'terminal.javascript-repl';\n\nconst PROMPT = '> ';\n\nfunction formatJsResult(value: unknown): string {\n if (value === undefined) return '';\n if (value === null) return 'null\\r\\n';\n if (typeof value === 'object') return JSON.stringify(value, null, 2) + '\\r\\n';\n return String(value) + '\\r\\n';\n}\n\nexport class JsReplBackend implements TerminalBackend {\n private writeCallbacks = new Set<(data: string) => void>();\n private lineInput: LineInput;\n private runtime: JsRuntime | null = null;\n private running = false;\n\n constructor() {\n this.lineInput = new LineInput((data) => this.emit(data));\n }\n\n onDidWrite(callback: (data: string) => void): () => void {\n this.writeCallbacks.add(callback);\n return () => this.writeCallbacks.delete(callback);\n }\n\n private emit(data: string): void {\n for (const cb of this.writeCallbacks) cb(data);\n }\n\n private getRuntime(): JsRuntime {\n if (!this.runtime) {\n this.runtime = createJsRuntime();\n }\n return this.runtime;\n }\n\n async open(): Promise<void> {\n this.emit('JavaScript REPL\\r\\n\\r\\n' + PROMPT);\n }\n\n close(): void {\n this.runtime?.close();\n this.runtime = null;\n this.lineInput.reset();\n }\n\n setDimensions(_dimensions: { cols: number; rows: number }): void {}\n\n handleInput(data: string): void {\n if (this.running) return;\n const line = this.lineInput.feed(data);\n if (line === null) return;\n void this.runLine(line);\n }\n\n private async runLine(line: string): Promise<void> {\n const trimmed = line.trim();\n if (!trimmed) {\n this.emit(PROMPT);\n return;\n }\n\n this.running = true;\n try {\n const result = await this.getRuntime().execute(trimmed);\n const output = formatJsResult(result);\n if (output) this.emit(output);\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n this.emit(`\\x1b[31m${msg}\\x1b[0m\\r\\n`);\n } finally {\n this.running = false;\n this.emit(PROMPT);\n }\n }\n}\n"],"mappings":"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"}
|