@caupulican/pi-adaptative 0.84.1 → 0.85.0
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 +28 -0
- package/dist/bundled-resources/extensions/tmux-agent-manager/index.d.ts.map +1 -1
- package/dist/bundled-resources/extensions/tmux-agent-manager/index.js +14 -8
- package/dist/bundled-resources/extensions/tmux-agent-manager/index.js.map +1 -1
- package/dist/bundled-resources/extensions/tmux-agent-manager/index.ts +14 -8
- package/dist/bundled-resources/skills/deduplicate-by-evidence/SKILL.md +7 -5
- package/dist/bundled-resources/skills/worker-profile-writer/SKILL.md +63 -0
- package/dist/core/autonomy/lane-tool-surface.d.ts.map +1 -1
- package/dist/core/autonomy/lane-tool-surface.js +4 -2
- package/dist/core/autonomy/lane-tool-surface.js.map +1 -1
- package/dist/core/background-lane-controller.d.ts +3 -0
- package/dist/core/background-lane-controller.d.ts.map +1 -1
- package/dist/core/background-lane-controller.js +6 -0
- package/dist/core/background-lane-controller.js.map +1 -1
- package/dist/core/default-tool-surface.d.ts.map +1 -1
- package/dist/core/default-tool-surface.js +1 -0
- package/dist/core/default-tool-surface.js.map +1 -1
- package/dist/core/delegation/worker-delegation-controller.d.ts +7 -0
- package/dist/core/delegation/worker-delegation-controller.d.ts.map +1 -1
- package/dist/core/delegation/worker-delegation-controller.js +28 -0
- package/dist/core/delegation/worker-delegation-controller.js.map +1 -1
- package/dist/core/delegation/worker-profile-resolver.d.ts +2 -0
- package/dist/core/delegation/worker-profile-resolver.d.ts.map +1 -1
- package/dist/core/delegation/worker-profile-resolver.js +46 -11
- package/dist/core/delegation/worker-profile-resolver.js.map +1 -1
- package/dist/core/doctor.d.ts +1 -1
- package/dist/core/doctor.d.ts.map +1 -1
- package/dist/core/doctor.js +5 -4
- package/dist/core/doctor.js.map +1 -1
- package/dist/core/model-capability.d.ts.map +1 -1
- package/dist/core/model-capability.js +1 -0
- package/dist/core/model-capability.js.map +1 -1
- package/dist/core/orchestration/lane-tool-manifests.d.ts +1 -1
- package/dist/core/orchestration/lane-tool-manifests.d.ts.map +1 -1
- package/dist/core/orchestration/lane-tool-manifests.js +6 -1
- package/dist/core/orchestration/lane-tool-manifests.js.map +1 -1
- package/dist/core/orchestration/session-task-profile-store.d.ts +31 -0
- package/dist/core/orchestration/session-task-profile-store.d.ts.map +1 -0
- package/dist/core/orchestration/session-task-profile-store.js +138 -0
- package/dist/core/orchestration/session-task-profile-store.js.map +1 -0
- package/dist/core/orchestration/task-profile-writer.d.ts +58 -0
- package/dist/core/orchestration/task-profile-writer.d.ts.map +1 -0
- package/dist/core/orchestration/task-profile-writer.js +165 -0
- package/dist/core/orchestration/task-profile-writer.js.map +1 -0
- package/dist/core/runtime-builder.d.ts +3 -1
- package/dist/core/runtime-builder.d.ts.map +1 -1
- package/dist/core/runtime-builder.js +14 -0
- package/dist/core/runtime-builder.js.map +1 -1
- package/dist/core/security/untrusted-boundary.d.ts.map +1 -1
- package/dist/core/security/untrusted-boundary.js +4 -6
- package/dist/core/security/untrusted-boundary.js.map +1 -1
- package/dist/core/session-role.d.ts.map +1 -1
- package/dist/core/session-role.js +1 -0
- package/dist/core/session-role.js.map +1 -1
- package/dist/core/system-prompt.d.ts.map +1 -1
- package/dist/core/system-prompt.js +21 -23
- package/dist/core/system-prompt.js.map +1 -1
- package/dist/core/tool-capability-policy.js +1 -1
- package/dist/core/tool-capability-policy.js.map +1 -1
- package/dist/core/tools/bash.d.ts +1 -6
- package/dist/core/tools/bash.d.ts.map +1 -1
- package/dist/core/tools/bash.js +2 -26
- package/dist/core/tools/bash.js.map +1 -1
- package/dist/core/tools/delegate.js +4 -4
- package/dist/core/tools/delegate.js.map +1 -1
- package/dist/core/tools/edit-diff.d.ts +32 -5
- package/dist/core/tools/edit-diff.d.ts.map +1 -1
- package/dist/core/tools/edit-diff.js +137 -69
- package/dist/core/tools/edit-diff.js.map +1 -1
- package/dist/core/tools/edit.d.ts +22 -7
- package/dist/core/tools/edit.d.ts.map +1 -1
- package/dist/core/tools/edit.js +128 -55
- package/dist/core/tools/edit.js.map +1 -1
- package/dist/core/tools/file-mutation-intent.d.ts +70 -0
- package/dist/core/tools/file-mutation-intent.d.ts.map +1 -0
- package/dist/core/tools/file-mutation-intent.js +325 -0
- package/dist/core/tools/file-mutation-intent.js.map +1 -0
- package/dist/core/tools/goal.d.ts.map +1 -1
- package/dist/core/tools/goal.js +41 -18
- package/dist/core/tools/goal.js.map +1 -1
- package/dist/core/tools/index.d.ts +3 -1
- package/dist/core/tools/index.d.ts.map +1 -1
- package/dist/core/tools/index.js +31 -8
- package/dist/core/tools/index.js.map +1 -1
- package/dist/core/tools/profile-writer.d.ts +33 -0
- package/dist/core/tools/profile-writer.d.ts.map +1 -0
- package/dist/core/tools/profile-writer.js +67 -0
- package/dist/core/tools/profile-writer.js.map +1 -0
- package/dist/core/tools/task-steps.d.ts.map +1 -1
- package/dist/core/tools/task-steps.js +6 -11
- package/dist/core/tools/task-steps.js.map +1 -1
- package/dist/core/tools/tmux-dispatch.d.ts +2 -0
- package/dist/core/tools/tmux-dispatch.d.ts.map +1 -1
- package/dist/core/tools/tmux-dispatch.js +16 -2
- package/dist/core/tools/tmux-dispatch.js.map +1 -1
- package/dist/core/tools/write.d.ts +24 -7
- package/dist/core/tools/write.d.ts.map +1 -1
- package/dist/core/tools/write.js +182 -107
- package/dist/core/tools/write.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/jscpd-cli.d.ts +3 -0
- package/dist/jscpd-cli.d.ts.map +1 -0
- package/dist/jscpd-cli.js +22 -0
- package/dist/jscpd-cli.js.map +1 -0
- package/dist/modes/interactive/components/profile-resource-editor.js +2 -2
- package/dist/modes/interactive/components/profile-resource-editor.js.map +1 -1
- package/dist/modes/interactive/components/tool-execution.d.ts +1 -0
- package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -1
- package/dist/modes/interactive/components/tool-execution.js +85 -3
- package/dist/modes/interactive/components/tool-execution.js.map +1 -1
- package/dist/modes/interactive/interactive-mode.js +1 -1
- package/dist/modes/interactive/interactive-mode.js.map +1 -1
- package/dist/utils/bundled-jscpd.d.ts +20 -0
- package/dist/utils/bundled-jscpd.d.ts.map +1 -0
- package/dist/utils/bundled-jscpd.js +154 -0
- package/dist/utils/bundled-jscpd.js.map +1 -0
- package/dist/utils/shell.d.ts.map +1 -1
- package/dist/utils/shell.js +11 -0
- package/dist/utils/shell.js.map +1 -1
- package/dist/utils/tools-manager.d.ts +1 -1
- package/dist/utils/tools-manager.d.ts.map +1 -1
- package/dist/utils/tools-manager.js +22 -0
- package/dist/utils/tools-manager.js.map +1 -1
- package/docs/index.md +3 -0
- package/docs/managed-data-tools.md +15 -0
- package/docs/quickstart.md +2 -2
- package/docs/tool-boundary-performance-roadmap-2026-08-02.md +166 -0
- package/docs/tool-repair.md +1 -1
- package/docs/worker-profiles.md +16 -0
- package/examples/extensions/built-in-tool-renderer.ts +12 -5
- package/examples/extensions/custom-provider-anthropic/package-lock.json +2 -2
- package/examples/extensions/custom-provider-anthropic/package.json +1 -1
- package/examples/extensions/custom-provider-gitlab-duo/package.json +1 -1
- package/examples/extensions/minimal-mode.ts +8 -7
- package/examples/extensions/prompt-customizer.ts +4 -2
- package/examples/extensions/sandbox/package-lock.json +2 -2
- package/examples/extensions/sandbox/package.json +1 -1
- package/examples/extensions/ssh.ts +113 -24
- package/examples/extensions/with-deps/package-lock.json +2 -2
- package/examples/extensions/with-deps/package.json +1 -1
- package/npm-shrinkwrap.json +112 -12
- package/package.json +7 -5
|
@@ -26,7 +26,13 @@
|
|
|
26
26
|
*/
|
|
27
27
|
|
|
28
28
|
import type { BashToolDetails, EditToolDetails, ExtensionAPI, ReadToolDetails } from "@caupulican/pi-adaptative";
|
|
29
|
-
import {
|
|
29
|
+
import {
|
|
30
|
+
createBashTool,
|
|
31
|
+
createEditTool,
|
|
32
|
+
createReadTool,
|
|
33
|
+
createWriteTool,
|
|
34
|
+
FileMutationIntentController,
|
|
35
|
+
} from "@caupulican/pi-adaptative";
|
|
30
36
|
import { Text } from "@caupulican/pi-tui";
|
|
31
37
|
|
|
32
38
|
export default function (pi: ExtensionAPI) {
|
|
@@ -151,7 +157,8 @@ export default function (pi: ExtensionAPI) {
|
|
|
151
157
|
});
|
|
152
158
|
|
|
153
159
|
// --- Edit tool: show path and diff stats ---
|
|
154
|
-
const
|
|
160
|
+
const fileMutationIntents = new FileMutationIntentController();
|
|
161
|
+
const originalEdit = createEditTool(cwd, { intentController: fileMutationIntents });
|
|
155
162
|
pi.registerTool({
|
|
156
163
|
name: "edit",
|
|
157
164
|
label: "edit",
|
|
@@ -216,7 +223,7 @@ export default function (pi: ExtensionAPI) {
|
|
|
216
223
|
});
|
|
217
224
|
|
|
218
225
|
// --- Write tool: show path and size ---
|
|
219
|
-
const originalWrite = createWriteTool(cwd);
|
|
226
|
+
const originalWrite = createWriteTool(cwd, { intentController: fileMutationIntents });
|
|
220
227
|
pi.registerTool({
|
|
221
228
|
name: "write",
|
|
222
229
|
label: "write",
|
|
@@ -230,8 +237,8 @@ export default function (pi: ExtensionAPI) {
|
|
|
230
237
|
renderCall(args, theme, _context) {
|
|
231
238
|
let text = theme.fg("toolTitle", theme.bold("write "));
|
|
232
239
|
text += theme.fg("accent", args.path);
|
|
233
|
-
const
|
|
234
|
-
text += theme.fg("dim", ` (${
|
|
240
|
+
const writeContent = args.action === "commit" && "content" in args ? args.content : undefined;
|
|
241
|
+
if (writeContent) text += theme.fg("dim", ` (${writeContent.length} characters)`);
|
|
235
242
|
return new Text(text, 0, 0);
|
|
236
243
|
},
|
|
237
244
|
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pi-extension-custom-provider",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.85.0",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "pi-extension-custom-provider",
|
|
9
|
-
"version": "0.
|
|
9
|
+
"version": "0.85.0",
|
|
10
10
|
"dependencies": {
|
|
11
11
|
"@anthropic-ai/sdk": "^0.52.0"
|
|
12
12
|
}
|
|
@@ -25,6 +25,7 @@ import {
|
|
|
25
25
|
createLsTool,
|
|
26
26
|
createReadTool,
|
|
27
27
|
createWriteTool,
|
|
28
|
+
FileMutationIntentController,
|
|
28
29
|
} from "@caupulican/pi-adaptative";
|
|
29
30
|
import { Text } from "@caupulican/pi-tui";
|
|
30
31
|
import { homedir } from "os";
|
|
@@ -44,11 +45,12 @@ function shortenPath(path: string): string {
|
|
|
44
45
|
const toolCache = new Map<string, ReturnType<typeof createBuiltInTools>>();
|
|
45
46
|
|
|
46
47
|
function createBuiltInTools(cwd: string) {
|
|
48
|
+
const fileMutationIntents = new FileMutationIntentController();
|
|
47
49
|
return {
|
|
48
50
|
read: createReadTool(cwd),
|
|
49
51
|
bash: createBashTool(cwd),
|
|
50
|
-
edit: createEditTool(cwd),
|
|
51
|
-
write: createWriteTool(cwd),
|
|
52
|
+
edit: createEditTool(cwd, { intentController: fileMutationIntents }),
|
|
53
|
+
write: createWriteTool(cwd, { intentController: fileMutationIntents }),
|
|
52
54
|
find: createFindTool(cwd),
|
|
53
55
|
grep: createGrepTool(cwd),
|
|
54
56
|
ls: createLsTool(cwd),
|
|
@@ -167,8 +169,7 @@ export default function (pi: ExtensionAPI) {
|
|
|
167
169
|
pi.registerTool({
|
|
168
170
|
name: "write",
|
|
169
171
|
label: "write",
|
|
170
|
-
description:
|
|
171
|
-
"Write content to a file. Creates the file if it doesn't exist, overwrites if it does. Automatically creates parent directories.",
|
|
172
|
+
description: "Create a new file through path-only preflight. Existing paths are never overwritten.",
|
|
172
173
|
parameters: getBuiltInTools(process.cwd()).write.parameters,
|
|
173
174
|
|
|
174
175
|
async execute(toolCallId, params, signal, onUpdate, ctx) {
|
|
@@ -179,10 +180,10 @@ export default function (pi: ExtensionAPI) {
|
|
|
179
180
|
renderCall(args, theme, _context) {
|
|
180
181
|
const path = shortenPath(args.path || "");
|
|
181
182
|
const pathDisplay = path ? theme.fg("accent", path) : theme.fg("toolOutput", "...");
|
|
182
|
-
const
|
|
183
|
-
const
|
|
183
|
+
const writeContent = args.action === "commit" && "content" in args ? args.content : undefined;
|
|
184
|
+
const sizeInfo = writeContent ? theme.fg("muted", ` (${writeContent.length} characters)`) : "";
|
|
184
185
|
|
|
185
|
-
return new Text(`${theme.fg("toolTitle", theme.bold("write"))} ${pathDisplay}${
|
|
186
|
+
return new Text(`${theme.fg("toolTitle", theme.bold("write"))} ${pathDisplay}${sizeInfo}`, 0, 0);
|
|
186
187
|
},
|
|
187
188
|
|
|
188
189
|
renderResult(result, { expanded }, theme, _context) {
|
|
@@ -37,12 +37,14 @@ function addToolGuidance(options: BuildSystemPromptOptions, basePrompt: string):
|
|
|
37
37
|
|
|
38
38
|
if (hasTool("edit")) {
|
|
39
39
|
parts.push(
|
|
40
|
-
"• Use
|
|
40
|
+
"• Use `edit` action=prepare before generating precise replacements, then commit with the returned intent. Match exact content including whitespace.",
|
|
41
41
|
);
|
|
42
42
|
}
|
|
43
43
|
|
|
44
44
|
if (hasTool("write")) {
|
|
45
|
-
parts.push(
|
|
45
|
+
parts.push(
|
|
46
|
+
"• Use `write` action=prepare before generating content; commit creates a new file and never overwrites.",
|
|
47
|
+
);
|
|
46
48
|
}
|
|
47
49
|
|
|
48
50
|
if (options.skills && options.skills.length > 0) {
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pi-extension-sandbox",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.85.0",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "pi-extension-sandbox",
|
|
9
|
-
"version": "0.
|
|
9
|
+
"version": "0.85.0",
|
|
10
10
|
"dependencies": {
|
|
11
11
|
"@anthropic-ai/sandbox-runtime": "^0.0.26"
|
|
12
12
|
}
|
|
@@ -10,10 +10,11 @@
|
|
|
10
10
|
*
|
|
11
11
|
* Requirements:
|
|
12
12
|
* - SSH key-based auth (no password prompts)
|
|
13
|
-
* - bash on remote
|
|
13
|
+
* - bash and GNU coreutils (sha256sum, stat) on remote
|
|
14
14
|
*/
|
|
15
15
|
|
|
16
16
|
import { spawn } from "node:child_process";
|
|
17
|
+
import { constants } from "node:fs";
|
|
17
18
|
import type { ExtensionAPI } from "@caupulican/pi-adaptative";
|
|
18
19
|
import {
|
|
19
20
|
type BashOperations,
|
|
@@ -22,13 +23,20 @@ import {
|
|
|
22
23
|
createReadTool,
|
|
23
24
|
createWriteTool,
|
|
24
25
|
type EditOperations,
|
|
26
|
+
FileMutationIntentController,
|
|
27
|
+
type FileMutationIntentOperations,
|
|
28
|
+
type FilePathInspection,
|
|
25
29
|
type ReadOperations,
|
|
26
30
|
type WriteOperations,
|
|
27
31
|
} from "@caupulican/pi-adaptative";
|
|
28
32
|
|
|
29
|
-
function
|
|
33
|
+
function shellQuote(value: string): string {
|
|
34
|
+
return `'${value.replaceAll("'", `'"'"'`)}'`;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
function sshExec(remote: string, command: string, stdin?: string | Buffer): Promise<Buffer> {
|
|
30
38
|
return new Promise((resolve, reject) => {
|
|
31
|
-
const child = spawn("ssh", [remote, command], { stdio: ["
|
|
39
|
+
const child = spawn("ssh", [remote, command], { stdio: ["pipe", "pipe", "pipe"] });
|
|
32
40
|
const chunks: Buffer[] = [];
|
|
33
41
|
const errChunks: Buffer[] = [];
|
|
34
42
|
child.stdout.on("data", (data) => chunks.push(data));
|
|
@@ -41,17 +49,18 @@ function sshExec(remote: string, command: string): Promise<Buffer> {
|
|
|
41
49
|
resolve(Buffer.concat(chunks));
|
|
42
50
|
}
|
|
43
51
|
});
|
|
52
|
+
child.stdin.end(stdin);
|
|
44
53
|
});
|
|
45
54
|
}
|
|
46
55
|
|
|
47
56
|
function createRemoteReadOps(remote: string, remoteCwd: string, localCwd: string): ReadOperations {
|
|
48
57
|
const toRemote = (p: string) => p.replace(localCwd, remoteCwd);
|
|
49
58
|
return {
|
|
50
|
-
readFile: (p) => sshExec(remote, `cat ${
|
|
51
|
-
access: (p) => sshExec(remote, `test -r ${
|
|
59
|
+
readFile: (p) => sshExec(remote, `cat -- ${shellQuote(toRemote(p))}`),
|
|
60
|
+
access: (p) => sshExec(remote, `test -r ${shellQuote(toRemote(p))}`).then(() => {}),
|
|
52
61
|
detectImageMimeType: async (p) => {
|
|
53
62
|
try {
|
|
54
|
-
const r = await sshExec(remote, `file --mime-type -b ${
|
|
63
|
+
const r = await sshExec(remote, `file --mime-type -b -- ${shellQuote(toRemote(p))}`);
|
|
55
64
|
const m = r.toString().trim();
|
|
56
65
|
return ["image/jpeg", "image/png", "image/gif", "image/webp"].includes(m) ? m : null;
|
|
57
66
|
} catch {
|
|
@@ -61,21 +70,86 @@ function createRemoteReadOps(remote: string, remoteCwd: string, localCwd: string
|
|
|
61
70
|
};
|
|
62
71
|
}
|
|
63
72
|
|
|
73
|
+
async function writeRemoteContent(remote: string, path: string, content: string, exclusive: boolean): Promise<void> {
|
|
74
|
+
const noClobber = exclusive ? "set -o noclobber; " : "";
|
|
75
|
+
await sshExec(remote, `${noClobber}cat > ${shellQuote(path)}`, content);
|
|
76
|
+
}
|
|
77
|
+
|
|
64
78
|
function createRemoteWriteOps(remote: string, remoteCwd: string, localCwd: string): WriteOperations {
|
|
65
79
|
const toRemote = (p: string) => p.replace(localCwd, remoteCwd);
|
|
66
80
|
return {
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
await sshExec(remote, `echo ${JSON.stringify(b64)} | base64 -d > ${JSON.stringify(toRemote(p))}`);
|
|
70
|
-
},
|
|
71
|
-
mkdir: (dir) => sshExec(remote, `mkdir -p ${JSON.stringify(toRemote(dir))}`).then(() => {}),
|
|
81
|
+
createFile: (p, content) => writeRemoteContent(remote, toRemote(p), content, true),
|
|
82
|
+
mkdir: (dir) => sshExec(remote, `mkdir -p -- ${shellQuote(toRemote(dir))}`).then(() => {}),
|
|
72
83
|
};
|
|
73
84
|
}
|
|
74
85
|
|
|
75
86
|
function createRemoteEditOps(remote: string, remoteCwd: string, localCwd: string): EditOperations {
|
|
76
87
|
const r = createRemoteReadOps(remote, remoteCwd, localCwd);
|
|
77
|
-
const
|
|
78
|
-
return {
|
|
88
|
+
const toRemote = (p: string) => p.replace(localCwd, remoteCwd);
|
|
89
|
+
return {
|
|
90
|
+
readFile: r.readFile,
|
|
91
|
+
writeFile: (p, content) => writeRemoteContent(remote, toRemote(p), content, false),
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
function createRemoteIntentOps(remote: string, remoteCwd: string, localCwd: string): FileMutationIntentOperations {
|
|
96
|
+
const toRemote = (p: string) => p.replace(localCwd, remoteCwd);
|
|
97
|
+
return {
|
|
98
|
+
async inspect(p, followSymlinks): Promise<FilePathInspection | undefined> {
|
|
99
|
+
const path = shellQuote(toRemote(p));
|
|
100
|
+
const kind = followSymlinks
|
|
101
|
+
? `if [ -f ${path} ]; then printf 'file\\t'; elif [ -d ${path} ]; then printf 'directory\\t'; elif [ -e ${path} ]; then printf 'other\\t'; else exit 44; fi`
|
|
102
|
+
: `if [ -L ${path} ]; then printf 'other\\t'; elif [ -f ${path} ]; then printf 'file\\t'; elif [ -d ${path} ]; then printf 'directory\\t'; elif [ -e ${path} ]; then printf 'other\\t'; else exit 44; fi`;
|
|
103
|
+
const follow = followSymlinks ? "-L " : "";
|
|
104
|
+
try {
|
|
105
|
+
const output = (
|
|
106
|
+
await sshExec(
|
|
107
|
+
remote,
|
|
108
|
+
`${kind}; stat ${follow}--printf ${shellQuote("%d\\t%i\\t%f\\t%s\\t%y\\t%z")} -- ${path}`,
|
|
109
|
+
)
|
|
110
|
+
)
|
|
111
|
+
.toString("utf8")
|
|
112
|
+
.trimEnd();
|
|
113
|
+
const [entryKind, dev, ino, mode, size, mtimeMs, ctimeMs] = output.split("\t");
|
|
114
|
+
if (
|
|
115
|
+
(entryKind !== "file" && entryKind !== "directory" && entryKind !== "other") ||
|
|
116
|
+
!dev ||
|
|
117
|
+
!ino ||
|
|
118
|
+
!mode ||
|
|
119
|
+
!size ||
|
|
120
|
+
!mtimeMs ||
|
|
121
|
+
!ctimeMs
|
|
122
|
+
) {
|
|
123
|
+
throw new Error(`Unexpected remote stat response for ${p}`);
|
|
124
|
+
}
|
|
125
|
+
return { kind: entryKind, identity: { dev, ino, mode, size, mtimeMs, ctimeMs } };
|
|
126
|
+
} catch (error) {
|
|
127
|
+
if (String(error).includes("SSH failed (44)")) return undefined;
|
|
128
|
+
throw error;
|
|
129
|
+
}
|
|
130
|
+
},
|
|
131
|
+
access(p, mode) {
|
|
132
|
+
const path = shellQuote(toRemote(p));
|
|
133
|
+
const checks = [
|
|
134
|
+
mode & constants.R_OK ? `test -r ${path}` : undefined,
|
|
135
|
+
mode & constants.W_OK ? `test -w ${path}` : undefined,
|
|
136
|
+
].filter((check): check is string => check !== undefined);
|
|
137
|
+
return sshExec(remote, checks.length > 0 ? checks.join(" && ") : `test -e ${path}`).then(() => {});
|
|
138
|
+
},
|
|
139
|
+
copyFileExclusive(sourcePath, targetPath) {
|
|
140
|
+
return sshExec(
|
|
141
|
+
remote,
|
|
142
|
+
`set -o noclobber; cat -- ${shellQuote(toRemote(sourcePath))} > ${shellQuote(toRemote(targetPath))}`,
|
|
143
|
+
).then(() => {});
|
|
144
|
+
},
|
|
145
|
+
async hashFile(p) {
|
|
146
|
+
const output = await sshExec(remote, `sha256sum -- ${shellQuote(toRemote(p))}`);
|
|
147
|
+
const digest = output.toString("utf8").trim().split(/\s+/, 1)[0];
|
|
148
|
+
if (!digest || !/^[0-9a-f]{64}$/i.test(digest)) throw new Error(`Invalid remote sha256 for ${p}`);
|
|
149
|
+
return digest.toLowerCase();
|
|
150
|
+
},
|
|
151
|
+
removeFile: (p) => sshExec(remote, `rm -- ${shellQuote(toRemote(p))}`).then(() => {}),
|
|
152
|
+
};
|
|
79
153
|
}
|
|
80
154
|
|
|
81
155
|
function createRemoteBashOps(remote: string, remoteCwd: string, localCwd: string): BashOperations {
|
|
@@ -83,7 +157,7 @@ function createRemoteBashOps(remote: string, remoteCwd: string, localCwd: string
|
|
|
83
157
|
return {
|
|
84
158
|
exec: (command, cwd, { onData, signal, timeout }) =>
|
|
85
159
|
new Promise((resolve, reject) => {
|
|
86
|
-
const cmd = `cd ${
|
|
160
|
+
const cmd = `cd ${shellQuote(toRemote(cwd))} && ${command}`;
|
|
87
161
|
const child = spawn("ssh", [remote, cmd], { stdio: ["ignore", "pipe", "pipe"] });
|
|
88
162
|
let timedOut = false;
|
|
89
163
|
const timer = timeout
|
|
@@ -115,15 +189,35 @@ export default function (pi: ExtensionAPI) {
|
|
|
115
189
|
pi.registerFlag("ssh", { description: "SSH remote: user@host or user@host:/path", type: "string" });
|
|
116
190
|
|
|
117
191
|
const localCwd = process.cwd();
|
|
192
|
+
const localFileMutationIntents = new FileMutationIntentController();
|
|
118
193
|
const localRead = createReadTool(localCwd);
|
|
119
|
-
const localWrite = createWriteTool(localCwd);
|
|
120
|
-
const localEdit = createEditTool(localCwd);
|
|
194
|
+
const localWrite = createWriteTool(localCwd, { intentController: localFileMutationIntents });
|
|
195
|
+
const localEdit = createEditTool(localCwd, { intentController: localFileMutationIntents });
|
|
121
196
|
const localBash = createBashTool(localCwd);
|
|
122
197
|
|
|
123
198
|
// Resolved lazily on session_start (CLI flags not available during factory)
|
|
124
199
|
let resolvedSsh: { remote: string; remoteCwd: string } | null = null;
|
|
200
|
+
let remoteFileTools: { write: ReturnType<typeof createWriteTool>; edit: ReturnType<typeof createEditTool> } | null =
|
|
201
|
+
null;
|
|
125
202
|
|
|
126
203
|
const getSsh = () => resolvedSsh;
|
|
204
|
+
const getRemoteFileTools = (ssh: { remote: string; remoteCwd: string }) => {
|
|
205
|
+
if (remoteFileTools) return remoteFileTools;
|
|
206
|
+
const intentController = new FileMutationIntentController({
|
|
207
|
+
operations: createRemoteIntentOps(ssh.remote, ssh.remoteCwd, localCwd),
|
|
208
|
+
});
|
|
209
|
+
remoteFileTools = {
|
|
210
|
+
write: createWriteTool(localCwd, {
|
|
211
|
+
operations: createRemoteWriteOps(ssh.remote, ssh.remoteCwd, localCwd),
|
|
212
|
+
intentController,
|
|
213
|
+
}),
|
|
214
|
+
edit: createEditTool(localCwd, {
|
|
215
|
+
operations: createRemoteEditOps(ssh.remote, ssh.remoteCwd, localCwd),
|
|
216
|
+
intentController,
|
|
217
|
+
}),
|
|
218
|
+
};
|
|
219
|
+
return remoteFileTools;
|
|
220
|
+
};
|
|
127
221
|
|
|
128
222
|
pi.registerTool({
|
|
129
223
|
...localRead,
|
|
@@ -144,10 +238,7 @@ export default function (pi: ExtensionAPI) {
|
|
|
144
238
|
async execute(id, params, signal, onUpdate, _ctx) {
|
|
145
239
|
const ssh = getSsh();
|
|
146
240
|
if (ssh) {
|
|
147
|
-
|
|
148
|
-
operations: createRemoteWriteOps(ssh.remote, ssh.remoteCwd, localCwd),
|
|
149
|
-
});
|
|
150
|
-
return tool.execute(id, params, signal, onUpdate);
|
|
241
|
+
return getRemoteFileTools(ssh).write.execute(id, params, signal, onUpdate);
|
|
151
242
|
}
|
|
152
243
|
return localWrite.execute(id, params, signal, onUpdate);
|
|
153
244
|
},
|
|
@@ -158,10 +249,7 @@ export default function (pi: ExtensionAPI) {
|
|
|
158
249
|
async execute(id, params, signal, onUpdate, _ctx) {
|
|
159
250
|
const ssh = getSsh();
|
|
160
251
|
if (ssh) {
|
|
161
|
-
|
|
162
|
-
operations: createRemoteEditOps(ssh.remote, ssh.remoteCwd, localCwd),
|
|
163
|
-
});
|
|
164
|
-
return tool.execute(id, params, signal, onUpdate);
|
|
252
|
+
return getRemoteFileTools(ssh).edit.execute(id, params, signal, onUpdate);
|
|
165
253
|
}
|
|
166
254
|
return localEdit.execute(id, params, signal, onUpdate);
|
|
167
255
|
},
|
|
@@ -185,6 +273,7 @@ export default function (pi: ExtensionAPI) {
|
|
|
185
273
|
// Resolve SSH config now that CLI flags are available
|
|
186
274
|
const arg = pi.getFlag("ssh") as string | undefined;
|
|
187
275
|
if (arg) {
|
|
276
|
+
remoteFileTools = null;
|
|
188
277
|
if (arg.includes(":")) {
|
|
189
278
|
const [remote, path] = arg.split(":");
|
|
190
279
|
resolvedSsh = { remote, remoteCwd: path };
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pi-extension-with-deps",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.85.0",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "pi-extension-with-deps",
|
|
9
|
-
"version": "0.
|
|
9
|
+
"version": "0.85.0",
|
|
10
10
|
"dependencies": {
|
|
11
11
|
"ms": "^2.1.3"
|
|
12
12
|
},
|
package/npm-shrinkwrap.json
CHANGED
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@caupulican/pi-adaptative",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.85.0",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "@caupulican/pi-adaptative",
|
|
9
|
-
"version": "0.
|
|
9
|
+
"version": "0.85.0",
|
|
10
10
|
"license": "MIT",
|
|
11
11
|
"dependencies": {
|
|
12
|
-
"@caupulican/pi-agent-core": "^0.
|
|
13
|
-
"@caupulican/pi-ai": "^0.
|
|
14
|
-
"@caupulican/pi-tui": "^0.
|
|
12
|
+
"@caupulican/pi-agent-core": "^0.85.0",
|
|
13
|
+
"@caupulican/pi-ai": "^0.85.0",
|
|
14
|
+
"@caupulican/pi-tui": "^0.85.0",
|
|
15
15
|
"@silvia-odwyer/photon-node": "0.3.4",
|
|
16
16
|
"chalk": "5.6.2",
|
|
17
17
|
"cross-spawn": "7.0.6",
|
|
@@ -20,6 +20,7 @@
|
|
|
20
20
|
"highlight.js": "10.7.3",
|
|
21
21
|
"hosted-git-info": "9.0.3",
|
|
22
22
|
"ignore": "7.0.5",
|
|
23
|
+
"jscpd": "5.0.14",
|
|
23
24
|
"jiti": "2.7.0",
|
|
24
25
|
"minimatch": "10.2.5",
|
|
25
26
|
"proper-lockfile": "4.1.2",
|
|
@@ -32,6 +33,7 @@
|
|
|
32
33
|
"@mariozechner/clipboard": "0.3.9"
|
|
33
34
|
},
|
|
34
35
|
"bin": {
|
|
36
|
+
"jscpd": "dist/jscpd-cli.js",
|
|
35
37
|
"pi": "dist/cli.js",
|
|
36
38
|
"pi-adaptative": "dist/cli.js"
|
|
37
39
|
},
|
|
@@ -475,11 +477,11 @@
|
|
|
475
477
|
}
|
|
476
478
|
},
|
|
477
479
|
"node_modules/@caupulican/pi-agent-core": {
|
|
478
|
-
"version": "0.
|
|
479
|
-
"resolved": "https://registry.npmjs.org/@caupulican/pi-agent-core/-/pi-agent-core-0.
|
|
480
|
+
"version": "0.85.0",
|
|
481
|
+
"resolved": "https://registry.npmjs.org/@caupulican/pi-agent-core/-/pi-agent-core-0.85.0.tgz",
|
|
480
482
|
"license": "MIT",
|
|
481
483
|
"dependencies": {
|
|
482
|
-
"@caupulican/pi-ai": "^0.
|
|
484
|
+
"@caupulican/pi-ai": "^0.85.0",
|
|
483
485
|
"ignore": "7.0.5",
|
|
484
486
|
"typebox": "1.1.38",
|
|
485
487
|
"yaml": "2.9.0"
|
|
@@ -489,8 +491,8 @@
|
|
|
489
491
|
}
|
|
490
492
|
},
|
|
491
493
|
"node_modules/@caupulican/pi-ai": {
|
|
492
|
-
"version": "0.
|
|
493
|
-
"resolved": "https://registry.npmjs.org/@caupulican/pi-ai/-/pi-ai-0.
|
|
494
|
+
"version": "0.85.0",
|
|
495
|
+
"resolved": "https://registry.npmjs.org/@caupulican/pi-ai/-/pi-ai-0.85.0.tgz",
|
|
494
496
|
"license": "MIT",
|
|
495
497
|
"dependencies": {
|
|
496
498
|
"@anthropic-ai/sdk": "0.91.1",
|
|
@@ -542,8 +544,8 @@
|
|
|
542
544
|
}
|
|
543
545
|
},
|
|
544
546
|
"node_modules/@caupulican/pi-tui": {
|
|
545
|
-
"version": "0.
|
|
546
|
-
"resolved": "https://registry.npmjs.org/@caupulican/pi-tui/-/pi-tui-0.
|
|
547
|
+
"version": "0.85.0",
|
|
548
|
+
"resolved": "https://registry.npmjs.org/@caupulican/pi-tui/-/pi-tui-0.85.0.tgz",
|
|
547
549
|
"license": "MIT",
|
|
548
550
|
"dependencies": {
|
|
549
551
|
"get-east-asian-width": "1.6.0",
|
|
@@ -1683,6 +1685,104 @@
|
|
|
1683
1685
|
"jiti": "lib/jiti-cli.mjs"
|
|
1684
1686
|
}
|
|
1685
1687
|
},
|
|
1688
|
+
"node_modules/jscpd": {
|
|
1689
|
+
"version": "5.0.14",
|
|
1690
|
+
"resolved": "https://registry.npmjs.org/jscpd/-/jscpd-5.0.14.tgz",
|
|
1691
|
+
"integrity": "sha512-zge+FPZZAymt2Do5Z0+QHyIn4/XcUhrO/W7of9HcHZfx2AK8++dYhLA1uWtwXj47ml3Of8PbcUW4wUWvYMCc3w==",
|
|
1692
|
+
"license": "MIT",
|
|
1693
|
+
"optionalDependencies": {
|
|
1694
|
+
"jscpd-darwin-arm64": "5.0.14",
|
|
1695
|
+
"jscpd-darwin-x64": "5.0.14",
|
|
1696
|
+
"jscpd-linux-arm64-gnu": "5.0.14",
|
|
1697
|
+
"jscpd-linux-x64-gnu": "5.0.14",
|
|
1698
|
+
"jscpd-linux-x64-musl": "5.0.14",
|
|
1699
|
+
"jscpd-windows-x64-msvc": "5.0.14"
|
|
1700
|
+
},
|
|
1701
|
+
"bin": {
|
|
1702
|
+
"jscpd": "run-jscpd.js"
|
|
1703
|
+
},
|
|
1704
|
+
"engines": {
|
|
1705
|
+
"node": ">=18"
|
|
1706
|
+
}
|
|
1707
|
+
},
|
|
1708
|
+
"node_modules/jscpd-darwin-arm64": {
|
|
1709
|
+
"version": "5.0.14",
|
|
1710
|
+
"resolved": "https://registry.npmjs.org/jscpd-darwin-arm64/-/jscpd-darwin-arm64-5.0.14.tgz",
|
|
1711
|
+
"integrity": "sha512-Ojjl79SBuj9tEW6WbjZ1a/1ZOR89dneH9yLQYQu8WyWaQownttnx7RYFEHU6aGhS4jIvwUEbr+1wxzFTb37cwg==",
|
|
1712
|
+
"license": "MIT",
|
|
1713
|
+
"os": [
|
|
1714
|
+
"darwin"
|
|
1715
|
+
],
|
|
1716
|
+
"cpu": [
|
|
1717
|
+
"arm64"
|
|
1718
|
+
],
|
|
1719
|
+
"optional": true
|
|
1720
|
+
},
|
|
1721
|
+
"node_modules/jscpd-darwin-x64": {
|
|
1722
|
+
"version": "5.0.14",
|
|
1723
|
+
"resolved": "https://registry.npmjs.org/jscpd-darwin-x64/-/jscpd-darwin-x64-5.0.14.tgz",
|
|
1724
|
+
"integrity": "sha512-DxFg5XvjMZ81iVeqillnM5apqcGCfNTbroNF+mPLr7RkHLGH6mudLgtO+ILL/hfpZXy1bF9oIY5BSudPmN/k9A==",
|
|
1725
|
+
"license": "MIT",
|
|
1726
|
+
"os": [
|
|
1727
|
+
"darwin"
|
|
1728
|
+
],
|
|
1729
|
+
"cpu": [
|
|
1730
|
+
"x64"
|
|
1731
|
+
],
|
|
1732
|
+
"optional": true
|
|
1733
|
+
},
|
|
1734
|
+
"node_modules/jscpd-linux-arm64-gnu": {
|
|
1735
|
+
"version": "5.0.14",
|
|
1736
|
+
"resolved": "https://registry.npmjs.org/jscpd-linux-arm64-gnu/-/jscpd-linux-arm64-gnu-5.0.14.tgz",
|
|
1737
|
+
"integrity": "sha512-1uw+XBHEt9pONXNICSp5HpaVWPjG6mQ6deDXaq9Yb0xCNJkX4/8gmn0vhzekIyZD2DspRYKPUolbDsqm/HEdYg==",
|
|
1738
|
+
"license": "MIT",
|
|
1739
|
+
"os": [
|
|
1740
|
+
"linux"
|
|
1741
|
+
],
|
|
1742
|
+
"cpu": [
|
|
1743
|
+
"arm64"
|
|
1744
|
+
],
|
|
1745
|
+
"optional": true
|
|
1746
|
+
},
|
|
1747
|
+
"node_modules/jscpd-linux-x64-gnu": {
|
|
1748
|
+
"version": "5.0.14",
|
|
1749
|
+
"resolved": "https://registry.npmjs.org/jscpd-linux-x64-gnu/-/jscpd-linux-x64-gnu-5.0.14.tgz",
|
|
1750
|
+
"integrity": "sha512-dFTbyyrm+Z9pcXIVzJQCw8QAgiNqIiO69sm4AfA7/wFdPoizoVzjhaXsYXcSV4bs0aoPiWbNazg0J0HgslT/5A==",
|
|
1751
|
+
"license": "MIT",
|
|
1752
|
+
"os": [
|
|
1753
|
+
"linux"
|
|
1754
|
+
],
|
|
1755
|
+
"cpu": [
|
|
1756
|
+
"x64"
|
|
1757
|
+
],
|
|
1758
|
+
"optional": true
|
|
1759
|
+
},
|
|
1760
|
+
"node_modules/jscpd-linux-x64-musl": {
|
|
1761
|
+
"version": "5.0.14",
|
|
1762
|
+
"resolved": "https://registry.npmjs.org/jscpd-linux-x64-musl/-/jscpd-linux-x64-musl-5.0.14.tgz",
|
|
1763
|
+
"integrity": "sha512-SayS7qQJvixyy9eR0+UjepkTsUUwqvlsiuSxfIdHgG2qzqoh/thnkgiu4By8fsiiDpQONsQrRrZDwHRQ3GDrBQ==",
|
|
1764
|
+
"license": "MIT",
|
|
1765
|
+
"os": [
|
|
1766
|
+
"linux"
|
|
1767
|
+
],
|
|
1768
|
+
"cpu": [
|
|
1769
|
+
"x64"
|
|
1770
|
+
],
|
|
1771
|
+
"optional": true
|
|
1772
|
+
},
|
|
1773
|
+
"node_modules/jscpd-windows-x64-msvc": {
|
|
1774
|
+
"version": "5.0.14",
|
|
1775
|
+
"resolved": "https://registry.npmjs.org/jscpd-windows-x64-msvc/-/jscpd-windows-x64-msvc-5.0.14.tgz",
|
|
1776
|
+
"integrity": "sha512-DqjxlVkUanlahGgY2lY7Zkrau4BUTI+AwWky+bPGK4kSK2AIOaUziY9Q19u8b58idXmJA9FKK98Fuu4ajNXVjQ==",
|
|
1777
|
+
"license": "MIT",
|
|
1778
|
+
"os": [
|
|
1779
|
+
"win32"
|
|
1780
|
+
],
|
|
1781
|
+
"cpu": [
|
|
1782
|
+
"x64"
|
|
1783
|
+
],
|
|
1784
|
+
"optional": true
|
|
1785
|
+
},
|
|
1686
1786
|
"node_modules/json-bigint": {
|
|
1687
1787
|
"version": "1.0.0",
|
|
1688
1788
|
"resolved": "https://registry.npmjs.org/json-bigint/-/json-bigint-1.0.0.tgz",
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@caupulican/pi-adaptative",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.85.0",
|
|
4
4
|
"description": "Adaptive fork of Pi coding agent for self-evolving agent harness experiments",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"piConfig": {
|
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
"configDir": ".pi"
|
|
9
9
|
},
|
|
10
10
|
"bin": {
|
|
11
|
+
"jscpd": "dist/jscpd-cli.js",
|
|
11
12
|
"pi": "dist/cli.js",
|
|
12
13
|
"pi-adaptative": "dist/cli.js"
|
|
13
14
|
},
|
|
@@ -71,7 +72,7 @@
|
|
|
71
72
|
],
|
|
72
73
|
"scripts": {
|
|
73
74
|
"clean": "shx rm -rf dist",
|
|
74
|
-
"build": "node ../../scripts/run-tsc.mjs -p tsconfig.build.json && shx chmod +x dist/cli.js && npm run copy-assets",
|
|
75
|
+
"build": "node ../../scripts/run-tsc.mjs -p tsconfig.build.json && shx chmod +x dist/cli.js dist/jscpd-cli.js && npm run copy-assets",
|
|
75
76
|
"build:binary": "npm --prefix ../tui run build && npm --prefix ../ai run build && npm --prefix ../agent run build && npm run build && bun build --compile ./dist/bun/cli.js ./src/utils/image-resize-worker.ts ./src/core/memory/providers/transcript-recall-worker.ts --outfile dist/pi && npm run copy-binary-assets",
|
|
76
77
|
"copy-assets": "shx mkdir -p dist/modes/interactive/theme && shx cp src/modes/interactive/theme/*.json dist/modes/interactive/theme/ && shx mkdir -p dist/modes/interactive/assets && shx cp src/modes/interactive/assets/*.png dist/modes/interactive/assets/ && shx mkdir -p dist/core/export-html/vendor && shx cp src/core/skill-block.mjs src/core/skill-block.d.mts dist/core/ && shx cp src/core/export-html/template.html src/core/export-html/template.css src/core/export-html/template.js src/core/export-html/session-tree-foundations.mjs src/core/export-html/session-tree-foundations.d.mts dist/core/export-html/ && shx cp src/core/export-html/vendor/*.js dist/core/export-html/vendor/ && shx mkdir -p dist/bundled-resources && shx cp -r src/bundled-resources/* dist/bundled-resources/",
|
|
77
78
|
"copy-binary-assets": "shx cp package.json dist/ && shx cp README.md dist/ && shx cp CHANGELOG.md dist/ && shx mkdir -p dist/theme && shx cp src/modes/interactive/theme/*.json dist/theme/ && shx mkdir -p dist/assets && shx cp src/modes/interactive/assets/*.png dist/assets/ && shx mkdir -p dist/export-html/vendor && shx cp src/core/skill-block.mjs dist/ && shx cp src/core/export-html/template.html src/core/export-html/template.css src/core/export-html/template.js src/core/export-html/session-tree-foundations.mjs dist/export-html/ && shx cp src/core/export-html/vendor/*.js dist/export-html/vendor/ && shx mkdir -p dist/bundled-resources && shx cp -r src/bundled-resources/* dist/bundled-resources/ && shx cp -r docs dist/ && shx cp -r examples dist/ && shx cp ../../node_modules/@silvia-odwyer/photon-node/photon_rs_bg.wasm dist/",
|
|
@@ -81,9 +82,9 @@
|
|
|
81
82
|
"postinstall": "node scripts/postinstall-python-runtime.mjs"
|
|
82
83
|
},
|
|
83
84
|
"dependencies": {
|
|
84
|
-
"@caupulican/pi-agent-core": "^0.
|
|
85
|
-
"@caupulican/pi-ai": "^0.
|
|
86
|
-
"@caupulican/pi-tui": "^0.
|
|
85
|
+
"@caupulican/pi-agent-core": "^0.85.0",
|
|
86
|
+
"@caupulican/pi-ai": "^0.85.0",
|
|
87
|
+
"@caupulican/pi-tui": "^0.85.0",
|
|
87
88
|
"@silvia-odwyer/photon-node": "0.3.4",
|
|
88
89
|
"chalk": "5.6.2",
|
|
89
90
|
"cross-spawn": "7.0.6",
|
|
@@ -92,6 +93,7 @@
|
|
|
92
93
|
"highlight.js": "10.7.3",
|
|
93
94
|
"hosted-git-info": "9.0.3",
|
|
94
95
|
"ignore": "7.0.5",
|
|
96
|
+
"jscpd": "5.0.14",
|
|
95
97
|
"jiti": "2.7.0",
|
|
96
98
|
"minimatch": "10.2.5",
|
|
97
99
|
"proper-lockfile": "4.1.2",
|