@mariozechner/pi-coding-agent 0.29.0 → 0.29.1
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/CHANGELOG.md +13 -0
- package/README.md +27 -12
- package/dist/core/custom-tools/loader.d.ts +5 -0
- package/dist/core/custom-tools/loader.d.ts.map +1 -1
- package/dist/core/custom-tools/loader.js +58 -3
- package/dist/core/custom-tools/loader.js.map +1 -1
- package/dist/core/hooks/loader.d.ts.map +1 -1
- package/dist/core/hooks/loader.js +8 -1
- package/dist/core/hooks/loader.js.map +1 -1
- package/dist/main.d.ts.map +1 -1
- package/dist/main.js +19 -2
- package/dist/main.js.map +1 -1
- package/dist/modes/interactive/components/settings-selector.d.ts +33 -0
- package/dist/modes/interactive/components/settings-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/settings-selector.js +164 -0
- package/dist/modes/interactive/components/settings-selector.js.map +1 -0
- package/dist/modes/interactive/interactive-mode.d.ts +1 -5
- package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
- package/dist/modes/interactive/interactive-mode.js +70 -116
- package/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/dist/modes/interactive/theme/theme.d.ts +1 -0
- package/dist/modes/interactive/theme/theme.d.ts.map +1 -1
- package/dist/modes/interactive/theme/theme.js +9 -0
- package/dist/modes/interactive/theme/theme.js.map +1 -1
- package/package.json +4 -4
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
import * as fs from "node:fs";
|
|
6
6
|
import * as os from "node:os";
|
|
7
7
|
import * as path from "node:path";
|
|
8
|
-
import { CombinedAutocompleteProvider, Container,
|
|
8
|
+
import { CombinedAutocompleteProvider, Container, Input, Loader, Markdown, ProcessTerminal, Spacer, Text, TruncatedText, TUI, visibleWidth, } from "@mariozechner/pi-tui";
|
|
9
9
|
import { exec, spawnSync } from "child_process";
|
|
10
10
|
import { APP_NAME, getAuthPath, getDebugLogPath } from "../../config.js";
|
|
11
11
|
import { isBashExecutionMessage } from "../../core/messages.js";
|
|
@@ -25,15 +25,12 @@ import { HookInputComponent } from "./components/hook-input.js";
|
|
|
25
25
|
import { HookSelectorComponent } from "./components/hook-selector.js";
|
|
26
26
|
import { ModelSelectorComponent } from "./components/model-selector.js";
|
|
27
27
|
import { OAuthSelectorComponent } from "./components/oauth-selector.js";
|
|
28
|
-
import { QueueModeSelectorComponent } from "./components/queue-mode-selector.js";
|
|
29
28
|
import { SessionSelectorComponent } from "./components/session-selector.js";
|
|
30
|
-
import {
|
|
31
|
-
import { ThemeSelectorComponent } from "./components/theme-selector.js";
|
|
32
|
-
import { ThinkingSelectorComponent } from "./components/thinking-selector.js";
|
|
29
|
+
import { SettingsSelectorComponent } from "./components/settings-selector.js";
|
|
33
30
|
import { ToolExecutionComponent } from "./components/tool-execution.js";
|
|
34
31
|
import { UserMessageComponent } from "./components/user-message.js";
|
|
35
32
|
import { UserMessageSelectorComponent } from "./components/user-message-selector.js";
|
|
36
|
-
import { getEditorTheme, getMarkdownTheme, onThemeChange, setTheme, theme } from "./theme/theme.js";
|
|
33
|
+
import { getAvailableThemes, getEditorTheme, getMarkdownTheme, onThemeChange, setTheme, theme } from "./theme/theme.js";
|
|
37
34
|
export class InteractiveMode {
|
|
38
35
|
setToolUIContext;
|
|
39
36
|
session;
|
|
@@ -107,7 +104,7 @@ export class InteractiveMode {
|
|
|
107
104
|
this.footer.setAutoCompactEnabled(session.autoCompactionEnabled);
|
|
108
105
|
// Define slash commands for autocomplete
|
|
109
106
|
const slashCommands = [
|
|
110
|
-
{ name: "
|
|
107
|
+
{ name: "settings", description: "Open settings menu" },
|
|
111
108
|
{ name: "model", description: "Select model (opens selector UI)" },
|
|
112
109
|
{ name: "export", description: "Export session to HTML file" },
|
|
113
110
|
{ name: "copy", description: "Copy last agent message to clipboard" },
|
|
@@ -117,17 +114,10 @@ export class InteractiveMode {
|
|
|
117
114
|
{ name: "branch", description: "Create a new branch from a previous message" },
|
|
118
115
|
{ name: "login", description: "Login with OAuth provider" },
|
|
119
116
|
{ name: "logout", description: "Logout from OAuth provider" },
|
|
120
|
-
{ name: "queue", description: "Select message queue mode (opens selector UI)" },
|
|
121
|
-
{ name: "theme", description: "Select color theme (opens selector UI)" },
|
|
122
117
|
{ name: "new", description: "Start a new session" },
|
|
123
118
|
{ name: "compact", description: "Manually compact the session context" },
|
|
124
|
-
{ name: "autocompact", description: "Toggle automatic context compaction" },
|
|
125
119
|
{ name: "resume", description: "Resume a different session" },
|
|
126
120
|
];
|
|
127
|
-
// Add image toggle command only if terminal supports images
|
|
128
|
-
if (getCapabilities().images) {
|
|
129
|
-
slashCommands.push({ name: "show-images", description: "Toggle inline image display" });
|
|
130
|
-
}
|
|
131
121
|
// Load hide thinking block setting
|
|
132
122
|
this.hideThinkingBlock = this.settingsManager.getHideThinkingBlock();
|
|
133
123
|
// Convert file commands to SlashCommand format
|
|
@@ -510,8 +500,8 @@ export class InteractiveMode {
|
|
|
510
500
|
if (!text)
|
|
511
501
|
return;
|
|
512
502
|
// Handle slash commands
|
|
513
|
-
if (text === "/
|
|
514
|
-
this.
|
|
503
|
+
if (text === "/settings") {
|
|
504
|
+
this.showSettingsSelector();
|
|
515
505
|
this.editor.setText("");
|
|
516
506
|
return;
|
|
517
507
|
}
|
|
@@ -560,16 +550,6 @@ export class InteractiveMode {
|
|
|
560
550
|
this.editor.setText("");
|
|
561
551
|
return;
|
|
562
552
|
}
|
|
563
|
-
if (text === "/queue") {
|
|
564
|
-
this.showQueueModeSelector();
|
|
565
|
-
this.editor.setText("");
|
|
566
|
-
return;
|
|
567
|
-
}
|
|
568
|
-
if (text === "/theme") {
|
|
569
|
-
this.showThemeSelector();
|
|
570
|
-
this.editor.setText("");
|
|
571
|
-
return;
|
|
572
|
-
}
|
|
573
553
|
if (text === "/new") {
|
|
574
554
|
this.editor.setText("");
|
|
575
555
|
await this.handleClearCommand();
|
|
@@ -587,16 +567,6 @@ export class InteractiveMode {
|
|
|
587
567
|
}
|
|
588
568
|
return;
|
|
589
569
|
}
|
|
590
|
-
if (text === "/autocompact") {
|
|
591
|
-
this.handleAutocompactCommand();
|
|
592
|
-
this.editor.setText("");
|
|
593
|
-
return;
|
|
594
|
-
}
|
|
595
|
-
if (text === "/show-images") {
|
|
596
|
-
this.showShowImagesSelector();
|
|
597
|
-
this.editor.setText("");
|
|
598
|
-
return;
|
|
599
|
-
}
|
|
600
570
|
if (text === "/debug") {
|
|
601
571
|
this.handleDebugCommand();
|
|
602
572
|
this.editor.setText("");
|
|
@@ -1202,59 +1172,74 @@ export class InteractiveMode {
|
|
|
1202
1172
|
this.ui.setFocus(focus);
|
|
1203
1173
|
this.ui.requestRender();
|
|
1204
1174
|
}
|
|
1205
|
-
|
|
1206
|
-
this.showSelector((done) => {
|
|
1207
|
-
const selector = new ThinkingSelectorComponent(this.session.thinkingLevel, this.session.getAvailableThinkingLevels(), (level) => {
|
|
1208
|
-
this.session.setThinkingLevel(level);
|
|
1209
|
-
this.footer.updateState(this.session.state);
|
|
1210
|
-
this.updateEditorBorderColor();
|
|
1211
|
-
done();
|
|
1212
|
-
this.showStatus(`Thinking level: ${level}`);
|
|
1213
|
-
}, () => {
|
|
1214
|
-
done();
|
|
1215
|
-
this.ui.requestRender();
|
|
1216
|
-
});
|
|
1217
|
-
return { component: selector, focus: selector.getSelectList() };
|
|
1218
|
-
});
|
|
1219
|
-
}
|
|
1220
|
-
showQueueModeSelector() {
|
|
1221
|
-
this.showSelector((done) => {
|
|
1222
|
-
const selector = new QueueModeSelectorComponent(this.session.queueMode, (mode) => {
|
|
1223
|
-
this.session.setQueueMode(mode);
|
|
1224
|
-
done();
|
|
1225
|
-
this.showStatus(`Queue mode: ${mode}`);
|
|
1226
|
-
}, () => {
|
|
1227
|
-
done();
|
|
1228
|
-
this.ui.requestRender();
|
|
1229
|
-
});
|
|
1230
|
-
return { component: selector, focus: selector.getSelectList() };
|
|
1231
|
-
});
|
|
1232
|
-
}
|
|
1233
|
-
showThemeSelector() {
|
|
1234
|
-
const currentTheme = this.settingsManager.getTheme() || "dark";
|
|
1175
|
+
showSettingsSelector() {
|
|
1235
1176
|
this.showSelector((done) => {
|
|
1236
|
-
const selector = new
|
|
1237
|
-
|
|
1238
|
-
this.settingsManager.
|
|
1239
|
-
this.
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1246
|
-
|
|
1247
|
-
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1177
|
+
const selector = new SettingsSelectorComponent({
|
|
1178
|
+
autoCompact: this.session.autoCompactionEnabled,
|
|
1179
|
+
showImages: this.settingsManager.getShowImages(),
|
|
1180
|
+
queueMode: this.session.queueMode,
|
|
1181
|
+
thinkingLevel: this.session.thinkingLevel,
|
|
1182
|
+
availableThinkingLevels: this.session.getAvailableThinkingLevels(),
|
|
1183
|
+
currentTheme: this.settingsManager.getTheme() || "dark",
|
|
1184
|
+
availableThemes: getAvailableThemes(),
|
|
1185
|
+
hideThinkingBlock: this.hideThinkingBlock,
|
|
1186
|
+
collapseChangelog: this.settingsManager.getCollapseChangelog(),
|
|
1187
|
+
}, {
|
|
1188
|
+
onAutoCompactChange: (enabled) => {
|
|
1189
|
+
this.session.setAutoCompactionEnabled(enabled);
|
|
1190
|
+
this.footer.setAutoCompactEnabled(enabled);
|
|
1191
|
+
},
|
|
1192
|
+
onShowImagesChange: (enabled) => {
|
|
1193
|
+
this.settingsManager.setShowImages(enabled);
|
|
1194
|
+
for (const child of this.chatContainer.children) {
|
|
1195
|
+
if (child instanceof ToolExecutionComponent) {
|
|
1196
|
+
child.setShowImages(enabled);
|
|
1197
|
+
}
|
|
1198
|
+
}
|
|
1199
|
+
},
|
|
1200
|
+
onQueueModeChange: (mode) => {
|
|
1201
|
+
this.session.setQueueMode(mode);
|
|
1202
|
+
},
|
|
1203
|
+
onThinkingLevelChange: (level) => {
|
|
1204
|
+
this.session.setThinkingLevel(level);
|
|
1205
|
+
this.footer.updateState(this.session.state);
|
|
1206
|
+
this.updateEditorBorderColor();
|
|
1207
|
+
},
|
|
1208
|
+
onThemeChange: (themeName) => {
|
|
1209
|
+
const result = setTheme(themeName, true);
|
|
1210
|
+
this.settingsManager.setTheme(themeName);
|
|
1253
1211
|
this.ui.invalidate();
|
|
1212
|
+
if (!result.success) {
|
|
1213
|
+
this.showError(`Failed to load theme "${themeName}": ${result.error}\nFell back to dark theme.`);
|
|
1214
|
+
}
|
|
1215
|
+
},
|
|
1216
|
+
onThemePreview: (themeName) => {
|
|
1217
|
+
const result = setTheme(themeName, true);
|
|
1218
|
+
if (result.success) {
|
|
1219
|
+
this.ui.invalidate();
|
|
1220
|
+
this.ui.requestRender();
|
|
1221
|
+
}
|
|
1222
|
+
},
|
|
1223
|
+
onHideThinkingBlockChange: (hidden) => {
|
|
1224
|
+
this.hideThinkingBlock = hidden;
|
|
1225
|
+
this.settingsManager.setHideThinkingBlock(hidden);
|
|
1226
|
+
for (const child of this.chatContainer.children) {
|
|
1227
|
+
if (child instanceof AssistantMessageComponent) {
|
|
1228
|
+
child.setHideThinkingBlock(hidden);
|
|
1229
|
+
}
|
|
1230
|
+
}
|
|
1231
|
+
this.chatContainer.clear();
|
|
1232
|
+
this.rebuildChatFromMessages();
|
|
1233
|
+
},
|
|
1234
|
+
onCollapseChangelogChange: (collapsed) => {
|
|
1235
|
+
this.settingsManager.setCollapseChangelog(collapsed);
|
|
1236
|
+
},
|
|
1237
|
+
onCancel: () => {
|
|
1238
|
+
done();
|
|
1254
1239
|
this.ui.requestRender();
|
|
1255
|
-
}
|
|
1240
|
+
},
|
|
1256
1241
|
});
|
|
1257
|
-
return { component: selector, focus: selector.
|
|
1242
|
+
return { component: selector, focus: selector.getSettingsList() };
|
|
1258
1243
|
});
|
|
1259
1244
|
}
|
|
1260
1245
|
showModelSelector() {
|
|
@@ -1640,37 +1625,6 @@ export class InteractiveMode {
|
|
|
1640
1625
|
}
|
|
1641
1626
|
await this.executeCompaction(customInstructions, false);
|
|
1642
1627
|
}
|
|
1643
|
-
handleAutocompactCommand() {
|
|
1644
|
-
const newState = !this.session.autoCompactionEnabled;
|
|
1645
|
-
this.session.setAutoCompactionEnabled(newState);
|
|
1646
|
-
this.footer.setAutoCompactEnabled(newState);
|
|
1647
|
-
this.showStatus(`Auto-compaction: ${newState ? "on" : "off"}`);
|
|
1648
|
-
}
|
|
1649
|
-
showShowImagesSelector() {
|
|
1650
|
-
// Only available if terminal supports images
|
|
1651
|
-
const caps = getCapabilities();
|
|
1652
|
-
if (!caps.images) {
|
|
1653
|
-
this.showWarning("Your terminal does not support inline images");
|
|
1654
|
-
return;
|
|
1655
|
-
}
|
|
1656
|
-
this.showSelector((done) => {
|
|
1657
|
-
const selector = new ShowImagesSelectorComponent(this.settingsManager.getShowImages(), (newValue) => {
|
|
1658
|
-
this.settingsManager.setShowImages(newValue);
|
|
1659
|
-
// Update all existing tool execution components with new setting
|
|
1660
|
-
for (const child of this.chatContainer.children) {
|
|
1661
|
-
if (child instanceof ToolExecutionComponent) {
|
|
1662
|
-
child.setShowImages(newValue);
|
|
1663
|
-
}
|
|
1664
|
-
}
|
|
1665
|
-
done();
|
|
1666
|
-
this.showStatus(`Inline images: ${newValue ? "on" : "off"}`);
|
|
1667
|
-
}, () => {
|
|
1668
|
-
done();
|
|
1669
|
-
this.ui.requestRender();
|
|
1670
|
-
});
|
|
1671
|
-
return { component: selector, focus: selector.getSelectList() };
|
|
1672
|
-
});
|
|
1673
|
-
}
|
|
1674
1628
|
async executeCompaction(customInstructions, isAuto = false) {
|
|
1675
1629
|
// Stop loading animation
|
|
1676
1630
|
if (this.loadingAnimation) {
|