@crouton-kit/crouter 0.3.70 → 0.3.79
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/README.md +1 -1
- package/dist/build-root.d.ts +12 -4
- package/dist/build-root.js +25 -6
- package/dist/builtin-memory/00-runtime-base.md +3 -10
- package/dist/builtin-memory/04-base-worker.md +18 -0
- package/dist/builtin-memory/04-orchestration-kernel.md +1 -1
- package/dist/builtin-memory/crouter-development/plugins.md +82 -5
- package/dist/builtin-pi-packages/pi-crtr-extensions/README.md +13 -34
- package/dist/builtin-pi-packages/pi-crtr-extensions/extensions/__tests__/provider-rotation.test.ts +1115 -1
- package/dist/builtin-pi-packages/pi-crtr-extensions/extensions/provider-rotation.ts +234 -71
- package/dist/builtin-pi-packages/pi-crtr-extensions/extensions/statusline.ts +2 -9
- package/dist/builtin-pi-packages/pi-crtr-extensions/lib/subscription-state.ts +2 -516
- package/dist/builtin-pi-packages/pi-crtr-extensions/package-lock.json +2 -2
- package/dist/builtin-pi-packages/pi-mode-switch/README.md +11 -39
- package/dist/builtin-pi-packages/pi-mode-switch/extensions/index.ts +20 -15
- package/dist/builtin-pi-packages/pi-mode-switch/package.json +1 -1
- package/dist/builtin-views/canvas/tui.mjs +8 -9
- package/dist/builtin-views/chat/tui.mjs +12 -12
- package/dist/builtin-views/git-pr/tui.mjs +7 -8
- package/dist/builtin-views/inbox/tui.mjs +27 -41
- package/dist/builtin-views/linkedin/tui.mjs +23 -37
- package/dist/builtin-views/prompt-review/tui.mjs +11 -11
- package/dist/builtin-views/settings/tui.mjs +11 -11
- package/dist/builtin-views/workspace-sidebar/tui.mjs +8 -9
- package/dist/clients/attach/__tests__/attach-chrome-remote.test.js +11 -6
- package/dist/clients/attach/__tests__/attach-keybindings.test.d.ts +1 -0
- package/dist/clients/attach/__tests__/attach-keybindings.test.js +113 -0
- package/dist/clients/attach/__tests__/crtr-output-render.test.js +1 -1
- package/dist/clients/attach/__tests__/mermaid-render.test.d.ts +1 -0
- package/dist/clients/attach/__tests__/mermaid-render.test.js +28 -0
- package/dist/clients/attach/__tests__/oauth-dialog-lifecycle.test.d.ts +1 -0
- package/dist/clients/attach/__tests__/oauth-dialog-lifecycle.test.js +110 -0
- package/dist/clients/attach/attach-cmd.d.ts +9 -1
- package/dist/clients/attach/attach-cmd.js +841 -792
- package/dist/clients/attach/auth-pickers.d.ts +0 -12
- package/dist/clients/attach/auth-pickers.js +64 -15
- package/dist/clients/attach/canvas-panels.js +2 -3
- package/dist/clients/attach/chat-view.d.ts +7 -8
- package/dist/clients/attach/chat-view.js +119 -79
- package/dist/clients/attach/edit-diff-render.d.ts +6 -0
- package/dist/clients/attach/edit-diff-render.js +263 -0
- package/dist/clients/attach/graph-overlay.d.ts +12 -2
- package/dist/clients/attach/graph-overlay.js +83 -33
- package/dist/clients/attach/input-controller.d.ts +28 -2
- package/dist/clients/attach/input-controller.js +38 -5
- package/dist/clients/attach/mermaid-render.js +5 -2
- package/dist/clients/attach/pickers.d.ts +8 -7
- package/dist/clients/attach/pickers.js +11 -17
- package/dist/clients/attach/slash-commands.d.ts +9 -0
- package/dist/clients/attach/slash-commands.js +127 -7
- package/dist/clients/attach/titled-editor.d.ts +12 -1
- package/dist/clients/attach/titled-editor.js +103 -8
- package/dist/commands/canvas-browse.js +2 -2
- package/dist/commands/human/queue.js +3 -4
- package/dist/commands/memory/lint.js +39 -5
- package/dist/commands/memory/write.js +1 -0
- package/dist/commands/node.js +9 -2
- package/dist/commands/pkg/plugin-inspect.js +22 -1
- package/dist/commands/pkg/plugin-manage.js +31 -9
- package/dist/commands/surface-tmux-spread.js +1 -3
- package/dist/commands/sys/__tests__/config-keybindings.test.d.ts +1 -0
- package/dist/commands/sys/__tests__/config-keybindings.test.js +55 -0
- package/dist/commands/sys/__tests__/config-model-ladders.test.d.ts +1 -0
- package/dist/commands/sys/__tests__/config-model-ladders.test.js +121 -0
- package/dist/commands/sys/__tests__/setup-core.test.js +158 -1
- package/dist/commands/sys/config.js +18 -21
- package/dist/commands/sys/doctor.js +42 -4
- package/dist/commands/sys/setup-core.d.ts +49 -1
- package/dist/commands/sys/setup-core.js +161 -4
- package/dist/commands/sys/setup.d.ts +88 -0
- package/dist/commands/sys/setup.js +943 -169
- package/dist/commands/view-pick.d.ts +4 -0
- package/dist/commands/view-pick.js +17 -7
- package/dist/core/__tests__/base-worker-prompt.test.d.ts +1 -0
- package/dist/core/__tests__/base-worker-prompt.test.js +24 -0
- package/dist/core/__tests__/canvas-inbox-watcher-hold.test.js +232 -1
- package/dist/core/__tests__/canvas-inbox-watcher.test.js +34 -9
- package/dist/core/__tests__/command-plugins-surfaces.test.d.ts +1 -0
- package/dist/core/__tests__/command-plugins-surfaces.test.js +298 -0
- package/dist/core/__tests__/command-plugins.test.d.ts +1 -0
- package/dist/core/__tests__/command-plugins.test.js +444 -0
- package/dist/core/__tests__/fault-classifier.test.js +15 -0
- package/dist/core/__tests__/fixtures/fake-engine.d.ts +6 -0
- package/dist/core/__tests__/fixtures/fake-engine.js +9 -1
- package/dist/core/__tests__/full/broker-dialogs.test.js +7 -2
- package/dist/core/__tests__/host-teardown-process-group.test.js +15 -4
- package/dist/core/__tests__/preview-registry-sync.test.js +30 -1
- package/dist/core/__tests__/scope-crouter-home-fence.test.d.ts +1 -0
- package/dist/core/__tests__/scope-crouter-home-fence.test.js +55 -0
- package/dist/core/__tests__/stream-watchdog.test.d.ts +1 -0
- package/dist/core/__tests__/stream-watchdog.test.js +70 -0
- package/dist/core/__tests__/tmux-surface.test.js +72 -0
- package/dist/core/canvas/browse/__tests__/model.test.js +23 -5
- package/dist/core/canvas/browse/__tests__/render.test.js +1 -0
- package/dist/core/canvas/browse/app.d.ts +6 -0
- package/dist/core/canvas/browse/app.js +230 -41
- package/dist/core/canvas/browse/model.d.ts +10 -6
- package/dist/core/canvas/browse/model.js +20 -12
- package/dist/core/canvas/browse/pins.d.ts +4 -0
- package/dist/core/canvas/browse/pins.js +29 -0
- package/dist/core/canvas/browse/render.d.ts +13 -1
- package/dist/core/canvas/browse/render.js +72 -15
- package/dist/core/canvas/nav-model.js +5 -11
- package/dist/core/canvas/paths.d.ts +5 -0
- package/dist/core/canvas/paths.js +7 -0
- package/dist/core/command-plugins/adapter.d.ts +15 -0
- package/dist/core/command-plugins/adapter.js +145 -0
- package/dist/core/command-plugins/compose.d.ts +5 -0
- package/dist/core/command-plugins/compose.js +56 -0
- package/dist/core/command-plugins/discovery.d.ts +104 -0
- package/dist/core/command-plugins/discovery.js +565 -0
- package/dist/core/config.d.ts +48 -0
- package/dist/core/config.js +228 -110
- package/dist/core/fault-classifier.js +1 -1
- package/dist/core/fs-utils.d.ts +1 -0
- package/dist/core/fs-utils.js +15 -1
- package/dist/core/keybindings/__tests__/bespoke-consumers.test.d.ts +1 -0
- package/dist/core/keybindings/__tests__/bespoke-consumers.test.js +40 -0
- package/dist/core/keybindings/__tests__/resolve.test.d.ts +1 -0
- package/dist/core/keybindings/__tests__/resolve.test.js +224 -0
- package/dist/core/keybindings/catalog.d.ts +14 -0
- package/dist/core/keybindings/catalog.js +257 -0
- package/dist/core/keybindings/index.d.ts +5 -0
- package/dist/core/keybindings/index.js +4 -0
- package/dist/core/keybindings/match.d.ts +29 -0
- package/dist/core/keybindings/match.js +99 -0
- package/dist/core/keybindings/persistence.d.ts +14 -0
- package/dist/core/keybindings/persistence.js +31 -0
- package/dist/core/keybindings/resolve.d.ts +14 -0
- package/dist/core/keybindings/resolve.js +305 -0
- package/dist/core/keybindings/types.d.ts +37 -0
- package/dist/core/keybindings/types.js +1 -0
- package/dist/core/memory-resolver.d.ts +1 -1
- package/dist/core/memory-resolver.js +10 -3
- package/dist/core/predicate.d.ts +5 -3
- package/dist/core/predicate.js +5 -3
- package/dist/core/profiles/select.d.ts +6 -0
- package/dist/core/profiles/select.js +86 -52
- package/dist/core/provider-management.d.ts +12 -0
- package/dist/core/provider-management.js +24 -0
- package/dist/core/runtime/broker-protocol.d.ts +33 -5
- package/dist/core/runtime/broker.js +164 -14
- package/dist/core/runtime/launch.d.ts +39 -6
- package/dist/core/runtime/launch.js +78 -20
- package/dist/core/runtime/naming.js +3 -3
- package/dist/core/runtime/pi-cli.d.ts +6 -0
- package/dist/core/runtime/pi-cli.js +16 -2
- package/dist/core/runtime/pi-vendored.d.ts +8 -0
- package/dist/core/runtime/pi-vendored.js +14 -0
- package/dist/core/runtime/placement.d.ts +2 -2
- package/dist/core/runtime/placement.js +4 -1
- package/dist/core/runtime/promote.js +4 -0
- package/dist/core/runtime/recap.d.ts +3 -3
- package/dist/core/runtime/recap.js +75 -47
- package/dist/core/runtime/recycle.js +6 -1
- package/dist/core/runtime/reset.js +5 -0
- package/dist/core/runtime/session-list-cache.d.ts +33 -0
- package/dist/core/runtime/session-list-cache.js +338 -0
- package/dist/core/runtime/spawn.js +52 -45
- package/dist/core/runtime/stream-watchdog.d.ts +26 -0
- package/dist/core/runtime/stream-watchdog.js +75 -0
- package/dist/core/runtime/tmux-chrome.d.ts +1 -1
- package/dist/core/runtime/tmux-chrome.js +2 -2
- package/dist/core/runtime/tmux.d.ts +18 -15
- package/dist/core/runtime/tmux.js +217 -110
- package/dist/core/scope.js +27 -4
- package/dist/core/subscription-state.d.ts +90 -0
- package/dist/core/subscription-state.js +762 -0
- package/dist/core/tui/__tests__/host-keybindings.test.d.ts +1 -0
- package/dist/core/tui/__tests__/host-keybindings.test.js +112 -0
- package/dist/core/tui/host.d.ts +30 -1
- package/dist/core/tui/host.js +148 -34
- package/dist/core/view/contract.d.ts +17 -3
- package/dist/daemon/crtrd.js +253 -12
- package/dist/pi-extensions/__tests__/canvas-stophook-agentend.test.js +41 -0
- package/dist/pi-extensions/__tests__/canvas-stophook-context-nudge.test.d.ts +1 -0
- package/dist/pi-extensions/__tests__/canvas-stophook-context-nudge.test.js +121 -0
- package/dist/pi-extensions/canvas-inbox-watcher.d.ts +1 -1
- package/dist/pi-extensions/canvas-inbox-watcher.js +203 -25
- package/dist/pi-extensions/canvas-recap.d.ts +4 -0
- package/dist/pi-extensions/canvas-recap.js +73 -46
- package/dist/pi-extensions/canvas-stophook.d.ts +11 -0
- package/dist/pi-extensions/canvas-stophook.js +33 -4
- package/dist/types.d.ts +9 -26
- package/dist/types.js +1 -28
- package/dist/web-client/assets/{index-DiFuLcp6.js → index--md2ylfi.js} +1 -1
- package/dist/web-client/index.html +1 -1
- package/dist/web-client/sw.js +1 -1
- package/package.json +8 -4
- package/dist/pi-extensions/canvas-nav.d.ts +0 -43
- package/dist/pi-extensions/canvas-nav.js +0 -640
- package/dist/pi-extensions/widget-order-bus.d.ts +0 -6
- package/dist/pi-extensions/widget-order-bus.js +0 -34
|
@@ -1,10 +1,131 @@
|
|
|
1
1
|
import { spawnSync } from 'node:child_process';
|
|
2
2
|
import { chmod, mkdir, writeFile } from 'node:fs/promises';
|
|
3
|
+
import { readFileSync } from 'node:fs';
|
|
3
4
|
import { homedir } from 'node:os';
|
|
4
5
|
import { basename, dirname, join, resolve } from 'node:path';
|
|
6
|
+
import { isDeepStrictEqual } from 'node:util';
|
|
7
|
+
import { BINDING_CATALOG, normalizeGesture, resolveKeybindings, } from '../../core/keybindings/index.js';
|
|
5
8
|
import { builtinPiPackageDir } from '../../core/scope.js';
|
|
6
9
|
import { readJsonIfExists } from '../../core/fs-utils.js';
|
|
7
10
|
import { resolveBundledPiCliPath } from '../../core/runtime/pi-cli.js';
|
|
11
|
+
function isKeybindingsObject(value) {
|
|
12
|
+
return value !== null && typeof value === 'object' && !Array.isArray(value);
|
|
13
|
+
}
|
|
14
|
+
function cloneKeybindings(value) {
|
|
15
|
+
if (!isKeybindingsObject(value))
|
|
16
|
+
return {};
|
|
17
|
+
return Object.fromEntries(Object.entries(value).map(([id, gestures]) => [
|
|
18
|
+
id,
|
|
19
|
+
Array.isArray(gestures) ? [...gestures] : gestures,
|
|
20
|
+
]));
|
|
21
|
+
}
|
|
22
|
+
/** Transactional sparse keybinding draft used by the full-screen setup tab. */
|
|
23
|
+
export class SetupKeybindingsDraft {
|
|
24
|
+
expected;
|
|
25
|
+
baseline;
|
|
26
|
+
current;
|
|
27
|
+
baselineInvalidRoot;
|
|
28
|
+
invalidRoot;
|
|
29
|
+
constructor(rawKeybindings) {
|
|
30
|
+
this.expected = rawKeybindings;
|
|
31
|
+
this.baseline = cloneKeybindings(rawKeybindings);
|
|
32
|
+
this.current = cloneKeybindings(rawKeybindings);
|
|
33
|
+
this.baselineInvalidRoot = rawKeybindings !== undefined && !isKeybindingsObject(rawKeybindings) ? rawKeybindings : undefined;
|
|
34
|
+
this.invalidRoot = this.baselineInvalidRoot;
|
|
35
|
+
}
|
|
36
|
+
get dirty() {
|
|
37
|
+
return !isDeepStrictEqual(this.current, this.baseline)
|
|
38
|
+
|| !isDeepStrictEqual(this.invalidRoot, this.baselineInvalidRoot);
|
|
39
|
+
}
|
|
40
|
+
overrides() {
|
|
41
|
+
return cloneKeybindings(this.current);
|
|
42
|
+
}
|
|
43
|
+
expectedKeybindings() {
|
|
44
|
+
return this.expected;
|
|
45
|
+
}
|
|
46
|
+
resolution() {
|
|
47
|
+
return resolveKeybindings(this.invalidRoot === undefined ? this.current : this.invalidRoot);
|
|
48
|
+
}
|
|
49
|
+
/** True while the persisted `keybindings` root is a non-object (e.g. a string):
|
|
50
|
+
* edits cannot be layered onto an invalid root, so the tab must reset-all first. */
|
|
51
|
+
hasInvalidRoot() {
|
|
52
|
+
return this.invalidRoot !== undefined;
|
|
53
|
+
}
|
|
54
|
+
expression(id) {
|
|
55
|
+
return this.resolution().gestures(id).join(', ');
|
|
56
|
+
}
|
|
57
|
+
edit(id, expression) {
|
|
58
|
+
if (this.invalidRoot !== undefined) {
|
|
59
|
+
return {
|
|
60
|
+
ok: false,
|
|
61
|
+
diagnostics: [{
|
|
62
|
+
severity: 'error',
|
|
63
|
+
code: 'invalid-keybindings',
|
|
64
|
+
offendingValue: this.invalidRoot,
|
|
65
|
+
message: 'Reset all before editing: the saved keybindings root is invalid.',
|
|
66
|
+
}],
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
const definition = BINDING_CATALOG.find((candidate) => candidate.id === id);
|
|
70
|
+
let gestures;
|
|
71
|
+
try {
|
|
72
|
+
gestures = expression.trim() === ''
|
|
73
|
+
? []
|
|
74
|
+
: expression.split(',').map((gesture) => normalizeGesture(gesture.trim(), definition));
|
|
75
|
+
}
|
|
76
|
+
catch (error) {
|
|
77
|
+
return {
|
|
78
|
+
ok: false,
|
|
79
|
+
diagnostics: [{
|
|
80
|
+
severity: 'error',
|
|
81
|
+
code: 'invalid-override',
|
|
82
|
+
bindingId: id,
|
|
83
|
+
offendingValue: expression,
|
|
84
|
+
message: error instanceof Error ? error.message : String(error),
|
|
85
|
+
}],
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
const deduped = [...new Set(gestures)];
|
|
89
|
+
// Sparse invariant: a member is stored only when it changes the effective
|
|
90
|
+
// resolution. If the committed gestures equal the catalog default for this
|
|
91
|
+
// id, drop the member instead of recording a redundant override — otherwise
|
|
92
|
+
// committing an unchanged default flips the row to a spurious user/unsaved
|
|
93
|
+
// state that persistence would then strip anyway.
|
|
94
|
+
const withoutId = { ...this.current };
|
|
95
|
+
delete withoutId[id];
|
|
96
|
+
const defaultGestures = [...resolveKeybindings(withoutId).gestures(id)];
|
|
97
|
+
const prospective = isDeepStrictEqual(deduped, defaultGestures)
|
|
98
|
+
? withoutId
|
|
99
|
+
: { ...this.current, [id]: deduped };
|
|
100
|
+
const resolution = resolveKeybindings(prospective);
|
|
101
|
+
const relevant = resolution.diagnostics.filter((diagnostic) => diagnostic.bindingId === id || diagnostic.relatedBindingIds?.includes(id));
|
|
102
|
+
if (relevant.length > 0)
|
|
103
|
+
return { ok: false, diagnostics: relevant };
|
|
104
|
+
this.current = prospective;
|
|
105
|
+
return { ok: true, diagnostics: resolution.diagnostics };
|
|
106
|
+
}
|
|
107
|
+
unbind(id) {
|
|
108
|
+
return this.edit(id, '');
|
|
109
|
+
}
|
|
110
|
+
resetRow(id) {
|
|
111
|
+
delete this.current[id];
|
|
112
|
+
}
|
|
113
|
+
resetAll() {
|
|
114
|
+
this.current = {};
|
|
115
|
+
this.invalidRoot = undefined;
|
|
116
|
+
}
|
|
117
|
+
discard() {
|
|
118
|
+
this.current = cloneKeybindings(this.baseline);
|
|
119
|
+
this.invalidRoot = this.baselineInvalidRoot;
|
|
120
|
+
}
|
|
121
|
+
markSaved(overrides) {
|
|
122
|
+
this.expected = Object.keys(overrides).length === 0 ? undefined : cloneKeybindings(overrides);
|
|
123
|
+
this.baseline = cloneKeybindings(overrides);
|
|
124
|
+
this.current = cloneKeybindings(overrides);
|
|
125
|
+
this.baselineInvalidRoot = undefined;
|
|
126
|
+
this.invalidRoot = undefined;
|
|
127
|
+
}
|
|
128
|
+
}
|
|
8
129
|
const PACKAGE_COPY = {
|
|
9
130
|
'crtr-extensions': {
|
|
10
131
|
name: 'pi-crtr-extensions',
|
|
@@ -13,8 +134,8 @@ const PACKAGE_COPY = {
|
|
|
13
134
|
},
|
|
14
135
|
'mode-switch': {
|
|
15
136
|
name: 'pi-mode-switch',
|
|
16
|
-
shortDescription: 'Alt+
|
|
17
|
-
longDescription: 'Press Alt+
|
|
137
|
+
shortDescription: 'Alt+Shift+P cycles spec / plan / normal modes; injects mode-specific guidance on change.',
|
|
138
|
+
longDescription: 'Press Alt+Shift+P to rotate between three operating modes — spec (requirements gathering), plan (design before code), and normal (execution). Each switch appends mode-tailored guidance to keep the agent in the right gear.',
|
|
18
139
|
},
|
|
19
140
|
'oauth-adapter': {
|
|
20
141
|
name: 'pi-claude-oauth-adapter',
|
|
@@ -231,6 +352,25 @@ export function resolveSettingsPath(homeDir = homedir()) {
|
|
|
231
352
|
export function resolveExaKeyPath(homeDir = homedir()) {
|
|
232
353
|
return join(homeDir, '.crouter', 'exa.key');
|
|
233
354
|
}
|
|
355
|
+
export function resolveComposioKeyPath(homeDir = homedir()) {
|
|
356
|
+
return join(homeDir, '.crouter', 'composio.key');
|
|
357
|
+
}
|
|
358
|
+
function detectApiKey(envVar, keyPath) {
|
|
359
|
+
if ((process.env[envVar] ?? '').trim() !== '')
|
|
360
|
+
return { present: true, source: 'env' };
|
|
361
|
+
try {
|
|
362
|
+
if (readFileSync(keyPath, 'utf8').trim() !== '')
|
|
363
|
+
return { present: true, source: 'file' };
|
|
364
|
+
}
|
|
365
|
+
catch { /* absent/unreadable → not present */ }
|
|
366
|
+
return { present: false };
|
|
367
|
+
}
|
|
368
|
+
export function detectExaKey(homeDir = homedir()) {
|
|
369
|
+
return detectApiKey('EXA_API_KEY', resolveExaKeyPath(homeDir));
|
|
370
|
+
}
|
|
371
|
+
export function detectComposioKey(homeDir = homedir()) {
|
|
372
|
+
return detectApiKey('COMPOSIO_API_KEY', resolveComposioKeyPath(homeDir));
|
|
373
|
+
}
|
|
234
374
|
export function buildSetupInitialState(opts = {}) {
|
|
235
375
|
const homeDir = opts.homeDir ?? homedir();
|
|
236
376
|
const settingsPath = opts.settingsPath ?? resolveSettingsPath(homeDir);
|
|
@@ -240,7 +380,7 @@ export function buildSetupInitialState(opts = {}) {
|
|
|
240
380
|
const commandExists = opts.commandExists ?? detectCommandOnPath;
|
|
241
381
|
const packageManager = opts.packageManager ?? detectPackageManager(process.platform, commandExists);
|
|
242
382
|
const systemTools = ['tmux', 'nvim'].map((tool) => buildSystemToolState(tool, packageManager, commandExists));
|
|
243
|
-
return { manifest, installedPackageIds, systemTools, exaKeyPath: resolveExaKeyPath(homeDir) };
|
|
383
|
+
return { manifest, installedPackageIds, systemTools, exaKeyPath: resolveExaKeyPath(homeDir), composioKeyPath: resolveComposioKeyPath(homeDir) };
|
|
244
384
|
}
|
|
245
385
|
export function buildSetupStaticInstructions(opts) {
|
|
246
386
|
return {
|
|
@@ -257,6 +397,7 @@ export function buildSetupStaticInstructions(opts) {
|
|
|
257
397
|
return `- ${plan.tool}: ${plan.hint}`;
|
|
258
398
|
}),
|
|
259
399
|
exaLine: `- Exa key: write to ${opts.exaKeyPath} or set EXA_API_KEY`,
|
|
400
|
+
composioLine: `- Composio key: write to ${opts.composioKeyPath} or set COMPOSIO_API_KEY`,
|
|
260
401
|
footer: 'Run `crtr sys setup` in a TTY to open the wizard.',
|
|
261
402
|
};
|
|
262
403
|
}
|
|
@@ -266,11 +407,12 @@ export function renderSetupStaticInstructions(state) {
|
|
|
266
407
|
installedPackageIds: state.installedPackageIds,
|
|
267
408
|
systemPlans: state.systemTools.map((tool) => tool.plan),
|
|
268
409
|
exaKeyPath: state.exaKeyPath,
|
|
410
|
+
composioKeyPath: state.composioKeyPath,
|
|
269
411
|
});
|
|
270
412
|
return [
|
|
271
413
|
instructions.headline,
|
|
272
414
|
'',
|
|
273
|
-
'Provider login: open the wizard in a TTY and use the
|
|
415
|
+
'Provider login: open the wizard in a TTY and use the Providers tab (same flow as /login) to authenticate a model provider.',
|
|
274
416
|
'',
|
|
275
417
|
'Packages:',
|
|
276
418
|
...instructions.packageLines,
|
|
@@ -279,6 +421,7 @@ export function renderSetupStaticInstructions(state) {
|
|
|
279
421
|
...instructions.systemLines,
|
|
280
422
|
'',
|
|
281
423
|
instructions.exaLine,
|
|
424
|
+
instructions.composioLine,
|
|
282
425
|
instructions.footer,
|
|
283
426
|
].join('\n') + '\n';
|
|
284
427
|
}
|
|
@@ -299,12 +442,19 @@ export async function writeExaKey(exaKeyPath, exaKey) {
|
|
|
299
442
|
await writeFile(exaKeyPath, `${exaKey}\n`, 'utf8');
|
|
300
443
|
await chmod(exaKeyPath, 0o600).catch(() => undefined);
|
|
301
444
|
}
|
|
445
|
+
export async function writeComposioKey(composioKeyPath, composioKey) {
|
|
446
|
+
await mkdir(dirname(composioKeyPath), { recursive: true });
|
|
447
|
+
await writeFile(composioKeyPath, `${composioKey}\n`, 'utf8');
|
|
448
|
+
await chmod(composioKeyPath, 0o600).catch(() => undefined);
|
|
449
|
+
}
|
|
302
450
|
export function summarizeSetupExecution(result) {
|
|
303
451
|
return {
|
|
304
452
|
installed: [...result.installedPackages, ...result.installedSystemDeps],
|
|
305
453
|
skipped: [...result.skippedPackages, ...result.skippedSystemDeps],
|
|
306
454
|
exaKeyWritten: result.exaKeyWritten,
|
|
307
455
|
exaKeyPath: result.exaKeyPath,
|
|
456
|
+
composioKeyWritten: result.composioKeyWritten,
|
|
457
|
+
composioKeyPath: result.composioKeyPath,
|
|
308
458
|
};
|
|
309
459
|
}
|
|
310
460
|
export function formatSetupExecutionSummary(summary) {
|
|
@@ -313,6 +463,7 @@ export function formatSetupExecutionSummary(summary) {
|
|
|
313
463
|
summary.installed.length > 0 ? `installed: ${summary.installed.join(', ')}` : 'installed: none',
|
|
314
464
|
summary.skipped.length > 0 ? `skipped: ${summary.skipped.join(', ')}` : 'skipped: none',
|
|
315
465
|
summary.exaKeyWritten ? `exa key written: ${summary.exaKeyPath}` : 'exa key written: no',
|
|
466
|
+
summary.composioKeyWritten ? `composio key written: ${summary.composioKeyPath}` : 'composio key written: no',
|
|
316
467
|
].join('\n') + '\n';
|
|
317
468
|
}
|
|
318
469
|
export async function executeSetupSubmission(submission) {
|
|
@@ -344,6 +495,10 @@ export async function executeSetupSubmission(submission) {
|
|
|
344
495
|
if (exaKeyWritten) {
|
|
345
496
|
await writeExaKey(submission.exaKeyPath, submission.exaKey);
|
|
346
497
|
}
|
|
498
|
+
const composioKeyWritten = submission.composioKey.trim() !== '';
|
|
499
|
+
if (composioKeyWritten) {
|
|
500
|
+
await writeComposioKey(submission.composioKeyPath, submission.composioKey);
|
|
501
|
+
}
|
|
347
502
|
return summarizeSetupExecution({
|
|
348
503
|
installedPackages,
|
|
349
504
|
skippedPackages,
|
|
@@ -351,5 +506,7 @@ export async function executeSetupSubmission(submission) {
|
|
|
351
506
|
skippedSystemDeps,
|
|
352
507
|
exaKeyWritten,
|
|
353
508
|
exaKeyPath: submission.exaKeyPath,
|
|
509
|
+
composioKeyWritten,
|
|
510
|
+
composioKeyPath: submission.composioKeyPath,
|
|
354
511
|
});
|
|
355
512
|
}
|
|
@@ -1,2 +1,90 @@
|
|
|
1
1
|
import type { LeafDef } from '../../core/command.js';
|
|
2
|
+
import { TUI, type Component, type Focusable } from '@earendil-works/pi-tui';
|
|
3
|
+
import { type BindingId, type BindingResolution } from '../../core/keybindings/index.js';
|
|
4
|
+
import { type SetupPackageId, type SetupPackageManifestEntry, type SetupSubmission, type SetupSystemToolState } from './setup-core.js';
|
|
5
|
+
export declare class SetupWizard implements Component, Focusable {
|
|
6
|
+
private readonly manifest;
|
|
7
|
+
private readonly installedPackageIds;
|
|
8
|
+
private readonly systemTools;
|
|
9
|
+
private readonly exaInput;
|
|
10
|
+
private readonly composioInput;
|
|
11
|
+
private readonly keyInput;
|
|
12
|
+
private readonly openingBindings;
|
|
13
|
+
private readonly keyDraft;
|
|
14
|
+
private readonly terminalRows;
|
|
15
|
+
private readonly selectedPackageIds;
|
|
16
|
+
private readonly selectedSystemTools;
|
|
17
|
+
private readonly providers;
|
|
18
|
+
private activeTab;
|
|
19
|
+
private pluginIndex;
|
|
20
|
+
private systemIndex;
|
|
21
|
+
private expandedPluginId;
|
|
22
|
+
private confirming;
|
|
23
|
+
private keyIndex;
|
|
24
|
+
private keyScroll;
|
|
25
|
+
private keyFilter;
|
|
26
|
+
private filteringKeys;
|
|
27
|
+
private editingKey;
|
|
28
|
+
private keyEditError;
|
|
29
|
+
private keyDiagnostics;
|
|
30
|
+
private keyConfirm;
|
|
31
|
+
private keyNotice;
|
|
32
|
+
private cachedWidth;
|
|
33
|
+
private cachedLines;
|
|
34
|
+
private _focused;
|
|
35
|
+
onSubmit?: (submission: SetupSubmission) => void;
|
|
36
|
+
onCancel?: () => void;
|
|
37
|
+
constructor(manifest: SetupPackageManifestEntry[], installedPackageIds: Set<SetupPackageId>, systemTools: SetupSystemToolState[], tui: TUI, agentDir: string, openingBindings: BindingResolution<BindingId>, rawKeybindings: unknown, terminalRows: () => number);
|
|
38
|
+
set focused(value: boolean);
|
|
39
|
+
get focused(): boolean;
|
|
40
|
+
invalidate(): void;
|
|
41
|
+
private setTab;
|
|
42
|
+
private moveTab;
|
|
43
|
+
private cancel;
|
|
44
|
+
dispose(): void;
|
|
45
|
+
private matches;
|
|
46
|
+
/** Human hint label for an action, derived from the opening snapshot so footers
|
|
47
|
+
* reflect the effective (possibly remapped) gestures the wizard actually honors. */
|
|
48
|
+
private label;
|
|
49
|
+
/** Like `label`, but drops gestures a focused pi text Input consumes as data
|
|
50
|
+
* (single printable chars and the arrow keys), so the Exa/Composio footers do
|
|
51
|
+
* not claim keys that never reach the wizard while a field owns focus. */
|
|
52
|
+
private fieldSafeLabel;
|
|
53
|
+
private handleGlobalTabSwitch;
|
|
54
|
+
private selectedPackage;
|
|
55
|
+
private selectedSystem;
|
|
56
|
+
private movePlugin;
|
|
57
|
+
private moveSystem;
|
|
58
|
+
private togglePackage;
|
|
59
|
+
private toggleSystem;
|
|
60
|
+
private toggleDetails;
|
|
61
|
+
private hasPendingInstalls;
|
|
62
|
+
private buildSubmission;
|
|
63
|
+
private finalize;
|
|
64
|
+
private filteredKeybindings;
|
|
65
|
+
private selectedKeybinding;
|
|
66
|
+
private moveKey;
|
|
67
|
+
private keyViewportLines;
|
|
68
|
+
private keyPageSize;
|
|
69
|
+
private beginKeyEdit;
|
|
70
|
+
private commitKeyEdit;
|
|
71
|
+
private cancelKeyEdit;
|
|
72
|
+
private saveKeybindings;
|
|
73
|
+
private refreshTmuxBindingsAfterSave;
|
|
74
|
+
private confirmKeyAction;
|
|
75
|
+
private handleKeybindingsInput;
|
|
76
|
+
handleInput(data: string): void;
|
|
77
|
+
private renderHeader;
|
|
78
|
+
private renderFooter;
|
|
79
|
+
private renderProviders;
|
|
80
|
+
private renderPlugins;
|
|
81
|
+
private renderSystems;
|
|
82
|
+
private renderExa;
|
|
83
|
+
private renderComposio;
|
|
84
|
+
private renderConfirm;
|
|
85
|
+
private keyRowHasMessage;
|
|
86
|
+
private keyLineCost;
|
|
87
|
+
private renderKeybindings;
|
|
88
|
+
render(width: number): string[];
|
|
89
|
+
}
|
|
2
90
|
export declare const sysSetupLeaf: LeafDef;
|