@fradser/pi-context 0.6.1 → 0.6.3
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 +21 -0
- package/extensions/context-command.ts +1 -1
- package/extensions/context-tools.ts +18 -21
- package/package.json +2 -2
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Frad LEE
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -3,7 +3,7 @@ import type { ExtensionAPI } from "@earendil-works/pi-coding-agent";
|
|
|
3
3
|
const CONTEXT_GUIDANCE = `
|
|
4
4
|
## Isolated research
|
|
5
5
|
|
|
6
|
-
|
|
6
|
+
For questions about an external repository, library, codebase, or current technical topic, call \`context_get\` instead of researching inline. Research then stays out of the main session.
|
|
7
7
|
`;
|
|
8
8
|
|
|
9
9
|
export function registerContextGuidance(pi: ExtensionAPI): void {
|
|
@@ -1,8 +1,9 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { type Component,
|
|
1
|
+
import { keyHint, type ExtensionAPI } from "@earendil-works/pi-coding-agent";
|
|
2
|
+
import { type Component, Text, truncateToWidth, visibleWidth, wrapTextWithAnsi } from "@earendil-works/pi-tui";
|
|
3
3
|
import {
|
|
4
|
+
bindLifecycleRenderers,
|
|
5
|
+
contentDetailLines,
|
|
4
6
|
createLiveActivityWidget,
|
|
5
|
-
createStaticToolLifecycleResultRenderer,
|
|
6
7
|
eventToolLifecycle,
|
|
7
8
|
runPiWorker,
|
|
8
9
|
type PiLiveWidgetContext,
|
|
@@ -12,6 +13,14 @@ import { Type } from "typebox";
|
|
|
12
13
|
import { buildContextResearchPrompt } from "./context-prompt.ts";
|
|
13
14
|
|
|
14
15
|
const RESEARCH_TOOLS = ["read", "bash"];
|
|
16
|
+
|
|
17
|
+
/** Geometry bound once: the research row shares hint and wrapping. */
|
|
18
|
+
const contextRows = bindLifecycleRenderers({
|
|
19
|
+
fit: truncateToWidth,
|
|
20
|
+
visibleWidth,
|
|
21
|
+
wrapDetail: (line, width) => wrapTextWithAnsi(line, Math.max(1, width)),
|
|
22
|
+
expandHint: () => keyHint("app.tools.expand", "to expand"),
|
|
23
|
+
});
|
|
15
24
|
const FINAL_ANSWER_RETRY_INSTRUCTION = `
|
|
16
25
|
|
|
17
26
|
Completion requirement: the previous attempt produced no textual final answer. Complete the original research request now without relying on hidden reasoning, transient tool output, or state from the prior attempt; repeat any inspection needed to support the answer. Your final assistant message must be a self-contained plain-text answer with the conclusion and concrete evidence. Do not finish immediately after a tool call.`;
|
|
@@ -64,10 +73,6 @@ function renderContextCall(
|
|
|
64
73
|
};
|
|
65
74
|
}
|
|
66
75
|
|
|
67
|
-
function resultText(result: ToolTextResult): string {
|
|
68
|
-
return result.content.find((part) => part.type === "text")?.text ?? "";
|
|
69
|
-
}
|
|
70
|
-
|
|
71
76
|
export function buildResearchPrompt(query: string, finalAnswerRetry = false): string {
|
|
72
77
|
const prompt = buildContextResearchPrompt({
|
|
73
78
|
userResearchRequest: query,
|
|
@@ -87,14 +92,14 @@ interface ActiveResearch {
|
|
|
87
92
|
|
|
88
93
|
let researchToken = 0;
|
|
89
94
|
let activeResearch: ActiveResearch | undefined;
|
|
95
|
+
// Identity, marker, and activity rendering all come from pi-kit, so this
|
|
96
|
+
// widget uses the same row language as every other package's status row; the
|
|
97
|
+
// activity format is the only per-package choice.
|
|
90
98
|
const researchWidget = createLiveActivityWidget({
|
|
91
99
|
key: "context-research",
|
|
92
100
|
placement: "aboveEditor",
|
|
93
101
|
fit: truncateToWidth,
|
|
94
|
-
|
|
95
|
-
formatActivity: (activity, theme) => new Markdown(
|
|
96
|
-
activity, 0, 0, getMarkdownTheme(), { color: (text) => theme.fg("accent", text) },
|
|
97
|
-
).render(Math.max(1, visibleWidth(activity))).map((line) => line.trim()).filter(Boolean).join(" "),
|
|
102
|
+
activityFormat: "markdown",
|
|
98
103
|
});
|
|
99
104
|
|
|
100
105
|
/** Show the running-research status above the editor; returns a token for updates/clear. */
|
|
@@ -186,20 +191,12 @@ export function registerContextTools(pi: ExtensionAPI): void {
|
|
|
186
191
|
}
|
|
187
192
|
const query = (context.args as { query?: string })?.query;
|
|
188
193
|
const subject = formatResearchSubject(query);
|
|
189
|
-
const text = resultText(result as ToolTextResult);
|
|
190
|
-
const details = text.split("\n").map((line) => line.trim()).filter(Boolean);
|
|
191
194
|
const spec = eventToolLifecycle("context", subject, {
|
|
192
195
|
label: "researched",
|
|
193
|
-
details,
|
|
196
|
+
details: contentDetailLines(result),
|
|
194
197
|
detailLimit: "all",
|
|
195
198
|
});
|
|
196
|
-
return
|
|
197
|
-
createSpec: () => spec,
|
|
198
|
-
expandHint: keyHint("app.tools.expand", "to expand"),
|
|
199
|
-
fit: truncateToWidth,
|
|
200
|
-
visibleWidth,
|
|
201
|
-
wrapDetail: (line, width) => wrapTextWithAnsi(line, Math.max(1, width)),
|
|
202
|
-
})(result as ToolTextResult, options, theme, context);
|
|
199
|
+
return contextRows.result(() => spec)(result as ToolTextResult, options, theme, context);
|
|
203
200
|
},
|
|
204
201
|
async execute(_toolCallId, params, signal, onUpdate, ctx) {
|
|
205
202
|
const widget = startResearchWidget(ctx as ResearchWidgetContext | undefined);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fradser/pi-context",
|
|
3
|
-
"version": "0.6.
|
|
3
|
+
"version": "0.6.3",
|
|
4
4
|
"description": "Retrieve context for repositories, libraries, and technical questions with one native tool that launches an isolated prompt-constrained Pi research child.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"pi-package",
|
|
@@ -36,6 +36,6 @@
|
|
|
36
36
|
"typebox": "*"
|
|
37
37
|
},
|
|
38
38
|
"dependencies": {
|
|
39
|
-
"@fradser/pi-kit": "0.
|
|
39
|
+
"@fradser/pi-kit": "0.5.1"
|
|
40
40
|
}
|
|
41
41
|
}
|