@timurproko/a1 0.2.6-dev.717 → 0.2.6-dev.734
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/cli.js +13 -2
- package/bin/ui.js +13 -0
- package/dist/app/session-shell/clipboard-services.d.ts +19 -0
- package/dist/app/session-shell/clipboard-services.js +7 -0
- package/dist/app/session-shell/exit-notice.d.ts +9 -5
- package/dist/app/session-shell/exit-notice.js +5 -5
- package/dist/app/session-shell/index.d.ts +3 -1
- package/dist/app/session-shell/index.js +1 -0
- package/dist/app/session-shell/paste-preparation-client.d.ts +3 -0
- package/dist/app/session-shell/paste-preparation-client.js +5 -2
- package/dist/app/session-shell/path-chip-presentation.d.ts +10 -3
- package/dist/app/session-shell/path-chip-presentation.js +48 -6
- package/dist/app/session-shell/prompt-chips.js +30 -4
- package/dist/app/session-shell/prompt-suggestion-controller.d.ts +5 -4
- package/dist/app/session-shell/prompt-suggestion-controller.js +148 -58
- package/dist/app/session-shell/quit-outro.d.ts +3 -1
- package/dist/app/session-shell/quit-outro.js +23 -8
- package/dist/app/session-shell/response-copy-transport.d.ts +6 -1
- package/dist/app/session-shell/response-copy-transport.js +8 -2
- package/dist/app/session-shell/session-shell-root.d.ts +22 -11
- package/dist/app/session-shell/session-shell-root.js +19 -12
- package/dist/app/session-shell/session-shell.d.ts +19 -21
- package/dist/app/session-shell/session-shell.js +678 -840
- package/dist/app/session-shell/session-viewport-controller.js +33 -21
- package/dist/cli/dispatch.js +5 -3
- package/dist/cli/session-context.d.ts +5 -1
- package/dist/cli/session-context.js +25 -8
- package/dist/composition/owned-ui.d.ts +23 -2
- package/dist/composition/owned-ui.js +124 -33
- package/dist/composition/session-info-reference.d.ts +2 -2
- package/dist/composition/session-info-reference.js +2 -2
- package/dist/composition/settings-route-host.js +2 -1
- package/dist/contracts/agent-engine/capability-ports.d.ts +1 -85
- package/dist/contracts/agent-engine/capability-ports.js +1 -35
- package/dist/contracts/agent-engine/index.d.ts +1 -7
- package/dist/contracts/agent-engine/index.js +0 -4
- package/dist/contracts/owned-ui/index.d.ts +9 -3
- package/dist/contracts/owned-ui/index.js +2 -1
- package/dist/contracts/owned-ui/model.d.ts +10 -0
- package/dist/contracts/owned-ui/session-backend.d.ts +119 -0
- package/dist/contracts/owned-ui/session-presenters.d.ts +55 -0
- package/dist/contracts/owned-ui/session-presenters.js +1 -0
- package/dist/contracts/owned-ui/session-workflows.d.ts +342 -0
- package/dist/contracts/owned-ui/session-workflows.js +30 -0
- package/dist/contracts/owned-ui/suggestion-diagnostics.d.ts +5 -1
- package/dist/contracts/owned-ui/suggestion-diagnostics.js +3 -1
- package/dist/contracts/owned-ui/validation.js +7 -0
- package/dist/features/launch/index.d.ts +1 -1
- package/dist/features/launch/session-context.d.ts +17 -2
- package/dist/features/launch/session-context.js +9 -5
- package/dist/features/owned-ui/settings-app.js +56 -54
- package/dist/features/prompt-suggestions/diagnostics.js +4 -1
- package/dist/foundation/lifecycle/index.d.ts +2 -2
- package/dist/foundation/lifecycle/index.js +1 -1
- package/dist/foundation/lifecycle/session-repository-context.d.ts +19 -2
- package/dist/foundation/lifecycle/session-repository-context.js +434 -66
- package/dist/foundation/process-containment/index.d.ts +1 -0
- package/dist/foundation/process-containment/index.js +1 -0
- package/dist/foundation/process-containment/native-process-inspector.d.ts +3 -0
- package/dist/foundation/process-containment/native-process-inspector.js +21 -0
- package/dist/foundation/release/bootstrap.js +1 -2
- package/dist/foundation/release/progress-palette.generated.d.ts +2 -2
- package/dist/foundation/release/progress-palette.generated.js +2 -2
- package/dist/foundation/release/release-gc.js +1 -1
- package/dist/foundation/release/update.js +0 -4
- package/dist/foundation/startup/startup-descriptor.js +2 -2
- package/dist/foundation/storage/control-store.js +0 -12
- package/dist/integrations/pi/components/components.js +2 -18
- package/dist/integrations/pi/components/index.d.ts +4 -4
- package/dist/integrations/pi/components/index.js +2 -2
- package/dist/integrations/pi/components/modal-frame.js +3 -4
- package/dist/integrations/pi/components/models-dialog.js +6 -35
- package/dist/integrations/pi/components/prompt-input-port.d.ts +1 -0
- package/dist/integrations/pi/components/resources/builtin-themes.d.ts +2 -2
- package/dist/integrations/pi/components/resources/builtin-themes.js +2 -2
- package/dist/integrations/pi/components/share-operation-dialog.js +3 -3
- package/dist/integrations/pi/components/shell-editor-autocomplete.js +19 -16
- package/dist/integrations/pi/components/shell-extension-ui.d.ts +5 -3
- package/dist/integrations/pi/components/shell-extension-ui.js +26 -12
- package/dist/integrations/pi/components/shell-hotkey-sections.js +2 -2
- package/dist/integrations/pi/components/shell-presenters-info.js +10 -10
- package/dist/integrations/pi/components/shell-presenters-transcript.js +13 -13
- package/dist/integrations/pi/components/shell-selectors-dialogs.js +5 -6
- package/dist/integrations/pi/components/shell-shared-facade.d.ts +21 -1
- package/dist/integrations/pi/components/shell-shared-facade.js +19 -3
- package/dist/integrations/pi/components/skills-dialog.js +3 -3
- package/dist/integrations/pi/components/submitted-prompt-adapter.js +2 -3
- package/dist/integrations/pi/components/theme.d.ts +9 -0
- package/dist/integrations/pi/components/theme.js +30 -0
- package/dist/integrations/pi/components/tool-result-adapter.js +6 -1
- package/dist/integrations/pi/components/upstream/adjacent/core/keybindings.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/adjacent/core/keybindings.js +1 -1
- package/dist/integrations/pi/components/upstream/assets/earendil-image.json +2 -2
- package/dist/integrations/pi/components/upstream/components/countdown-timer.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/components/earendil-announcement.js +1 -1
- package/dist/integrations/pi/components/upstream/components/extension-editor.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/components/extension-editor.js +6 -6
- package/dist/integrations/pi/components/upstream/components/extension-input.js +4 -4
- package/dist/integrations/pi/components/upstream/components/extension-selector.js +4 -4
- package/dist/integrations/pi/components/upstream/components/mermaid.js +1 -1
- package/dist/integrations/pi/components/upstream/components/owned-editor.d.ts +5 -5
- package/dist/integrations/pi/components/upstream/components/owned-editor.js +8 -5
- package/dist/integrations/pi/components/upstream/components/pi-logo.js +1 -1
- package/dist/integrations/pi/components/upstream/components/scoped-models-selector.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/components/scoped-models-selector.js +3 -3
- package/dist/integrations/pi/components/upstream/components/session-footer.js +1 -1
- package/dist/integrations/pi/components/upstream/components/session-selector-search.js +1 -1
- package/dist/integrations/pi/components/upstream/components/session-selector.js +9 -9
- package/dist/integrations/pi/components/upstream/components/skill-invocation-message.d.ts +3 -2
- package/dist/integrations/pi/components/upstream/components/skill-invocation-message.js +6 -3
- package/dist/integrations/pi/components/upstream/components/status-indicator.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/components/status-indicator.js +1 -1
- package/dist/integrations/pi/components/upstream/components/themed-text.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/components/themed-text.js +1 -1
- package/dist/integrations/pi/components/upstream/components/thinking-selector.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/components/thinking-selector.js +2 -2
- package/dist/integrations/pi/components/upstream/components/tool-execution.d.ts +4 -0
- package/dist/integrations/pi/components/upstream/components/tool-execution.js +11 -1
- package/dist/integrations/pi/components/upstream/components/tree-selector.d.ts +2 -2
- package/dist/integrations/pi/components/upstream/components/tree-selector.js +27 -18
- package/dist/integrations/pi/components/upstream/components/trust-selector.js +1 -1
- package/dist/integrations/pi/components/upstream/external-editor.js +1 -1
- package/dist/integrations/pi/components/upstream/history/editor-core.d.ts +4 -4
- package/dist/integrations/pi/components/upstream/history/editor-core.js +11 -7
- package/dist/integrations/pi/components/upstream/history/kill-ring.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/history/kill-ring.js +1 -1
- package/dist/integrations/pi/components/upstream/history/printable-key.js +1 -1
- package/dist/integrations/pi/components/upstream/history/text-helpers.js +1 -1
- package/dist/integrations/pi/components/upstream/history/undo-stack.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/history/undo-stack.js +1 -1
- package/dist/integrations/pi/components/upstream/history/word-navigation.js +1 -1
- package/dist/integrations/pi/components/upstream/model-search.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/program-status-reporter.d.ts +31 -0
- package/dist/integrations/pi/components/upstream/program-status-reporter.js +89 -0
- package/dist/integrations/pi/components/upstream/theme/theme-controller.d.ts +1 -1
- package/dist/integrations/pi/components/upstream/theme/theme.d.ts +22 -1
- package/dist/integrations/pi/components/upstream/theme/theme.js +225 -10
- package/dist/integrations/pi/engine/adapter.d.ts +44 -24
- package/dist/integrations/pi/engine/adapter.js +130 -22
- package/dist/integrations/pi/engine/command-dispatch.d.ts +2 -5
- package/dist/integrations/pi/engine/extension-ui-binding.d.ts +2 -11
- package/dist/integrations/pi/engine/host-ports.d.ts +20 -0
- package/dist/integrations/pi/engine/host-ports.js +13 -0
- package/dist/integrations/pi/engine/host.d.ts +70 -0
- package/dist/integrations/pi/engine/host.js +147 -0
- package/dist/integrations/pi/engine/index.d.ts +8 -4
- package/dist/integrations/pi/engine/index.js +3 -1
- package/dist/integrations/pi/engine/pi-settings-metadata.json +1 -1
- package/dist/integrations/pi/engine/resource-catalog.d.ts +4 -23
- package/dist/integrations/pi/engine/resources/changelog.json +4 -4
- package/dist/integrations/pi/engine/runtime-integration.d.ts +8 -2
- package/dist/integrations/pi/engine/runtime-integration.js +12 -7
- package/dist/integrations/pi/engine/session-events.js +10 -2
- package/dist/integrations/pi/engine/session-integration.d.ts +3 -8
- package/dist/integrations/pi/engine/session-integration.js +0 -49
- package/dist/integrations/pi/engine/session-runtime.d.ts +18 -3
- package/dist/integrations/pi/engine/session-runtime.js +18 -7
- package/dist/integrations/pi/engine/settings-bridge.d.ts +2 -2
- package/dist/integrations/pi/engine/settings-bridge.js +0 -2
- package/dist/integrations/pi/engine/settings-port.d.ts +2 -0
- package/dist/integrations/pi/engine/settings-port.js +3 -5
- package/dist/integrations/pi/engine/transcript-projection.js +2 -1
- package/dist/integrations/pi/engine/workflows.d.ts +33 -260
- package/dist/integrations/pi/engine/workflows.js +6 -28
- package/dist/integrations/pi/session-presenters/index.d.ts +2 -0
- package/dist/integrations/pi/session-presenters/index.js +1 -0
- package/dist/integrations/pi/session-presenters/presenters.d.ts +16 -0
- package/dist/integrations/pi/session-presenters/presenters.js +341 -0
- package/dist/integrations/pi/startup-public.js +306 -290
- package/dist/integrations/pi/startup-public.manifest.json +289 -265
- package/dist/integrations/pi/tui-runtime/adapter.d.ts +2 -1
- package/dist/integrations/pi/tui-runtime/adapter.js +7 -2
- package/dist/integrations/pi/tui-runtime/contracts.d.ts +3 -1
- package/dist/integrations/pi/tui-runtime/damage-aware-terminal.d.ts +8 -1
- package/dist/integrations/pi/tui-runtime/damage-aware-terminal.js +67 -2
- package/dist/integrations/pi/tui-runtime/index.d.ts +1 -1
- package/dist/integrations/pi/tui-runtime/index.js +1 -1
- package/dist/native/darwin-arm64/manifest.json +1 -1
- package/dist/native/linux-x64/manifest.json +1 -1
- package/dist/native/win32-x64/manifest.json +2 -2
- package/dist/native/win32-x64/process-guardian.exe +0 -0
- package/dist/product-identity.d.ts +2 -2
- package/dist/product-identity.js +2 -2
- package/dist/product-identity.json +3 -1
- package/dist/runtime-payload-inventory.json +3092 -2878
- package/dist/ui/components/prompt-input.d.ts +2 -0
- package/dist/ui/components/prompt-input.js +5 -1
- package/dist/ui/components/text-selection.d.ts +1 -1
- package/dist/ui/components/text-selection.js +3 -1
- package/dist/ui/components/theme.d.ts +2 -0
- package/dist/ui/components/transcript-viewport.d.ts +6 -4
- package/dist/ui/components/transcript-viewport.js +94 -16
- package/dist/ui/components/value-menu.d.ts +2 -0
- package/dist/ui/components/value-menu.js +13 -8
- package/dist/ui/settings/declarations.d.ts +38 -14
- package/dist/ui/settings/declarations.js +35 -11
- package/dist/ui/settings/migrations.js +23 -0
- package/docs/architecture/boundaries.md +9 -1
- package/docs/architecture/project-structure.md +7 -5
- package/docs/architecture/prompt-suggestions.md +14 -10
- package/docs/local-worktree-cleanup.md +11 -5
- package/docs/openspec-archive-automation.md +6 -5
- package/package.json +3 -3
- package/dist/contracts/agent-engine/model.d.ts +0 -78
- package/dist/contracts/agent-engine/model.js +0 -1
- package/dist/contracts/agent-engine/ports.d.ts +0 -18
- package/dist/contracts/agent-engine/serialization.d.ts +0 -7
- package/dist/contracts/agent-engine/serialization.js +0 -58
- package/dist/contracts/agent-engine/validation.d.ts +0 -5
- package/dist/contracts/agent-engine/validation.js +0 -128
- package/dist/integrations/pi/components/upstream/theme/system-theme.d.ts +0 -61
- package/dist/integrations/pi/components/upstream/theme/system-theme.js +0 -709
- /package/dist/contracts/{agent-engine/ports.js → owned-ui/session-backend.js} +0 -0
|
@@ -8,6 +8,7 @@ import { PiExtensionUiBinding } from "./extension-ui-binding.js";
|
|
|
8
8
|
import { PiPromptSuggestions } from "./prompt-suggestions.js";
|
|
9
9
|
import { PiResourceCatalog } from "./resource-catalog.js";
|
|
10
10
|
import { PiEngineRuntime } from "./session-runtime.js";
|
|
11
|
+
import { detachedEngineHostPorts } from "./host-ports.js";
|
|
11
12
|
import { PiEngineSettings } from "./settings-port.js";
|
|
12
13
|
import { PiSessionEvents } from "./session-events.js";
|
|
13
14
|
import { readUsageView } from "./usage-view.js";
|
|
@@ -24,10 +25,11 @@ const DEFAULT_SURFACE = {
|
|
|
24
25
|
focusedRegion: "editor",
|
|
25
26
|
hardwareCursor: false,
|
|
26
27
|
};
|
|
27
|
-
/** Owns the pinned Pi session lifecycle and
|
|
28
|
+
/** Owns the pinned Pi session lifecycle and serves it to the owned shell as the neutral session backend. */
|
|
28
29
|
export class PiEngineAdapter {
|
|
29
30
|
#agentDir;
|
|
30
31
|
#sessionId;
|
|
32
|
+
#engineHost;
|
|
31
33
|
#workflowHost;
|
|
32
34
|
#engine;
|
|
33
35
|
#workflowInteraction;
|
|
@@ -118,9 +120,13 @@ export class PiEngineAdapter {
|
|
|
118
120
|
emitView: () => { this.#emitView(); },
|
|
119
121
|
});
|
|
120
122
|
#disposed = false;
|
|
121
|
-
|
|
123
|
+
#ports;
|
|
124
|
+
constructor(options) {
|
|
125
|
+
if (typeof options.sessionId !== "string" || options.sessionId.length === 0)
|
|
126
|
+
throw new TypeError("engine session id is required");
|
|
122
127
|
this.#agentDir = options.agentDir ?? getAgentDir();
|
|
123
|
-
this.#sessionId = options.sessionId
|
|
128
|
+
this.#sessionId = options.sessionId;
|
|
129
|
+
this.#engineHost = options.engineHost ?? detachedEngineHostPorts();
|
|
124
130
|
this.#workflowHost = options.workflowHost ?? defaultWorkflowHost();
|
|
125
131
|
this.#workflowInteraction = { prompt: async () => null, notify() { } };
|
|
126
132
|
this.#engine = new PiEngineRuntime({
|
|
@@ -133,7 +139,8 @@ export class PiEngineAdapter {
|
|
|
133
139
|
projectTrustPrompt: options.projectTrustPrompt,
|
|
134
140
|
createRuntime: options.createRuntime,
|
|
135
141
|
checkPackageUpdates: options.checkPackageUpdates,
|
|
136
|
-
|
|
142
|
+
signal: this.#engineHost.signal,
|
|
143
|
+
markStartupPhase: phase => this.#engineHost.markStartupPhase(phase),
|
|
137
144
|
...(options.repositoryContextReader === undefined ? {} : { repositoryContextReader: options.repositoryContextReader }),
|
|
138
145
|
host: this.#workflowHost,
|
|
139
146
|
}, {
|
|
@@ -143,6 +150,9 @@ export class PiEngineAdapter {
|
|
|
143
150
|
...this.#terminal,
|
|
144
151
|
hardwareCursor: runtime.services.settingsManager?.getShowHardwareCursor?.() ?? this.#terminal.hardwareCursor,
|
|
145
152
|
};
|
|
153
|
+
const httpIdleTimeoutMs = runtime.services.settingsManager?.getHttpIdleTimeoutMs?.();
|
|
154
|
+
if (typeof httpIdleTimeoutMs === "number")
|
|
155
|
+
this.#engineHost.httpPolicyLoaded(httpIdleTimeoutMs, this.#sessionId);
|
|
146
156
|
},
|
|
147
157
|
rebindBlocked: () => this.#delivery.overloaded || this.#admissionStopped || this.#disposed,
|
|
148
158
|
sessionReplacing: () => { this.#commands.cancelPending(["new-session", "resume-session"]); },
|
|
@@ -203,6 +213,7 @@ export class PiEngineAdapter {
|
|
|
203
213
|
runtime: () => this.#engine.runtime,
|
|
204
214
|
requireSession: () => this.#requireWorkflowSession(),
|
|
205
215
|
thinkingLevelChanged: level => { this.#thinkingLevel = level; this.#emitView(); },
|
|
216
|
+
httpPolicyChanged: timeoutMs => { this.#engineHost.httpPolicyChanged(timeoutMs, this.#sessionId); },
|
|
206
217
|
emitView: () => { this.#emitView(); },
|
|
207
218
|
});
|
|
208
219
|
this.#suggestions = new PiPromptSuggestions({
|
|
@@ -212,7 +223,16 @@ export class PiEngineAdapter {
|
|
|
212
223
|
identity: () => ({ sessionId: this.#sessionId, sessionGeneration: this.#engine.generation, runSequence: this.#events.runSequence, responseSequence: this.#events.responseSequence }),
|
|
213
224
|
unavailable: () => this.#disposed || this.#delivery.overloaded || this.#admissionStopped,
|
|
214
225
|
});
|
|
215
|
-
|
|
226
|
+
this.#ports = this.#createPorts();
|
|
227
|
+
}
|
|
228
|
+
get identity() { return this.#ports.identity; }
|
|
229
|
+
get session() { return this.#ports.session; }
|
|
230
|
+
get workflows() { return this.#ports.workflows; }
|
|
231
|
+
get settings() { return this.#ports.settings; }
|
|
232
|
+
get catalog() { return this.#ports.catalog; }
|
|
233
|
+
get extensions() { return this.#ports.extensions; }
|
|
234
|
+
/** The Pi objects behind pinned selectors and renderers, for the session presenters owner only. */
|
|
235
|
+
presentationSource() { return this.#ports.presentation; }
|
|
216
236
|
setWorkflowInteractionHost(interaction) {
|
|
217
237
|
this.#workflowInteraction = interaction;
|
|
218
238
|
}
|
|
@@ -272,9 +292,16 @@ export class PiEngineAdapter {
|
|
|
272
292
|
this.#editor = { ...this.#editor, submitEnabled: true };
|
|
273
293
|
this.#emitEvent({ type: "session-lifecycle", lifecycle: "ready", reason: null });
|
|
274
294
|
this.#emitView();
|
|
275
|
-
void this.#engine.announcePackageUpdates();
|
|
276
295
|
return this.view();
|
|
277
296
|
}
|
|
297
|
+
/** Announce pinned Pi's changelog since the profile's last seen version; the host calls this once per process. */
|
|
298
|
+
announceStartupChangelog() {
|
|
299
|
+
return this.#engine.announceChangelog();
|
|
300
|
+
}
|
|
301
|
+
/** Probe extension packages for updates and announce them; the host calls this once per process. */
|
|
302
|
+
announcePackageUpdates() {
|
|
303
|
+
return this.#engine.announcePackageUpdates();
|
|
304
|
+
}
|
|
278
305
|
onEvent(listener) {
|
|
279
306
|
return this.#delivery.subscribe(listener, this.#delivery.stamp({ type: "session-view", view: this.view() }));
|
|
280
307
|
}
|
|
@@ -311,18 +338,12 @@ export class PiEngineAdapter {
|
|
|
311
338
|
async cycleModelWorkflow(direction) {
|
|
312
339
|
return this.#workflows.cycleModelWorkflow(direction);
|
|
313
340
|
}
|
|
314
|
-
pinnedModelSelectorContext() {
|
|
315
|
-
return this.#contexts.pinnedModelSelectorContext();
|
|
316
|
-
}
|
|
317
341
|
pinnedProjectTrustContext() {
|
|
318
342
|
return this.#contexts.pinnedProjectTrustContext();
|
|
319
343
|
}
|
|
320
344
|
persistProjectTrust(updates) {
|
|
321
345
|
this.#contexts.persistProjectTrust(updates);
|
|
322
346
|
}
|
|
323
|
-
pinnedSessionSelectorContext() {
|
|
324
|
-
return this.#contexts.pinnedSessionSelectorContext();
|
|
325
|
-
}
|
|
326
347
|
pinnedScopedModelsContext() {
|
|
327
348
|
return this.#contexts.pinnedScopedModelsContext();
|
|
328
349
|
}
|
|
@@ -362,9 +383,6 @@ export class PiEngineAdapter {
|
|
|
362
383
|
pinnedForkOptions() {
|
|
363
384
|
return this.#contexts.pinnedForkOptions();
|
|
364
385
|
}
|
|
365
|
-
pinnedTreeSelectorContext() {
|
|
366
|
-
return this.#contexts.pinnedTreeSelectorContext();
|
|
367
|
-
}
|
|
368
386
|
/** Bind the owned UI's clipboard lifecycle without changing the comparison host. True means acknowledged delivery. */
|
|
369
387
|
bindClipboardWriter(writer) {
|
|
370
388
|
return this.#workflows.bindClipboardWriter(writer);
|
|
@@ -414,17 +432,14 @@ export class PiEngineAdapter {
|
|
|
414
432
|
pinnedSettingsSnapshot() {
|
|
415
433
|
return this.#settings.pinnedSettingsSnapshot();
|
|
416
434
|
}
|
|
417
|
-
|
|
418
|
-
return this.#settings.applyPinnedSettingValue(callback, value);
|
|
419
|
-
}
|
|
420
|
-
pinnedMessageRenderer(customType) {
|
|
435
|
+
#pinnedMessageRenderer(customType) {
|
|
421
436
|
return this.#requireWorkflowSession().extensionRunner?.getMessageRenderer?.(customType);
|
|
422
437
|
}
|
|
423
|
-
pinnedShortcutDescriptions(bindings) {
|
|
438
|
+
#pinnedShortcutDescriptions(bindings) {
|
|
424
439
|
const shortcuts = this.#requireWorkflowSession().extensionRunner?.getShortcuts?.(bindings);
|
|
425
440
|
return shortcuts === undefined ? [] : [...shortcuts].map(([key, shortcut]) => ({ key, description: shortcut.description ?? shortcut.extensionPath }));
|
|
426
441
|
}
|
|
427
|
-
pinnedToolRenderers(toolName) {
|
|
442
|
+
#pinnedToolRenderers(toolName) {
|
|
428
443
|
const runner = this.#requireWorkflowSession().extensionRunner;
|
|
429
444
|
if (runner === undefined)
|
|
430
445
|
return undefined;
|
|
@@ -516,6 +531,99 @@ export class PiEngineAdapter {
|
|
|
516
531
|
throw error;
|
|
517
532
|
}
|
|
518
533
|
}
|
|
534
|
+
// Invariant: every sub-port member delegates at call time, so ports built once follow session replacement.
|
|
535
|
+
#createPorts() {
|
|
536
|
+
const engine = this.#engine;
|
|
537
|
+
const contexts = this.#contexts;
|
|
538
|
+
const workflows = this.#workflows;
|
|
539
|
+
const settings = this.#settings;
|
|
540
|
+
const resources = this.#resources;
|
|
541
|
+
const extensions = this.#extensions;
|
|
542
|
+
const isDisposed = () => this.#disposed;
|
|
543
|
+
const sessionId = this.#sessionId;
|
|
544
|
+
const agentDir = this.#agentDir;
|
|
545
|
+
return {
|
|
546
|
+
identity: {
|
|
547
|
+
sessionId,
|
|
548
|
+
agentDir,
|
|
549
|
+
get cwd() { return engine.cwd; },
|
|
550
|
+
get sessionGeneration() { return engine.generation; },
|
|
551
|
+
get sessionBindingGeneration() { return engine.bindingGeneration; },
|
|
552
|
+
get disposed() { return isDisposed(); },
|
|
553
|
+
currentSessionResumeMetadata: () => engine.currentSessionResumeMetadata(),
|
|
554
|
+
},
|
|
555
|
+
session: {
|
|
556
|
+
start: () => this.start(),
|
|
557
|
+
view: () => this.view(),
|
|
558
|
+
snapshot: () => this.snapshot(),
|
|
559
|
+
onEvent: listener => this.onEvent(listener),
|
|
560
|
+
execute: command => this.execute(command),
|
|
561
|
+
flushEvents: () => this.flushEvents(),
|
|
562
|
+
dispose: () => this.dispose(),
|
|
563
|
+
},
|
|
564
|
+
workflows: {
|
|
565
|
+
executeWorkflow: request => this.executeWorkflow(request),
|
|
566
|
+
executeBashWorkflow: (command, excludeFromContext) => workflows.executeBashWorkflow(command, excludeFromContext),
|
|
567
|
+
cycleModelWorkflow: direction => workflows.cycleModelWorkflow(direction),
|
|
568
|
+
workflowAutocompleteCommands: () => resources.workflowAutocompleteCommands(),
|
|
569
|
+
clearQueuedWorkflows: () => this.clearQueuedWorkflows(),
|
|
570
|
+
reloadBlockedResult: () => workflows.reloadBlockedResult(),
|
|
571
|
+
copyWorkflowText: text => workflows.copyWorkflowText(text),
|
|
572
|
+
setWorkflowInteractionHost: interaction => { this.setWorkflowInteractionHost(interaction); },
|
|
573
|
+
},
|
|
574
|
+
settings: {
|
|
575
|
+
get productMode() { return settings.productMode; },
|
|
576
|
+
snapshot: () => {
|
|
577
|
+
// Invariant: the selector-only model values travel on the presentation source, not in the neutral snapshot.
|
|
578
|
+
const { currentModel: _currentModel, availableDefaultModels: _availableDefaultModels, ...snapshot } = settings.pinnedSettingsSnapshot();
|
|
579
|
+
return snapshot;
|
|
580
|
+
},
|
|
581
|
+
bindOwner: (owner, handlers) => settings.bindSettingsOwner(owner, handlers),
|
|
582
|
+
setDefaultThinkingLevel: level => { settings.setDefaultThinkingLevel(level); },
|
|
583
|
+
configuredTheme: () => settings.configuredTheme(),
|
|
584
|
+
},
|
|
585
|
+
catalog: {
|
|
586
|
+
modelsContext: () => contexts.modelsContext(),
|
|
587
|
+
setSessionModelScope: scopeIds => { contexts.setSessionModelScope(scopeIds); },
|
|
588
|
+
persistModelScope: scopeIds => { contexts.persistModelScope(scopeIds); },
|
|
589
|
+
refreshModels: signal => contexts.refreshModels(signal),
|
|
590
|
+
pinnedScopedModelsContext: () => contexts.pinnedScopedModelsContext(),
|
|
591
|
+
updateScopedModels: enabledModelIds => { contexts.updateScopedModels(enabledModelIds); },
|
|
592
|
+
persistScopedModels: enabledModelIds => { contexts.persistScopedModels(enabledModelIds); },
|
|
593
|
+
refreshScopedModels: signal => contexts.refreshScopedModels(signal),
|
|
594
|
+
pinnedProjectTrustContext: () => contexts.pinnedProjectTrustContext(),
|
|
595
|
+
persistProjectTrust: updates => { contexts.persistProjectTrust(updates); },
|
|
596
|
+
pinnedLoginOptions: authType => contexts.loginOptions(authType),
|
|
597
|
+
pinnedLoginMethodOptions: providerReference => contexts.pinnedLoginMethodOptions(providerReference),
|
|
598
|
+
pinnedAmbientAuthentication: selection => contexts.pinnedAmbientAuthentication(selection),
|
|
599
|
+
pinnedLogoutOptions: () => contexts.logoutOptions(),
|
|
600
|
+
pinnedForkOptions: () => contexts.pinnedForkOptions(),
|
|
601
|
+
},
|
|
602
|
+
extensions: {
|
|
603
|
+
nonVisualResources: () => resources.nonVisualResources(),
|
|
604
|
+
extensionResources: () => resources.extensionResources(),
|
|
605
|
+
resolveTranscriptImage: assetId => this.resolveTranscriptImage(assetId),
|
|
606
|
+
visualExtensionSupport: () => extensions.support(),
|
|
607
|
+
bindExtensionUi: (ui, shutdown) => extensions.bind(ui, shutdown),
|
|
608
|
+
unbindExtensionUi: () => extensions.unbind(),
|
|
609
|
+
bindClipboardWriter: writer => workflows.bindClipboardWriter(writer),
|
|
610
|
+
announceReleaseUpdate: release => { this.announceReleaseUpdate(release); },
|
|
611
|
+
},
|
|
612
|
+
presentation: {
|
|
613
|
+
pinnedModelSelectorContext: () => contexts.pinnedModelSelectorContext(),
|
|
614
|
+
pinnedSessionSelectorContext: () => contexts.pinnedSessionSelectorContext(),
|
|
615
|
+
pinnedTreeSelectorContext: () => contexts.pinnedTreeSelectorContext(),
|
|
616
|
+
pinnedMessageRenderer: customType => this.#pinnedMessageRenderer(customType),
|
|
617
|
+
pinnedToolRenderers: toolName => this.#pinnedToolRenderers(toolName),
|
|
618
|
+
pinnedShortcutDescriptions: bindings => this.#pinnedShortcutDescriptions(bindings),
|
|
619
|
+
pinnedSettingsModels: () => {
|
|
620
|
+
const { currentModel, availableDefaultModels } = settings.pinnedSettingsSnapshot();
|
|
621
|
+
return { ...(currentModel === undefined ? {} : { currentModel }), availableDefaultModels };
|
|
622
|
+
},
|
|
623
|
+
applyPinnedSettingValue: (callback, value) => settings.applyPinnedSettingValue(callback, value),
|
|
624
|
+
},
|
|
625
|
+
};
|
|
626
|
+
}
|
|
519
627
|
#requireWorkflowSession() {
|
|
520
628
|
if (this.#disposed || !this.#engine.runtime || !this.#engine.session)
|
|
521
629
|
throw new Error("engine adapter is not running");
|
|
@@ -704,7 +812,7 @@ export class PiEngineAdapter {
|
|
|
704
812
|
return diagnostic;
|
|
705
813
|
}
|
|
706
814
|
}
|
|
707
|
-
export async function createPiEngineAdapter(options
|
|
815
|
+
export async function createPiEngineAdapter(options) {
|
|
708
816
|
const adapter = new PiEngineAdapter(options);
|
|
709
817
|
await adapter.start();
|
|
710
818
|
return adapter;
|
|
@@ -1,9 +1,6 @@
|
|
|
1
|
-
import { type OwnedUiCommand, type
|
|
1
|
+
import { type OwnedUiCommand, type OwnedUiCommandResult, type OwnedUiDiagnostics } from "../../../contracts/owned-ui/index.js";
|
|
2
2
|
import type { PiEmittedEvent } from "./event-delivery.js";
|
|
3
|
-
export
|
|
4
|
-
readonly outcome: OwnedUiCommandOutcome;
|
|
5
|
-
readonly diagnostic: string | null;
|
|
6
|
-
}
|
|
3
|
+
export type AdapterCommandResult = OwnedUiCommandResult;
|
|
7
4
|
export interface PiCommandDispatchPorts {
|
|
8
5
|
sessionId(): string;
|
|
9
6
|
/** True before the runtime and session exist or after disposal: commands are rejected, not queued. */
|
|
@@ -1,15 +1,6 @@
|
|
|
1
1
|
import type { AgentSession } from "../startup-public.js";
|
|
2
|
-
import {
|
|
3
|
-
export
|
|
4
|
-
readonly available: boolean;
|
|
5
|
-
readonly contractComplete: true;
|
|
6
|
-
readonly contractVersion: typeof OWNED_UI_EXTENSION_CONTRACT_VERSION;
|
|
7
|
-
readonly binding: "bound" | "unbound";
|
|
8
|
-
readonly uiCallbacks: typeof OWNED_UI_EXTENSION_UI_CALLBACKS;
|
|
9
|
-
readonly uiProperties: typeof OWNED_UI_EXTENSION_UI_PROPERTIES;
|
|
10
|
-
readonly renderCallbacks: typeof OWNED_UI_EXTENSION_RENDER_CALLBACKS;
|
|
11
|
-
readonly diagnostic: string;
|
|
12
|
-
}
|
|
2
|
+
import { type OwnedUiDiagnostics, type OwnedUiVisualExtensionSupport } from "../../../contracts/owned-ui/index.js";
|
|
3
|
+
export type OwnedPiVisualExtensionSupport = OwnedUiVisualExtensionSupport;
|
|
13
4
|
export interface PiExtensionUiBindingPorts {
|
|
14
5
|
session(): AgentSession | undefined;
|
|
15
6
|
diagnostic(severity: OwnedUiDiagnostics["severity"], code: string, message: string, recoverable: boolean): void;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { type StartupPhase } from "../../../foundation/startup/startup-runtime.js";
|
|
2
|
+
/**
|
|
3
|
+
* What one engine session may ask of the process-level host that created it. The host owns
|
|
4
|
+
* everything process-wide; a session only reports what it learned and reads the host's signal.
|
|
5
|
+
*/
|
|
6
|
+
export interface PiEngineHostSessionPorts {
|
|
7
|
+
/** Aborted when the host is disposed; host-level timers and probes stop with it. */
|
|
8
|
+
readonly signal: AbortSignal;
|
|
9
|
+
/** Record a startup trace phase; the host records each phase once per process. */
|
|
10
|
+
markStartupPhase(phase: StartupPhase): Promise<void>;
|
|
11
|
+
/** A session's runtime loaded the profile's HTTP idle timeout; the host installs the dispatcher once. */
|
|
12
|
+
httpPolicyLoaded(timeoutMs: number, sessionId: string): void;
|
|
13
|
+
/** A session wrote the HTTP idle timeout setting; the host re-installs the dispatcher for the process. */
|
|
14
|
+
httpPolicyChanged(timeoutMs: number, sessionId: string): void;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* The ports of an adapter built without a host: the signal never fires, phases trace as before, and
|
|
18
|
+
* no process dispatcher is installed, because only the host owns that.
|
|
19
|
+
*/
|
|
20
|
+
export declare function detachedEngineHostPorts(): PiEngineHostSessionPorts;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { markStartupPhase } from "../../../foundation/startup/startup-runtime.js";
|
|
2
|
+
/**
|
|
3
|
+
* The ports of an adapter built without a host: the signal never fires, phases trace as before, and
|
|
4
|
+
* no process dispatcher is installed, because only the host owns that.
|
|
5
|
+
*/
|
|
6
|
+
export function detachedEngineHostPorts() {
|
|
7
|
+
return {
|
|
8
|
+
signal: new AbortController().signal,
|
|
9
|
+
markStartupPhase: phase => markStartupPhase(process.env, phase),
|
|
10
|
+
httpPolicyLoaded() { },
|
|
11
|
+
httpPolicyChanged() { },
|
|
12
|
+
};
|
|
13
|
+
}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import { PiEngineAdapter } from "./adapter.js";
|
|
2
|
+
import { type StartupPhase } from "../../../foundation/startup/startup-runtime.js";
|
|
3
|
+
import type { PiEnginePackageUpdateProbe, PiEngineRuntimeFactory, PiRepositoryContextReader } from "./session-runtime.js";
|
|
4
|
+
import type { PiProjectTrustPreflightPrompt } from "./project-trust-preflight.js";
|
|
5
|
+
import type { PiSessionForkPrompt, PiSessionSelection } from "./session-selection.js";
|
|
6
|
+
import type { PiWorkflowHost } from "./workflows.js";
|
|
7
|
+
import type { OwnedUiSessionFactory, OwnedUiSessionRequest, UiAccentColor } from "../../../contracts/owned-ui/index.js";
|
|
8
|
+
/** The theme singletons the host applies. Composition supplies them so the engine owns no presentation module. */
|
|
9
|
+
export interface PiEngineHostThemeApplier {
|
|
10
|
+
/** Apply the base theme in the engine's grammar: a theme name, or a `light/dark` pair meaning "follow the terminal". */
|
|
11
|
+
base(setting: string | undefined): void;
|
|
12
|
+
accentColor(color: UiAccentColor): void;
|
|
13
|
+
packageBorderProjection(enabled: boolean): void;
|
|
14
|
+
}
|
|
15
|
+
export interface PiEngineHostTheme {
|
|
16
|
+
/** `dark` pins bare A1's one base; `engine-configured` follows the theme the first session is configured with. */
|
|
17
|
+
readonly base: "dark" | "engine-configured";
|
|
18
|
+
readonly accentColor: UiAccentColor;
|
|
19
|
+
readonly packageBorderProjection: boolean;
|
|
20
|
+
readonly apply: PiEngineHostThemeApplier;
|
|
21
|
+
}
|
|
22
|
+
export interface PiEngineHostOptions {
|
|
23
|
+
readonly productMode: "bare" | "comparison";
|
|
24
|
+
readonly theme: PiEngineHostTheme;
|
|
25
|
+
/** Themes installed on this machine, listed by the component adapter that owns the theme unit. */
|
|
26
|
+
readonly availableThemes?: () => readonly string[];
|
|
27
|
+
/** Comparison profiles preserve Pi's startup changelog; bare A1 owns release-note startup. Defaults to on. */
|
|
28
|
+
readonly announceStartupChangelog?: boolean;
|
|
29
|
+
readonly projectTrustPrompt?: PiProjectTrustPreflightPrompt;
|
|
30
|
+
readonly checkPackageUpdates?: PiEnginePackageUpdateProbe;
|
|
31
|
+
readonly workflowHost?: PiWorkflowHost;
|
|
32
|
+
readonly createRuntime?: PiEngineRuntimeFactory;
|
|
33
|
+
/** Installs the process HTTP dispatcher; defaults to the owned undici seam. */
|
|
34
|
+
readonly installHttpDispatcher?: (timeoutMs: number) => void;
|
|
35
|
+
/** Records one startup trace phase; defaults to the process startup trace. */
|
|
36
|
+
readonly markStartupPhase?: (phase: StartupPhase) => Promise<void>;
|
|
37
|
+
}
|
|
38
|
+
/** A session request as the Pi host takes it: the neutral request plus how the Pi session is opened. */
|
|
39
|
+
export interface PiEngineSessionRequest extends OwnedUiSessionRequest {
|
|
40
|
+
readonly sessionPath?: string;
|
|
41
|
+
readonly sessionSelection?: PiSessionSelection;
|
|
42
|
+
readonly sessionForkPrompt?: PiSessionForkPrompt;
|
|
43
|
+
readonly repositoryContextReader?: PiRepositoryContextReader;
|
|
44
|
+
}
|
|
45
|
+
/** The dispatcher policy in force for the process and the session that put it there. */
|
|
46
|
+
export interface PiEngineHttpPolicy {
|
|
47
|
+
readonly timeoutMs: number;
|
|
48
|
+
readonly sessionId: string;
|
|
49
|
+
readonly origin: "startup" | "setting";
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* The process-level owner of everything in the engine integration that is process-wide: the undici
|
|
53
|
+
* dispatcher, the theme singletons, the one-time changelog and package-update announcements, and
|
|
54
|
+
* the startup trace. Sessions come only from `create`, so their ids are unique per process.
|
|
55
|
+
*/
|
|
56
|
+
export interface PiEngineHost extends OwnedUiSessionFactory {
|
|
57
|
+
/** Aborted on disposal; every host-level timer and probe stops with it. */
|
|
58
|
+
readonly signal: AbortSignal;
|
|
59
|
+
readonly disposed: boolean;
|
|
60
|
+
create(request: PiEngineSessionRequest): Promise<PiEngineAdapter>;
|
|
61
|
+
/** Ids of the sessions this host created that are not yet disposed. */
|
|
62
|
+
liveSessionIds(): readonly string[];
|
|
63
|
+
/** The dispatcher policy in force, or null before any session loaded one. */
|
|
64
|
+
httpPolicy(): PiEngineHttpPolicy | null;
|
|
65
|
+
/** Re-apply the owned accent; the live setting change from composition lands here. */
|
|
66
|
+
setAccentColor(color: UiAccentColor): void;
|
|
67
|
+
/** Abort the signal and dispose every session still live. */
|
|
68
|
+
dispose(): Promise<void>;
|
|
69
|
+
}
|
|
70
|
+
export declare function createPiEngineHost(options: PiEngineHostOptions): PiEngineHost;
|
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
import { PiEngineAdapter } from "./adapter.js";
|
|
2
|
+
import { configureOwnedHttpDispatcher } from "./http-dispatcher.js";
|
|
3
|
+
import { markStartupPhase } from "../../../foundation/startup/startup-runtime.js";
|
|
4
|
+
export function createPiEngineHost(options) {
|
|
5
|
+
return new ProcessPiEngineHost(options);
|
|
6
|
+
}
|
|
7
|
+
const SESSION_ID_PREFIX = "owned-session-";
|
|
8
|
+
class ProcessPiEngineHost {
|
|
9
|
+
#options;
|
|
10
|
+
#abort = new AbortController();
|
|
11
|
+
#sessions = new Map();
|
|
12
|
+
#tracedPhases = new Set();
|
|
13
|
+
#sessionPorts;
|
|
14
|
+
#installHttpDispatcher;
|
|
15
|
+
#markStartupPhase;
|
|
16
|
+
#accentColor;
|
|
17
|
+
#nextSessionNumber = 1;
|
|
18
|
+
#httpPolicy = null;
|
|
19
|
+
#themeApplied = false;
|
|
20
|
+
#announced = false;
|
|
21
|
+
#disposed = false;
|
|
22
|
+
constructor(options) {
|
|
23
|
+
this.#options = options;
|
|
24
|
+
this.#accentColor = options.theme.accentColor;
|
|
25
|
+
this.#installHttpDispatcher = options.installHttpDispatcher ?? configureOwnedHttpDispatcher;
|
|
26
|
+
this.#markStartupPhase = options.markStartupPhase ?? (phase => markStartupPhase(process.env, phase));
|
|
27
|
+
this.#sessionPorts = {
|
|
28
|
+
signal: this.#abort.signal,
|
|
29
|
+
markStartupPhase: phase => this.#tracePhase(phase),
|
|
30
|
+
httpPolicyLoaded: (timeoutMs, sessionId) => { this.#applyHttpPolicy(timeoutMs, sessionId, "startup"); },
|
|
31
|
+
httpPolicyChanged: (timeoutMs, sessionId) => { this.#applyHttpPolicy(timeoutMs, sessionId, "setting"); },
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
get signal() {
|
|
35
|
+
return this.#abort.signal;
|
|
36
|
+
}
|
|
37
|
+
get disposed() {
|
|
38
|
+
return this.#disposed;
|
|
39
|
+
}
|
|
40
|
+
liveSessionIds() {
|
|
41
|
+
this.#forgetDisposedSessions();
|
|
42
|
+
return [...this.#sessions.keys()];
|
|
43
|
+
}
|
|
44
|
+
httpPolicy() {
|
|
45
|
+
return this.#httpPolicy;
|
|
46
|
+
}
|
|
47
|
+
setAccentColor(color) {
|
|
48
|
+
this.#accentColor = color;
|
|
49
|
+
if (this.#themeApplied)
|
|
50
|
+
this.#options.theme.apply.accentColor(color);
|
|
51
|
+
}
|
|
52
|
+
async create(request) {
|
|
53
|
+
if (this.#disposed)
|
|
54
|
+
throw new Error("engine host is disposed");
|
|
55
|
+
const sessionId = this.#claimSessionId(request.sessionId);
|
|
56
|
+
const options = this.#options;
|
|
57
|
+
const adapter = new PiEngineAdapter({
|
|
58
|
+
cwd: request.cwd,
|
|
59
|
+
sessionId,
|
|
60
|
+
engineHost: this.#sessionPorts,
|
|
61
|
+
settingsProductMode: options.productMode,
|
|
62
|
+
...(options.availableThemes === undefined ? {} : { availableThemes: options.availableThemes }),
|
|
63
|
+
...(options.projectTrustPrompt === undefined ? {} : { projectTrustPrompt: options.projectTrustPrompt }),
|
|
64
|
+
...(options.checkPackageUpdates === undefined ? {} : { checkPackageUpdates: options.checkPackageUpdates }),
|
|
65
|
+
...(options.workflowHost === undefined ? {} : { workflowHost: options.workflowHost }),
|
|
66
|
+
...(options.createRuntime === undefined ? {} : { createRuntime: options.createRuntime }),
|
|
67
|
+
...(request.sessionPath === undefined ? {} : { sessionPath: request.sessionPath }),
|
|
68
|
+
...(request.sessionSelection === undefined ? {} : { sessionSelection: request.sessionSelection }),
|
|
69
|
+
...(request.sessionForkPrompt === undefined ? {} : { sessionForkPrompt: request.sessionForkPrompt }),
|
|
70
|
+
...(request.repositoryContextReader === undefined ? {} : { repositoryContextReader: request.repositoryContextReader }),
|
|
71
|
+
});
|
|
72
|
+
this.#sessions.set(sessionId, adapter);
|
|
73
|
+
try {
|
|
74
|
+
await adapter.start();
|
|
75
|
+
}
|
|
76
|
+
catch (error) {
|
|
77
|
+
this.#sessions.delete(sessionId);
|
|
78
|
+
throw error;
|
|
79
|
+
}
|
|
80
|
+
this.#applyThemeOnce(adapter);
|
|
81
|
+
await this.#announceOnce(adapter);
|
|
82
|
+
return adapter;
|
|
83
|
+
}
|
|
84
|
+
async dispose() {
|
|
85
|
+
if (this.#disposed)
|
|
86
|
+
return;
|
|
87
|
+
this.#disposed = true;
|
|
88
|
+
this.#abort.abort();
|
|
89
|
+
const live = [...this.#sessions.values()].filter(session => !session.disposed);
|
|
90
|
+
this.#sessions.clear();
|
|
91
|
+
await Promise.all(live.map(session => session.dispose()));
|
|
92
|
+
}
|
|
93
|
+
// Invariant: an id names one live session; a disposed session's id may be reused by a caller, never by generation.
|
|
94
|
+
#claimSessionId(requested) {
|
|
95
|
+
this.#forgetDisposedSessions();
|
|
96
|
+
if (requested !== undefined) {
|
|
97
|
+
if (requested.length === 0)
|
|
98
|
+
throw new TypeError("engine session id is required");
|
|
99
|
+
if (this.#sessions.has(requested))
|
|
100
|
+
throw new Error(`engine session id is already live: ${requested}`);
|
|
101
|
+
return requested;
|
|
102
|
+
}
|
|
103
|
+
let candidate = `${SESSION_ID_PREFIX}${this.#nextSessionNumber++}`;
|
|
104
|
+
while (this.#sessions.has(candidate))
|
|
105
|
+
candidate = `${SESSION_ID_PREFIX}${this.#nextSessionNumber++}`;
|
|
106
|
+
return candidate;
|
|
107
|
+
}
|
|
108
|
+
#forgetDisposedSessions() {
|
|
109
|
+
for (const [sessionId, session] of this.#sessions)
|
|
110
|
+
if (session.disposed)
|
|
111
|
+
this.#sessions.delete(sessionId);
|
|
112
|
+
}
|
|
113
|
+
// Rationale: the profile's timeout is installed once, by whichever session loads it first; a written
|
|
114
|
+
// setting re-installs from any session because the dispatcher is process-wide either way.
|
|
115
|
+
#applyHttpPolicy(timeoutMs, sessionId, origin) {
|
|
116
|
+
if (this.#disposed || (origin === "startup" && this.#httpPolicy !== null))
|
|
117
|
+
return;
|
|
118
|
+
this.#installHttpDispatcher(timeoutMs);
|
|
119
|
+
this.#httpPolicy = { timeoutMs, sessionId, origin };
|
|
120
|
+
}
|
|
121
|
+
async #tracePhase(phase) {
|
|
122
|
+
if (this.#tracedPhases.has(phase))
|
|
123
|
+
return;
|
|
124
|
+
this.#tracedPhases.add(phase);
|
|
125
|
+
await this.#markStartupPhase(phase);
|
|
126
|
+
}
|
|
127
|
+
// Compatibility: bare A1 ships one base visual target while its UI is being completed: dark, regardless
|
|
128
|
+
// of terminal detection or a stored Pi theme, with its owned accent projected over it. Comparison keeps
|
|
129
|
+
// Pi's configured theme and unmodified semantic accent. The base is read from the first session.
|
|
130
|
+
#applyThemeOnce(adapter) {
|
|
131
|
+
if (this.#themeApplied)
|
|
132
|
+
return;
|
|
133
|
+
this.#themeApplied = true;
|
|
134
|
+
const theme = this.#options.theme;
|
|
135
|
+
theme.apply.packageBorderProjection(theme.packageBorderProjection);
|
|
136
|
+
theme.apply.accentColor(this.#accentColor);
|
|
137
|
+
theme.apply.base(theme.base === "dark" ? "dark" : adapter.configuredTheme());
|
|
138
|
+
}
|
|
139
|
+
async #announceOnce(adapter) {
|
|
140
|
+
if (this.#announced)
|
|
141
|
+
return;
|
|
142
|
+
this.#announced = true;
|
|
143
|
+
if (this.#options.announceStartupChangelog !== false)
|
|
144
|
+
await adapter.announceStartupChangelog();
|
|
145
|
+
void adapter.announcePackageUpdates();
|
|
146
|
+
}
|
|
147
|
+
}
|
|
@@ -1,11 +1,15 @@
|
|
|
1
1
|
export { EngineDeliveryError, PiEngineAdapter, createPiEngineAdapter } from "./adapter.js";
|
|
2
|
-
export type { AdapterCommandResult, OwnedPiExtensionResourceSummary, OwnedPiExtensionSourceSummary, OwnedPiResourceSummary, OwnedPiVisualExtensionSupport, PiEngineAdapterOptions, PiEngineRuntimeFactory, PiEngineRuntimeFactoryInput, } from "./adapter.js";
|
|
2
|
+
export type { AdapterCommandResult, OwnedPiExtensionResourceSummary, OwnedPiExtensionSourceSummary, OwnedPiResourceSummary, OwnedPiVisualExtensionSupport, PiEngineAdapterOptions, PiEngineRuntimeFactory, PiEngineRuntimeFactoryInput, PiSessionPresentationSource, } from "./adapter.js";
|
|
3
|
+
export { createPiEngineHost } from "./host.js";
|
|
4
|
+
export type { PiEngineHost, PiEngineHostOptions, PiEngineHostTheme, PiEngineHostThemeApplier, PiEngineHttpPolicy, PiEngineSessionRequest, } from "./host.js";
|
|
5
|
+
export { detachedEngineHostPorts } from "./host-ports.js";
|
|
6
|
+
export type { PiEngineHostSessionPorts } from "./host-ports.js";
|
|
3
7
|
export { bindPiRuntimeSession, createPiRuntimeIntegration, createPiRuntimeServicesAfterTrust, disposePiRuntimeIntegration, replacePiRuntimeSession, resolveConfiguredModelScope, } from "./runtime-integration.js";
|
|
4
|
-
export type { PiRuntimeIntegrationOptions, PiRuntimePreflightDependencies, PiSessionReplacement } from "./runtime-integration.js";
|
|
8
|
+
export type { PiRuntimeIntegrationOptions, PiRuntimePreflightDependencies, PiSessionReplacement, PiStartupPhaseMarker } from "./runtime-integration.js";
|
|
5
9
|
export { PiSessionSelectionError, openSelectedPiSession, resolveSessionArgumentPath } from "./session-selection.js";
|
|
6
10
|
export type { PiSessionForkPrompt, PiSessionSelection } from "./session-selection.js";
|
|
7
|
-
export { PiSessionCommandIntegration
|
|
8
|
-
export type { PiDocumentedSessionCommands,
|
|
11
|
+
export { PiSessionCommandIntegration } from "./session-integration.js";
|
|
12
|
+
export type { PiDocumentedSessionCommands, PiSessionCommand, PiSessionCommandResult } from "./session-integration.js";
|
|
9
13
|
export { AUTOMATIC_THEME, EXPOSED_SETTING_KEYS, PI_SETTING_EFFECTS, PiSettingsBridge, PiSettingsCoordinator, parseAutomaticTheme, settingsEffectInventoryDrift, settingsInventoryDrift, settingsVisualInventoryViolations, } from "./settings-bridge.js";
|
|
10
14
|
export { assertPiSettingsMetadata, loadPiSettingsMetadata, PI_SETTINGS_METADATA_FILE } from "./settings-metadata.js";
|
|
11
15
|
export type { PiSettingBounds, PiSettingPresentation, PiSettingsMetadata } from "./settings-metadata.js";
|
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
export { EngineDeliveryError, PiEngineAdapter, createPiEngineAdapter } from "./adapter.js";
|
|
2
|
+
export { createPiEngineHost } from "./host.js";
|
|
3
|
+
export { detachedEngineHostPorts } from "./host-ports.js";
|
|
2
4
|
export { bindPiRuntimeSession, createPiRuntimeIntegration, createPiRuntimeServicesAfterTrust, disposePiRuntimeIntegration, replacePiRuntimeSession, resolveConfiguredModelScope, } from "./runtime-integration.js";
|
|
3
5
|
export { PiSessionSelectionError, openSelectedPiSession, resolveSessionArgumentPath } from "./session-selection.js";
|
|
4
|
-
export { PiSessionCommandIntegration
|
|
6
|
+
export { PiSessionCommandIntegration } from "./session-integration.js";
|
|
5
7
|
export { AUTOMATIC_THEME, EXPOSED_SETTING_KEYS, PI_SETTING_EFFECTS, PiSettingsBridge, PiSettingsCoordinator, parseAutomaticTheme, settingsEffectInventoryDrift, settingsInventoryDrift, settingsVisualInventoryViolations, } from "./settings-bridge.js";
|
|
6
8
|
export { assertPiSettingsMetadata, loadPiSettingsMetadata, PI_SETTINGS_METADATA_FILE } from "./settings-metadata.js";
|
|
7
9
|
export { resolvePiProjectTrustPreflight } from "./project-trust-preflight.js";
|
|
@@ -149,7 +149,7 @@
|
|
|
149
149
|
},
|
|
150
150
|
"outputPad": {
|
|
151
151
|
"label": "Output padding",
|
|
152
|
-
"description": "Horizontal padding for
|
|
152
|
+
"description": "Horizontal padding for messages, tool output, and command output",
|
|
153
153
|
"opensDialog": false,
|
|
154
154
|
"values": [
|
|
155
155
|
"0",
|
|
@@ -1,29 +1,10 @@
|
|
|
1
1
|
import type { AgentSession, AgentSessionRuntime } from "../startup-public.js";
|
|
2
|
+
import type { OwnedUiExtensionResourceSummary, OwnedUiExtensionSourceSummary, OwnedUiResourceSummary } from "../../../contracts/owned-ui/index.js";
|
|
2
3
|
import type { PiWorkflowContexts } from "./workflow-contexts.js";
|
|
3
4
|
import { type PiProductMode, type PiWorkflowAutocompleteCommand } from "./workflows.js";
|
|
4
|
-
export
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
readonly label: string;
|
|
8
|
-
readonly sourcePath: string | null;
|
|
9
|
-
readonly diagnostic: string | null;
|
|
10
|
-
}
|
|
11
|
-
export interface OwnedPiExtensionSourceSummary {
|
|
12
|
-
readonly source: string;
|
|
13
|
-
readonly scope: "user" | "project" | "temporary";
|
|
14
|
-
readonly origin: "package" | "top-level";
|
|
15
|
-
readonly baseDir: string | null;
|
|
16
|
-
}
|
|
17
|
-
export interface OwnedPiExtensionResourceSummary {
|
|
18
|
-
readonly kind: "extension";
|
|
19
|
-
readonly id: string;
|
|
20
|
-
readonly sourcePath: string | null;
|
|
21
|
-
readonly resolvedPath: string | null;
|
|
22
|
-
readonly sourceInfo: OwnedPiExtensionSourceSummary | null;
|
|
23
|
-
readonly loaded: boolean;
|
|
24
|
-
readonly hidden: boolean;
|
|
25
|
-
readonly diagnostic: string | null;
|
|
26
|
-
}
|
|
5
|
+
export type OwnedPiResourceSummary = OwnedUiResourceSummary;
|
|
6
|
+
export type OwnedPiExtensionSourceSummary = OwnedUiExtensionSourceSummary;
|
|
7
|
+
export type OwnedPiExtensionResourceSummary = OwnedUiExtensionResourceSummary;
|
|
27
8
|
export interface PiResourceCatalogPorts {
|
|
28
9
|
session(): AgentSession | undefined;
|
|
29
10
|
runtime(): AgentSessionRuntime | undefined;
|