@diegopetrucci/pi-extensions 0.1.74 → 0.1.76
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/LICENSE +2 -0
- package/README.md +9 -4
- package/extensions/agent-workflow-audit/index.ts +1398 -1009
- package/extensions/agent-workflow-audit/package.json +1 -1
- package/extensions/annotate-git-diff/README.md +3 -1
- package/extensions/annotate-git-diff/clipboard.ts +109 -100
- package/extensions/annotate-git-diff/git.ts +853 -767
- package/extensions/annotate-git-diff/glimpseui.d.ts +87 -78
- package/extensions/annotate-git-diff/index.ts +712 -671
- package/extensions/annotate-git-diff/package.json +1 -1
- package/extensions/annotate-git-diff/prompt.ts +45 -45
- package/extensions/annotate-git-diff/quiet-glimpse.ts +161 -155
- package/extensions/annotate-git-diff/review-server.ts +337 -311
- package/extensions/annotate-git-diff/types.ts +132 -132
- package/extensions/annotate-git-diff/ui.ts +27 -27
- package/extensions/annotate-git-diff/watch.ts +74 -74
- package/extensions/annotate-git-diff/web/app.js +1947 -1884
- package/extensions/annotate-git-diff/web/index.html +5 -6
- package/extensions/annotate-last-message/README.md +1 -1
- package/extensions/annotate-last-message/glimpseui.d.ts +87 -78
- package/extensions/annotate-last-message/index.ts +210 -206
- package/extensions/annotate-last-message/package.json +1 -1
- package/extensions/annotate-last-message/prompt.ts +87 -66
- package/extensions/annotate-last-message/quiet-glimpse.ts +161 -155
- package/extensions/annotate-last-message/session.ts +94 -89
- package/extensions/annotate-last-message/theme.ts +199 -193
- package/extensions/annotate-last-message/types.ts +23 -23
- package/extensions/annotate-last-message/ui.ts +27 -25
- package/extensions/annotate-last-message/web/app.js +4 -7
- package/extensions/annotate-last-message/web/md-renderer.js +1 -1
- package/extensions/brrr/README.md +1 -1
- package/extensions/brrr/index.ts +213 -191
- package/extensions/brrr/package.json +1 -1
- package/extensions/claude-fast/README.md +5 -79
- package/extensions/claude-fast/index.ts +31 -289
- package/extensions/claude-fast/package.json +2 -3
- package/extensions/code-reviewer/README.md +1 -1
- package/extensions/code-reviewer/index.ts +1598 -1350
- package/extensions/code-reviewer/package.json +1 -1
- package/extensions/confirm-destructive/README.md +1 -1
- package/extensions/confirm-destructive/index.ts +55 -51
- package/extensions/confirm-destructive/package.json +1 -1
- package/extensions/context-cap/index.ts +312 -304
- package/extensions/context-cap/package.json +1 -1
- package/extensions/context-inspector/index.ts +1211 -1064
- package/extensions/context-inspector/package.json +1 -1
- package/extensions/contrarian/index.ts +1854 -1735
- package/extensions/contrarian/package.json +1 -1
- package/extensions/dirty-repo-guard/index.ts +41 -41
- package/extensions/dynamic-context-pruning/README.md +6 -38
- package/extensions/dynamic-context-pruning/index.ts +2124 -1980
- package/extensions/dynamic-context-pruning/package.json +1 -1
- package/extensions/fast/README.md +50 -12
- package/extensions/fast/index.ts +513 -317
- package/extensions/fast/package.json +1 -1
- package/extensions/git-footer/README.md +1 -1
- package/extensions/git-footer/index.ts +458 -411
- package/extensions/git-footer/package.json +2 -3
- package/extensions/gnosis/index.ts +180 -130
- package/extensions/gnosis/package.json +1 -1
- package/extensions/inline-bash/index.ts +88 -88
- package/extensions/inline-bash/package.json +1 -1
- package/extensions/librarian/index.ts +1669 -1419
- package/extensions/librarian/package.json +1 -1
- package/extensions/minimal-footer/index.ts +994 -1012
- package/extensions/minimal-footer/openai-usage.ts +195 -190
- package/extensions/notify/index.ts +222 -230
- package/extensions/notify/package.json +1 -1
- package/extensions/openai-fast/README.md +5 -73
- package/extensions/openai-fast/index.ts +32 -272
- package/extensions/openai-fast/package.json +2 -3
- package/extensions/oracle/index.ts +1731 -1625
- package/extensions/oracle/package.json +1 -1
- package/extensions/permission-gate/index.ts +658 -608
- package/extensions/permission-gate/package.json +1 -1
- package/extensions/permission-gate/powershell-safety.ts +840 -793
- package/extensions/project-mcp-json/.pi-fleet-tested-version +1 -0
- package/extensions/project-mcp-json/README.md +199 -0
- package/extensions/project-mcp-json/config.ts +564 -0
- package/extensions/project-mcp-json/index.ts +119 -0
- package/extensions/project-mcp-json/package.json +38 -0
- package/extensions/quiet-tools/index.ts +282 -264
- package/extensions/review/README.md +2 -2
- package/extensions/review/index.ts +1745 -1872
- package/extensions/review/package.json +1 -1
- package/extensions/todo/index.ts +284 -265
- package/extensions/triage-comments/README.md +2 -2
- package/extensions/triage-comments/index.ts +2294 -1882
- package/extensions/triage-comments/package.json +1 -1
- package/package.json +6 -3
- package/assets/social-preview.png +0 -0
- package/extensions/claude-fast/claude-fast.example.json +0 -4
- package/extensions/openai-fast/openai-fast.example.json +0 -4
|
@@ -1,18 +1,18 @@
|
|
|
1
1
|
import { homedir } from "node:os";
|
|
2
2
|
|
|
3
3
|
import {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
4
|
+
createBashToolDefinition,
|
|
5
|
+
createEditToolDefinition,
|
|
6
|
+
createFindToolDefinition,
|
|
7
|
+
createGrepToolDefinition,
|
|
8
|
+
createLsToolDefinition,
|
|
9
|
+
createReadToolDefinition,
|
|
10
|
+
createWriteToolDefinition,
|
|
11
|
+
keyHint,
|
|
12
|
+
SettingsManager,
|
|
13
|
+
type ExtensionAPI,
|
|
14
|
+
type ToolDefinition as PiToolDefinition,
|
|
15
|
+
type ToolsOptions,
|
|
16
16
|
} from "@earendil-works/pi-coding-agent";
|
|
17
17
|
import { Container, Text, truncateToWidth } from "@earendil-works/pi-tui";
|
|
18
18
|
|
|
@@ -27,351 +27,369 @@ type RenderTheme = ToolRenderResultParams[2];
|
|
|
27
27
|
type ToolRenderContext = ToolRenderResultParams[3];
|
|
28
28
|
|
|
29
29
|
type TimerRenderState = {
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
30
|
+
startedAt?: number;
|
|
31
|
+
endedAt?: number;
|
|
32
|
+
interval?: ReturnType<typeof setInterval>;
|
|
33
33
|
};
|
|
34
34
|
|
|
35
35
|
class QuietLinesRenderComponent extends Container {
|
|
36
|
-
|
|
36
|
+
private linesRenderer: ((width: number) => string[]) | undefined;
|
|
37
37
|
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
38
|
+
setLinesRenderer(linesRenderer: (width: number) => string[]): void {
|
|
39
|
+
this.linesRenderer = linesRenderer;
|
|
40
|
+
this.invalidate();
|
|
41
|
+
}
|
|
42
42
|
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
43
|
+
render(width: number): string[] {
|
|
44
|
+
return this.linesRenderer?.(width).filter((line) => line) ?? [];
|
|
45
|
+
}
|
|
46
46
|
}
|
|
47
47
|
|
|
48
48
|
class QuietCallRenderComponent extends QuietLinesRenderComponent {}
|
|
49
49
|
class QuietResultRenderComponent extends QuietLinesRenderComponent {}
|
|
50
50
|
|
|
51
51
|
function sanitizeInlineText(text: string): string {
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
52
|
+
return text
|
|
53
|
+
.replace(/\x1b\][^\x07]*(?:\x07|\x1b\\)/g, "")
|
|
54
|
+
.replace(/\x1b\[[0-?]*[ -/]*[@-~]/g, "")
|
|
55
|
+
.replace(/[\r\n\t]+/g, " ")
|
|
56
|
+
.replace(/[\x00-\x08\x0B-\x1F\x7F]/g, "");
|
|
57
57
|
}
|
|
58
58
|
|
|
59
59
|
function str(value: unknown): string | null {
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
60
|
+
if (typeof value === "string") return sanitizeInlineText(value);
|
|
61
|
+
if (value == null) return "";
|
|
62
|
+
return null;
|
|
63
63
|
}
|
|
64
64
|
|
|
65
65
|
function asRecord(args: unknown): Record<string, unknown> | undefined {
|
|
66
|
-
|
|
66
|
+
return args && typeof args === "object" ? (args as Record<string, unknown>) : undefined;
|
|
67
67
|
}
|
|
68
68
|
|
|
69
69
|
function firstStringArg(args: unknown, names: string[]): string | null {
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
70
|
+
const record = asRecord(args);
|
|
71
|
+
if (!record) return "";
|
|
72
|
+
for (const name of names) {
|
|
73
|
+
if (Object.prototype.hasOwnProperty.call(record, name)) {
|
|
74
|
+
return str(record[name]);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
return "";
|
|
78
78
|
}
|
|
79
79
|
|
|
80
80
|
function numberArg(args: unknown, name: string): number | undefined {
|
|
81
|
-
|
|
82
|
-
|
|
81
|
+
const value = asRecord(args)?.[name];
|
|
82
|
+
return typeof value === "number" ? value : undefined;
|
|
83
83
|
}
|
|
84
84
|
|
|
85
85
|
function invalidArgText(theme: RenderTheme): string {
|
|
86
|
-
|
|
86
|
+
return theme.fg("error", "[invalid arg]");
|
|
87
87
|
}
|
|
88
88
|
|
|
89
89
|
function shortenPath(path: string): string {
|
|
90
|
-
|
|
91
|
-
|
|
90
|
+
const home = homedir();
|
|
91
|
+
return home && path.startsWith(home) ? `~${path.slice(home.length)}` : path;
|
|
92
92
|
}
|
|
93
93
|
|
|
94
94
|
function formatToolTitle(toolName: string, theme: RenderTheme): string {
|
|
95
|
-
|
|
95
|
+
return theme.fg("toolTitle", theme.bold(toolName));
|
|
96
96
|
}
|
|
97
97
|
|
|
98
98
|
function formatPathArg(args: unknown, theme: RenderTheme, placeholder = "..."): string {
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
99
|
+
const path = firstStringArg(args, ["file_path", "path"]);
|
|
100
|
+
if (path === null) return invalidArgText(theme);
|
|
101
|
+
return path ? theme.fg("accent", shortenPath(path)) : theme.fg("toolOutput", placeholder);
|
|
102
102
|
}
|
|
103
103
|
|
|
104
104
|
function formatReadLineRange(args: unknown, theme: RenderTheme): string {
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
105
|
+
const offset = numberArg(args, "offset");
|
|
106
|
+
const limit = numberArg(args, "limit");
|
|
107
|
+
if (offset === undefined && limit === undefined) return "";
|
|
108
|
+
const startLine = offset ?? 1;
|
|
109
|
+
const endLine = limit !== undefined ? startLine + limit - 1 : "";
|
|
110
|
+
return theme.fg("warning", `:${startLine}${endLine ? `-${endLine}` : ""}`);
|
|
111
111
|
}
|
|
112
112
|
|
|
113
113
|
function formatQuietReadCall(args: unknown, theme: RenderTheme): string {
|
|
114
|
-
|
|
114
|
+
return `${formatToolTitle("read", theme)} ${formatPathArg(args, theme)}${formatReadLineRange(args, theme)}`;
|
|
115
115
|
}
|
|
116
116
|
|
|
117
117
|
function formatQuietBashCall(args: unknown, theme: RenderTheme): string {
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
118
|
+
const command = str(asRecord(args)?.command);
|
|
119
|
+
const timeout = numberArg(args, "timeout");
|
|
120
|
+
const commandDisplay =
|
|
121
|
+
command === null
|
|
122
|
+
? invalidArgText(theme)
|
|
123
|
+
: command
|
|
124
|
+
? theme.fg("toolTitle", theme.bold(command))
|
|
125
|
+
: theme.fg("toolOutput", "...");
|
|
126
|
+
const timeoutSuffix = timeout ? theme.fg("muted", ` (timeout ${timeout}s)`) : "";
|
|
127
|
+
return `${theme.fg("toolTitle", theme.bold("$"))} ${commandDisplay}${timeoutSuffix}`;
|
|
127
128
|
}
|
|
128
129
|
|
|
129
130
|
function formatSearchPath(rawPath: string | null, theme: RenderTheme): string {
|
|
130
|
-
|
|
131
|
+
return rawPath === null ? invalidArgText(theme) : shortenPath(rawPath || ".");
|
|
131
132
|
}
|
|
132
133
|
|
|
133
134
|
function formatQuietGrepCall(args: unknown, theme: RenderTheme): string {
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
135
|
+
const pattern = str(asRecord(args)?.pattern);
|
|
136
|
+
const rawPath = str(asRecord(args)?.path);
|
|
137
|
+
const glob = str(asRecord(args)?.glob);
|
|
138
|
+
const limit = numberArg(args, "limit");
|
|
139
|
+
let text = `${formatToolTitle("grep", theme)} ${
|
|
140
|
+
pattern === null ? invalidArgText(theme) : theme.fg("accent", `/${pattern || ""}/`)
|
|
141
|
+
}${theme.fg("toolOutput", ` in ${formatSearchPath(rawPath, theme)}`)}`;
|
|
142
|
+
if (glob) text += theme.fg("toolOutput", ` (${glob})`);
|
|
143
|
+
if (glob === null) text += ` ${invalidArgText(theme)}`;
|
|
144
|
+
if (limit !== undefined) text += theme.fg("toolOutput", ` limit ${limit}`);
|
|
145
|
+
return text;
|
|
145
146
|
}
|
|
146
147
|
|
|
147
148
|
function formatQuietFindCall(args: unknown, theme: RenderTheme): string {
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
149
|
+
const pattern = str(asRecord(args)?.pattern);
|
|
150
|
+
const rawPath = str(asRecord(args)?.path);
|
|
151
|
+
const limit = numberArg(args, "limit");
|
|
152
|
+
let text = `${formatToolTitle("find", theme)} ${
|
|
153
|
+
pattern === null ? invalidArgText(theme) : theme.fg("accent", pattern || "")
|
|
154
|
+
}${theme.fg("toolOutput", ` in ${formatSearchPath(rawPath, theme)}`)}`;
|
|
155
|
+
if (limit !== undefined) text += theme.fg("toolOutput", ` (limit ${limit})`);
|
|
156
|
+
return text;
|
|
156
157
|
}
|
|
157
158
|
|
|
158
159
|
function formatQuietLsCall(args: unknown, theme: RenderTheme): string {
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
160
|
+
const rawPath = str(asRecord(args)?.path);
|
|
161
|
+
const limit = numberArg(args, "limit");
|
|
162
|
+
let text = `${formatToolTitle("ls", theme)} ${
|
|
163
|
+
rawPath === null ? invalidArgText(theme) : theme.fg("accent", shortenPath(rawPath || "."))
|
|
164
|
+
}`;
|
|
165
|
+
if (limit !== undefined) text += theme.fg("toolOutput", ` (limit ${limit})`);
|
|
166
|
+
return text;
|
|
166
167
|
}
|
|
167
168
|
|
|
168
|
-
function formatQuietPathOnlyCall(
|
|
169
|
-
|
|
169
|
+
function formatQuietPathOnlyCall(
|
|
170
|
+
toolName: "edit" | "write",
|
|
171
|
+
args: unknown,
|
|
172
|
+
theme: RenderTheme,
|
|
173
|
+
): string {
|
|
174
|
+
return `${formatToolTitle(toolName, theme)} ${formatPathArg(args, theme)}`;
|
|
170
175
|
}
|
|
171
176
|
|
|
172
177
|
function formatQuietCallLine(toolName: string, args: unknown, theme: RenderTheme): string {
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
178
|
+
switch (toolName) {
|
|
179
|
+
case "bash":
|
|
180
|
+
return formatQuietBashCall(args, theme);
|
|
181
|
+
case "edit":
|
|
182
|
+
return formatQuietPathOnlyCall("edit", args, theme);
|
|
183
|
+
case "find":
|
|
184
|
+
return formatQuietFindCall(args, theme);
|
|
185
|
+
case "grep":
|
|
186
|
+
return formatQuietGrepCall(args, theme);
|
|
187
|
+
case "ls":
|
|
188
|
+
return formatQuietLsCall(args, theme);
|
|
189
|
+
case "read":
|
|
190
|
+
return formatQuietReadCall(args, theme);
|
|
191
|
+
case "write":
|
|
192
|
+
return formatQuietPathOnlyCall("write", args, theme);
|
|
193
|
+
default:
|
|
194
|
+
return formatToolTitle(toolName, theme);
|
|
195
|
+
}
|
|
191
196
|
}
|
|
192
197
|
|
|
193
198
|
function formatExpandHint(theme: RenderTheme): string {
|
|
194
|
-
|
|
199
|
+
return `${theme.fg("muted", "(")}${keyHint("app.tools.expand", "to expand")}${theme.fg("muted", ")")}`;
|
|
195
200
|
}
|
|
196
201
|
|
|
197
202
|
function markToolTiming(options: ToolRenderResultParams[1], context: ToolRenderContext): void {
|
|
198
|
-
|
|
203
|
+
const state = context.state as TimerRenderState;
|
|
199
204
|
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
205
|
+
if ((!options.isPartial || context.isError) && state.startedAt !== undefined) {
|
|
206
|
+
state.endedAt ??= Date.now();
|
|
207
|
+
}
|
|
203
208
|
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
209
|
+
if ((!options.isPartial || context.isError) && state.interval) {
|
|
210
|
+
clearInterval(state.interval);
|
|
211
|
+
state.interval = undefined;
|
|
212
|
+
}
|
|
208
213
|
}
|
|
209
214
|
|
|
210
215
|
function renderQuietCollapsedResult(
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
216
|
+
_result: ToolRenderResultParams[0],
|
|
217
|
+
options: ToolRenderResultParams[1],
|
|
218
|
+
_theme: RenderTheme,
|
|
219
|
+
context: ToolRenderContext,
|
|
215
220
|
): QuietResultRenderComponent {
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
221
|
+
markToolTiming(options, context);
|
|
222
|
+
const component =
|
|
223
|
+
context.lastComponent instanceof QuietResultRenderComponent
|
|
224
|
+
? context.lastComponent
|
|
225
|
+
: new QuietResultRenderComponent();
|
|
226
|
+
component.setLinesRenderer(() => []);
|
|
227
|
+
return component;
|
|
222
228
|
}
|
|
223
229
|
|
|
224
230
|
function renderQuietCall(
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
231
|
+
toolName: string,
|
|
232
|
+
base: ToolDefinition,
|
|
233
|
+
args: ToolRenderCallParams[0],
|
|
234
|
+
theme: ToolRenderCallParams[1],
|
|
235
|
+
context: ToolRenderCallParams[2],
|
|
230
236
|
) {
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
237
|
+
const state = context.state as TimerRenderState;
|
|
238
|
+
if (context.executionStarted && state.startedAt === undefined) {
|
|
239
|
+
state.startedAt = Date.now();
|
|
240
|
+
state.endedAt = undefined;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
if (context.expanded || !QUIET_CALL_TOOL_NAMES.has(toolName)) {
|
|
244
|
+
const delegateContext =
|
|
245
|
+
context.lastComponent instanceof QuietCallRenderComponent
|
|
246
|
+
? { ...context, lastComponent: undefined }
|
|
247
|
+
: context;
|
|
248
|
+
return (
|
|
249
|
+
base.renderCall?.(args, theme, delegateContext) ??
|
|
250
|
+
new Text(theme.fg("toolTitle", theme.bold(toolName)), 0, 0)
|
|
251
|
+
);
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
const component =
|
|
255
|
+
context.lastComponent instanceof QuietCallRenderComponent
|
|
256
|
+
? context.lastComponent
|
|
257
|
+
: new QuietCallRenderComponent();
|
|
258
|
+
const line = formatQuietCallLine(toolName, args, theme);
|
|
259
|
+
const hint = formatExpandHint(theme);
|
|
260
|
+
component.setLinesRenderer((width) => [
|
|
261
|
+
truncateToWidth(line, width, "..."),
|
|
262
|
+
truncateToWidth(hint, width, "..."),
|
|
263
|
+
]);
|
|
264
|
+
return component;
|
|
254
265
|
}
|
|
255
266
|
|
|
256
267
|
function createQuietToolDefinition(base: ToolDefinition): ToolDefinition {
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
268
|
+
const baseRenderResult = base.renderResult;
|
|
269
|
+
|
|
270
|
+
return {
|
|
271
|
+
...base,
|
|
272
|
+
renderCall(args, theme, context) {
|
|
273
|
+
return renderQuietCall(base.name, base, args, theme, context);
|
|
274
|
+
},
|
|
275
|
+
renderResult(result, options, theme, context) {
|
|
276
|
+
if (options.expanded && baseRenderResult) {
|
|
277
|
+
const delegateContext =
|
|
278
|
+
context.lastComponent instanceof QuietResultRenderComponent
|
|
279
|
+
? { ...context, lastComponent: undefined }
|
|
280
|
+
: context;
|
|
281
|
+
return baseRenderResult(result, options, theme, delegateContext);
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
return renderQuietCollapsedResult(result, options, theme, context);
|
|
285
|
+
},
|
|
286
|
+
};
|
|
275
287
|
}
|
|
276
288
|
|
|
277
289
|
function createBaseToolOptions(cwd: string): ToolsOptions | undefined {
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
+
try {
|
|
291
|
+
const settings = SettingsManager.create(cwd);
|
|
292
|
+
return {
|
|
293
|
+
read: { autoResizeImages: settings.getImageAutoResize() },
|
|
294
|
+
bash: {
|
|
295
|
+
commandPrefix: settings.getShellCommandPrefix(),
|
|
296
|
+
shellPath: settings.getShellPath(),
|
|
297
|
+
},
|
|
298
|
+
};
|
|
299
|
+
} catch {
|
|
300
|
+
return undefined;
|
|
301
|
+
}
|
|
290
302
|
}
|
|
291
303
|
|
|
292
304
|
function createBaseToolDefinitions(cwd: string): ToolDefinition[] {
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
305
|
+
const options = createBaseToolOptions(cwd);
|
|
306
|
+
return [
|
|
307
|
+
createReadToolDefinition(cwd, options?.read),
|
|
308
|
+
createBashToolDefinition(cwd, options?.bash),
|
|
309
|
+
createEditToolDefinition(cwd, options?.edit),
|
|
310
|
+
createWriteToolDefinition(cwd, options?.write),
|
|
311
|
+
createGrepToolDefinition(cwd, options?.grep),
|
|
312
|
+
createFindToolDefinition(cwd, options?.find),
|
|
313
|
+
createLsToolDefinition(cwd, options?.ls),
|
|
314
|
+
] as ToolDefinition[];
|
|
303
315
|
}
|
|
304
316
|
|
|
305
317
|
function createQuietToolDefinitions(cwd: string, enabled: boolean): ToolDefinition[] {
|
|
306
|
-
|
|
307
|
-
|
|
318
|
+
const baseDefinitions = createBaseToolDefinitions(cwd);
|
|
319
|
+
return enabled ? baseDefinitions.map(createQuietToolDefinition) : baseDefinitions;
|
|
308
320
|
}
|
|
309
321
|
|
|
310
322
|
export const __testing = {
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
323
|
+
sanitizeInlineText,
|
|
324
|
+
formatQuietCallLine,
|
|
325
|
+
createQuietToolDefinition,
|
|
314
326
|
};
|
|
315
327
|
|
|
316
328
|
export default function quietToolsExtension(pi: ExtensionAPI) {
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
329
|
+
let enabled = true;
|
|
330
|
+
|
|
331
|
+
function registerTools(cwd: string): void {
|
|
332
|
+
for (const tool of createQuietToolDefinitions(cwd, enabled)) {
|
|
333
|
+
pi.registerTool(tool);
|
|
334
|
+
}
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
pi.on("session_start", async (_event, ctx) => {
|
|
338
|
+
registerTools(ctx.cwd);
|
|
339
|
+
});
|
|
340
|
+
|
|
341
|
+
pi.registerCommand("quiet-tools", {
|
|
342
|
+
description: "Toggle one-line collapsed invocations for built-in tool rows",
|
|
343
|
+
getArgumentCompletions: (prefix) => {
|
|
344
|
+
const commands = ["on", "off", "toggle", "status"];
|
|
345
|
+
const query = prefix.trim().toLowerCase();
|
|
346
|
+
const matches = commands.filter((command) => command.startsWith(query));
|
|
347
|
+
return matches.length > 0 ? matches.map((value) => ({ value, label: value })) : null;
|
|
348
|
+
},
|
|
349
|
+
handler: async (args, ctx) => {
|
|
350
|
+
const action = args.trim().toLowerCase() || "toggle";
|
|
351
|
+
|
|
352
|
+
if (action === "on" || action === "enable") {
|
|
353
|
+
enabled = true;
|
|
354
|
+
registerTools(ctx.cwd);
|
|
355
|
+
ctx.ui.notify(
|
|
356
|
+
"Quiet tool previews enabled: collapsed built-in tool rows show a one-line invocation plus an expand hint.",
|
|
357
|
+
"info",
|
|
358
|
+
);
|
|
359
|
+
return;
|
|
360
|
+
}
|
|
361
|
+
|
|
362
|
+
if (action === "off" || action === "disable") {
|
|
363
|
+
enabled = false;
|
|
364
|
+
registerTools(ctx.cwd);
|
|
365
|
+
ctx.ui.notify(
|
|
366
|
+
"Quiet tool previews disabled: restored pi's standard built-in tool renderers.",
|
|
367
|
+
"info",
|
|
368
|
+
);
|
|
369
|
+
return;
|
|
370
|
+
}
|
|
371
|
+
|
|
372
|
+
if (action === "toggle") {
|
|
373
|
+
enabled = !enabled;
|
|
374
|
+
registerTools(ctx.cwd);
|
|
375
|
+
ctx.ui.notify(
|
|
376
|
+
enabled
|
|
377
|
+
? "Quiet tool previews enabled: collapsed built-in tool rows show a one-line invocation plus an expand hint."
|
|
378
|
+
: "Quiet tool previews disabled: restored pi's standard built-in tool renderers.",
|
|
379
|
+
"info",
|
|
380
|
+
);
|
|
381
|
+
return;
|
|
382
|
+
}
|
|
383
|
+
|
|
384
|
+
if (action === "status") {
|
|
385
|
+
ctx.ui.notify(
|
|
386
|
+
`Quiet tool previews are ${enabled ? "enabled" : "disabled"}. Collapsed tool rows ${enabled ? "show a one-line invocation and hide output until expanded" : "use pi's default rendering"}. Model-visible tool results are unchanged.`,
|
|
387
|
+
"info",
|
|
388
|
+
);
|
|
389
|
+
return;
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
ctx.ui.notify("Usage: /quiet-tools on | off | toggle | status", "warning");
|
|
393
|
+
},
|
|
394
|
+
});
|
|
377
395
|
}
|