@chainingintention/pi-web-cn 1.202608.5 → 1.202608.6
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/client/assets/{CodeViewer-BUT2Idcq.js → CodeViewer-CWKEeX0r.js} +1 -1
- package/dist/client/assets/{TerminalPanel-b8CZY7en.js → TerminalPanel-BmA7Ayzk.js} +1 -1
- package/dist/client/assets/{UnifiedDiffViewer-CXY7AXrD.js → UnifiedDiffViewer-2DACwxFY.js} +1 -1
- package/dist/client/assets/{index-80SI7dCz.js → index-D6j67Izj.js} +491 -300
- package/dist/client/index.html +1 -1
- package/dist/config.js +17 -0
- package/dist/config.js.map +1 -1
- package/dist/pi-web-plugins/relays/relaysPanelElement.js +112 -46
- package/dist/server/piWebStatus.js +7 -1
- package/dist/server/piWebStatus.js.map +1 -1
- package/dist/server/sessiond/sessionServiceDependencies.js +1 -0
- package/dist/server/sessiond/sessionServiceDependencies.js.map +1 -1
- package/dist/server/sessiond.js +1 -0
- package/dist/server/sessiond.js.map +1 -1
- package/dist/server/sessions/extensionDialogWaiters.js +76 -0
- package/dist/server/sessions/extensionDialogWaiters.js.map +1 -0
- package/dist/server/sessions/pendingExtensionDialogStore.js +196 -0
- package/dist/server/sessions/pendingExtensionDialogStore.js.map +1 -0
- package/dist/server/sessions/piSessionService.js +375 -71
- package/dist/server/sessions/piSessionService.js.map +1 -1
- package/dist/server/sessions/sessionRoutes.js +48 -25
- package/dist/server/sessions/sessionRoutes.js.map +1 -1
- package/dist/server/sessions/sessionUiEvents.js +9 -2
- package/dist/server/sessions/sessionUiEvents.js.map +1 -1
- package/dist/server/sessions/spawnSessionTool.js +8 -1
- package/dist/server/sessions/spawnSessionTool.js.map +1 -1
- package/dist/server/sessions/spawnSubsessionTool.js +7 -1
- package/dist/server/sessions/spawnSubsessionTool.js.map +1 -1
- package/dist/shared/apiTypes.d.ts +116 -1
- package/dist/shared/apiTypes.js +8 -0
- package/dist/shared/apiTypes.js.map +1 -1
- package/dist/shared/federatedRoutes.js +2 -0
- package/dist/shared/federatedRoutes.js.map +1 -1
- package/docs/config.md +21 -1
- package/docs/plugins.md +14 -0
- package/package.json +1 -1
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
/** The value an extension's dialog Promise settles with on any close without an answer. */
|
|
2
|
+
export function extensionDialogCancelValue(kind) {
|
|
3
|
+
return kind === "confirm" ? false : undefined;
|
|
4
|
+
}
|
|
5
|
+
/**
|
|
6
|
+
* The auto-cancel delay of one dialog: the sooner of the extension's own
|
|
7
|
+
* `timeout` and the daemon's `extensionDialogsTimeoutMs` default, where `0`
|
|
8
|
+
* (or an invalid extension value, defensively ignored) means "waits forever".
|
|
9
|
+
*/
|
|
10
|
+
export function effectiveExtensionDialogTimeoutMs(extensionTimeoutMs, daemonDefaultMs) {
|
|
11
|
+
const fromExtension = typeof extensionTimeoutMs === "number" && Number.isFinite(extensionTimeoutMs) && extensionTimeoutMs > 0 ? extensionTimeoutMs : undefined;
|
|
12
|
+
const fromDaemon = daemonDefaultMs > 0 ? daemonDefaultMs : undefined;
|
|
13
|
+
if (fromExtension === undefined)
|
|
14
|
+
return fromDaemon;
|
|
15
|
+
if (fromDaemon === undefined)
|
|
16
|
+
return fromExtension;
|
|
17
|
+
return Math.min(fromExtension, fromDaemon);
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* The parked Promise resolvers behind open extension dialogs, plus the timers
|
|
21
|
+
* and signal subscriptions that can end a wait without the browser. Timers use
|
|
22
|
+
* the global `setTimeout`/`clearTimeout` looked up per call, the same seam the
|
|
23
|
+
* rest of the service's timer tests fake.
|
|
24
|
+
*
|
|
25
|
+
* Kept deliberately separate from {@link PendingExtensionDialogStore}: the
|
|
26
|
+
* store owns the domain state every browser sees, the waiters own the one
|
|
27
|
+
* in-memory resolver each open dialog parks inside extension code — state no
|
|
28
|
+
* browser ever observes and that must not survive the runtime. The pairing is
|
|
29
|
+
* the wiring's invariant: every open store record has exactly one parked
|
|
30
|
+
* waiter, and whoever closes the record settles the waiter exactly once.
|
|
31
|
+
*/
|
|
32
|
+
export class ExtensionDialogWaiters {
|
|
33
|
+
constructor() {
|
|
34
|
+
this.parked = new Map();
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Park the extension-facing Promise for a dialog the store just opened. Arms
|
|
38
|
+
* the timeout and signal triggers; both are disarmed when the wait settles,
|
|
39
|
+
* so a settled wait can never be triggered (nor trigger twice).
|
|
40
|
+
*/
|
|
41
|
+
park(dialog, triggers = {}) {
|
|
42
|
+
return new Promise((resolve) => {
|
|
43
|
+
const parked = { cancelValue: extensionDialogCancelValue(dialog.kind), resolve };
|
|
44
|
+
if (triggers.timeoutMs !== undefined) {
|
|
45
|
+
const handle = setTimeout(() => { triggers.onTrigger?.("timeout"); }, triggers.timeoutMs);
|
|
46
|
+
parked.cancelArmedTimeout = () => { clearTimeout(handle); };
|
|
47
|
+
}
|
|
48
|
+
if (triggers.signal !== undefined) {
|
|
49
|
+
const signal = triggers.signal;
|
|
50
|
+
const onAbort = () => { triggers.onTrigger?.("cancelled"); };
|
|
51
|
+
signal.addEventListener("abort", onAbort, { once: true });
|
|
52
|
+
parked.removeSignalListener = () => { signal.removeEventListener("abort", onAbort); };
|
|
53
|
+
}
|
|
54
|
+
this.parked.set(dialog.dialogId, parked);
|
|
55
|
+
});
|
|
56
|
+
}
|
|
57
|
+
/** Resolve the parked wait with the user's answer, which the store has already validated and recorded. */
|
|
58
|
+
settleWithAnswer(dialogId, answer) {
|
|
59
|
+
return this.settle(dialogId, (parked) => { parked.resolve(answer); });
|
|
60
|
+
}
|
|
61
|
+
/** Resolve the parked wait with the dialog kind's cancel value after a close without an answer. */
|
|
62
|
+
settleWithCancelValue(dialogId) {
|
|
63
|
+
return this.settle(dialogId, (parked) => { parked.resolve(parked.cancelValue); });
|
|
64
|
+
}
|
|
65
|
+
settle(dialogId, resolveParked) {
|
|
66
|
+
const parked = this.parked.get(dialogId);
|
|
67
|
+
if (parked === undefined)
|
|
68
|
+
return false;
|
|
69
|
+
this.parked.delete(dialogId);
|
|
70
|
+
parked.cancelArmedTimeout?.();
|
|
71
|
+
parked.removeSignalListener?.();
|
|
72
|
+
resolveParked(parked);
|
|
73
|
+
return true;
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
//# sourceMappingURL=extensionDialogWaiters.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"extensionDialogWaiters.js","sourceRoot":"","sources":["../../../src/server/sessions/extensionDialogWaiters.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,196 @@
|
|
|
1
|
+
import { randomUUID } from "node:crypto";
|
|
2
|
+
import { EXTENSION_DIALOG_ID_MAX_LENGTH, EXTENSION_DIALOG_INPUT_MAX_LENGTH, EXTENSION_DIALOG_OPTION_LIMIT, EXTENSION_DIALOG_TEXT_MAX_LENGTH, } from "../../shared/apiTypes.js";
|
|
3
|
+
/** Rejected input: the dialog is malformed, or an answer does not fit its kind. */
|
|
4
|
+
export class PendingExtensionDialogValidationError extends Error {
|
|
5
|
+
constructor(message) {
|
|
6
|
+
super(message);
|
|
7
|
+
this.name = "PendingExtensionDialogValidationError";
|
|
8
|
+
}
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Daemon-owned open-dialog state: the extension dialogs of every session,
|
|
12
|
+
* several per session because each dialog is an independent blocking wait
|
|
13
|
+
* inside extension code — opening one must never supersede another.
|
|
14
|
+
*
|
|
15
|
+
* The store is pure domain logic — no Fastify, no Pi session, no I/O, no
|
|
16
|
+
* timers. It validates dialogs and answers and owns the open/answer/cancel
|
|
17
|
+
* transitions; callers hold the waiting Promise resolvers, publish the
|
|
18
|
+
* returned records and outcomes, and own the timers that turn `timeoutAt`
|
|
19
|
+
* into a `"timeout"` cancel.
|
|
20
|
+
*
|
|
21
|
+
* State is deliberately daemon-lifetime and in-memory. An open dialog is
|
|
22
|
+
* meaningful only while the session runtime whose extension is waiting on it
|
|
23
|
+
* exists, and browsers rehydrate open dialogs from `SessionStatus` rather
|
|
24
|
+
* than from disk.
|
|
25
|
+
*/
|
|
26
|
+
export class PendingExtensionDialogStore {
|
|
27
|
+
constructor(options = {}) {
|
|
28
|
+
/** Per-session open dialogs in insertion order, so `pendingDialogs` reads oldest first. */
|
|
29
|
+
this.openBySessionId = new Map();
|
|
30
|
+
this.now = options.now ?? (() => new Date());
|
|
31
|
+
this.createDialogId = options.createDialogId ?? randomUUID;
|
|
32
|
+
}
|
|
33
|
+
/** The session's open dialogs, oldest first, for {@link SessionStatus} projection. */
|
|
34
|
+
pendingDialogs(sessionId) {
|
|
35
|
+
const dialogs = this.openBySessionId.get(requireSessionId(sessionId));
|
|
36
|
+
if (dialogs === undefined)
|
|
37
|
+
return [];
|
|
38
|
+
return [...dialogs.values()].map(cloneDialog);
|
|
39
|
+
}
|
|
40
|
+
open(input) {
|
|
41
|
+
const sessionId = requireSessionId(input.sessionId);
|
|
42
|
+
const kind = requireKind(input.kind);
|
|
43
|
+
const now = this.now();
|
|
44
|
+
const dialog = {
|
|
45
|
+
dialogId: requireId(this.createDialogId(), "dialogId"),
|
|
46
|
+
kind,
|
|
47
|
+
title: requireText(input.title, "dialog title"),
|
|
48
|
+
...kindFields(kind, input),
|
|
49
|
+
askedAt: now.toISOString(),
|
|
50
|
+
...timeoutField(input.timeoutMs, now),
|
|
51
|
+
runScoped: input.runScoped,
|
|
52
|
+
};
|
|
53
|
+
const dialogs = this.openBySessionId.get(sessionId) ?? new Map();
|
|
54
|
+
if (dialogs.has(dialog.dialogId)) {
|
|
55
|
+
throw new Error(`Dialog id ${dialog.dialogId} is already open in session ${sessionId}`);
|
|
56
|
+
}
|
|
57
|
+
dialogs.set(dialog.dialogId, dialog);
|
|
58
|
+
this.openBySessionId.set(sessionId, dialogs);
|
|
59
|
+
return cloneDialog(dialog);
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Record the user's answer and close the dialog. The answer is validated
|
|
63
|
+
* against the dialog's kind first, so an answer that does not fit leaves the
|
|
64
|
+
* dialog open for the browser to correct.
|
|
65
|
+
*/
|
|
66
|
+
answer(sessionId, dialogId, value) {
|
|
67
|
+
const dialog = this.openBySessionId.get(requireSessionId(sessionId))?.get(dialogId);
|
|
68
|
+
if (dialog === undefined)
|
|
69
|
+
return { status: "stale" };
|
|
70
|
+
const answer = validateAnswer(dialog, value);
|
|
71
|
+
return { status: "closed", outcome: this.requireClose(sessionId, dialog, "answered", answer) };
|
|
72
|
+
}
|
|
73
|
+
/** Close the dialog without an answer; the extension's wait settles with its kind's cancel value. */
|
|
74
|
+
cancel(sessionId, dialogId, reason) {
|
|
75
|
+
const dialog = this.openBySessionId.get(requireSessionId(sessionId))?.get(dialogId);
|
|
76
|
+
if (dialog === undefined)
|
|
77
|
+
return { status: "stale" };
|
|
78
|
+
return { status: "closed", outcome: this.requireClose(sessionId, dialog, reason, undefined) };
|
|
79
|
+
}
|
|
80
|
+
requireClose(sessionId, dialog, reason, answer) {
|
|
81
|
+
const dialogs = this.openBySessionId.get(sessionId);
|
|
82
|
+
if (dialogs?.delete(dialog.dialogId) !== true) {
|
|
83
|
+
throw new Error(`Dialog ${dialog.dialogId} of session ${sessionId} disappeared while closing`);
|
|
84
|
+
}
|
|
85
|
+
if (dialogs.size === 0)
|
|
86
|
+
this.openBySessionId.delete(sessionId);
|
|
87
|
+
return {
|
|
88
|
+
dialogId: dialog.dialogId,
|
|
89
|
+
reason,
|
|
90
|
+
...(answer === undefined ? {} : { answer }),
|
|
91
|
+
askedAt: dialog.askedAt,
|
|
92
|
+
closedAt: this.timestamp(),
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
timestamp() {
|
|
96
|
+
return this.now().toISOString();
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
function validateAnswer(dialog, value) {
|
|
100
|
+
switch (dialog.kind) {
|
|
101
|
+
case "confirm":
|
|
102
|
+
if (typeof value !== "boolean")
|
|
103
|
+
throw new PendingExtensionDialogValidationError(`Dialog ${dialog.dialogId} expects a boolean answer`);
|
|
104
|
+
return value;
|
|
105
|
+
case "select":
|
|
106
|
+
if (typeof value !== "string" || dialog.options?.includes(value) !== true) {
|
|
107
|
+
throw new PendingExtensionDialogValidationError(`Dialog ${dialog.dialogId} has no option ${String(value)}`);
|
|
108
|
+
}
|
|
109
|
+
return value;
|
|
110
|
+
case "input":
|
|
111
|
+
if (typeof value !== "string")
|
|
112
|
+
throw new PendingExtensionDialogValidationError(`Dialog ${dialog.dialogId} expects a text answer`);
|
|
113
|
+
if (value.length > EXTENSION_DIALOG_INPUT_MAX_LENGTH) {
|
|
114
|
+
throw new PendingExtensionDialogValidationError(`Answer of dialog ${dialog.dialogId} exceeds its length limit`);
|
|
115
|
+
}
|
|
116
|
+
return value;
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
/** Kind-specific fields of a validated record; irrelevant fields are dropped rather than rejected. */
|
|
120
|
+
function kindFields(kind, input) {
|
|
121
|
+
switch (kind) {
|
|
122
|
+
case "confirm": {
|
|
123
|
+
const message = optionalText(input.message, "dialog message");
|
|
124
|
+
return message === undefined ? {} : { message };
|
|
125
|
+
}
|
|
126
|
+
case "select":
|
|
127
|
+
return { options: validateOptions(input.options) };
|
|
128
|
+
case "input": {
|
|
129
|
+
const placeholder = optionalText(input.placeholder, "dialog placeholder");
|
|
130
|
+
return placeholder === undefined ? {} : { placeholder };
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
function validateOptions(options) {
|
|
135
|
+
if (options === undefined || options.length === 0) {
|
|
136
|
+
throw new PendingExtensionDialogValidationError("A select dialog must offer at least one option");
|
|
137
|
+
}
|
|
138
|
+
if (options.length > EXTENSION_DIALOG_OPTION_LIMIT) {
|
|
139
|
+
throw new PendingExtensionDialogValidationError(`A select dialog must not offer more than ${EXTENSION_DIALOG_OPTION_LIMIT.toString()} options`);
|
|
140
|
+
}
|
|
141
|
+
const seen = new Set();
|
|
142
|
+
return options.map((option) => {
|
|
143
|
+
const validated = requireText(option, "select option");
|
|
144
|
+
if (seen.has(validated))
|
|
145
|
+
throw new PendingExtensionDialogValidationError(`Duplicate select option ${validated}`);
|
|
146
|
+
seen.add(validated);
|
|
147
|
+
return validated;
|
|
148
|
+
});
|
|
149
|
+
}
|
|
150
|
+
function timeoutField(timeoutMs, now) {
|
|
151
|
+
if (timeoutMs === undefined)
|
|
152
|
+
return {};
|
|
153
|
+
if (!Number.isFinite(timeoutMs) || timeoutMs <= 0) {
|
|
154
|
+
throw new PendingExtensionDialogValidationError("A dialog timeout must be a positive number of milliseconds");
|
|
155
|
+
}
|
|
156
|
+
return { timeoutAt: new Date(now.getTime() + timeoutMs).toISOString() };
|
|
157
|
+
}
|
|
158
|
+
function cloneDialog(dialog) {
|
|
159
|
+
return { ...dialog, ...(dialog.options === undefined ? {} : { options: [...dialog.options] }) };
|
|
160
|
+
}
|
|
161
|
+
function requireSessionId(sessionId) {
|
|
162
|
+
if (sessionId === "")
|
|
163
|
+
throw new Error("sessionId must not be empty");
|
|
164
|
+
return sessionId;
|
|
165
|
+
}
|
|
166
|
+
/** Runtime guard: the input crosses extension code, so the declared kind is checked despite its type. */
|
|
167
|
+
function requireKind(kind) {
|
|
168
|
+
if (kind !== "confirm" && kind !== "select" && kind !== "input") {
|
|
169
|
+
throw new PendingExtensionDialogValidationError(`Unknown dialog kind ${kind}`);
|
|
170
|
+
}
|
|
171
|
+
return kind;
|
|
172
|
+
}
|
|
173
|
+
function requireId(value, field) {
|
|
174
|
+
if (value.trim() === "")
|
|
175
|
+
throw new PendingExtensionDialogValidationError(`${field} must not be empty`);
|
|
176
|
+
if (value.length > EXTENSION_DIALOG_ID_MAX_LENGTH)
|
|
177
|
+
throw new PendingExtensionDialogValidationError(`${field} exceeds its length limit`);
|
|
178
|
+
return value;
|
|
179
|
+
}
|
|
180
|
+
function requireText(value, field) {
|
|
181
|
+
if (value.trim() === "")
|
|
182
|
+
throw new PendingExtensionDialogValidationError(`${field} must not be empty`);
|
|
183
|
+
if (value.length > EXTENSION_DIALOG_TEXT_MAX_LENGTH)
|
|
184
|
+
throw new PendingExtensionDialogValidationError(`${field} exceeds its length limit`);
|
|
185
|
+
return value;
|
|
186
|
+
}
|
|
187
|
+
/** Optional cosmetic prose: blank means absent rather than being a validation error. */
|
|
188
|
+
function optionalText(value, field) {
|
|
189
|
+
if (value === undefined || value.trim() === "")
|
|
190
|
+
return undefined;
|
|
191
|
+
if (value.length > EXTENSION_DIALOG_TEXT_MAX_LENGTH) {
|
|
192
|
+
throw new PendingExtensionDialogValidationError(`${field} exceeds its length limit`);
|
|
193
|
+
}
|
|
194
|
+
return value;
|
|
195
|
+
}
|
|
196
|
+
//# sourceMappingURL=pendingExtensionDialogStore.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pendingExtensionDialogStore.js","sourceRoot":"","sources":["../../../src/server/sessions/pendingExtensionDialogStore.ts"],"names":[],"mappings":"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"}
|