@lenylvt/pi-coding-agent 0.64.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 +3331 -0
- package/README.md +48 -0
- package/dist/bun/cli.d.ts +3 -0
- package/dist/bun/cli.d.ts.map +1 -0
- package/dist/bun/cli.js +5 -0
- package/dist/bun/cli.js.map +1 -0
- package/dist/cli/args.d.ts +49 -0
- package/dist/cli/args.d.ts.map +1 -0
- package/dist/cli/args.js +292 -0
- package/dist/cli/args.js.map +1 -0
- package/dist/cli/config-selector.d.ts +14 -0
- package/dist/cli/config-selector.d.ts.map +1 -0
- package/dist/cli/config-selector.js +31 -0
- package/dist/cli/config-selector.js.map +1 -0
- package/dist/cli/file-processor.d.ts +15 -0
- package/dist/cli/file-processor.d.ts.map +1 -0
- package/dist/cli/file-processor.js +83 -0
- package/dist/cli/file-processor.js.map +1 -0
- package/dist/cli/initial-message.d.ts +18 -0
- package/dist/cli/initial-message.d.ts.map +1 -0
- package/dist/cli/initial-message.js +22 -0
- package/dist/cli/initial-message.js.map +1 -0
- package/dist/cli/list-models.d.ts +9 -0
- package/dist/cli/list-models.d.ts.map +1 -0
- package/dist/cli/list-models.js +92 -0
- package/dist/cli/list-models.js.map +1 -0
- package/dist/cli/session-picker.d.ts +9 -0
- package/dist/cli/session-picker.d.ts.map +1 -0
- package/dist/cli/session-picker.js +35 -0
- package/dist/cli/session-picker.js.map +1 -0
- package/dist/cli.d.ts +3 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +14 -0
- package/dist/cli.js.map +1 -0
- package/dist/config.d.ts +69 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +178 -0
- package/dist/config.js.map +1 -0
- package/dist/core/agent-session.d.ts +622 -0
- package/dist/core/agent-session.d.ts.map +1 -0
- package/dist/core/agent-session.js +2688 -0
- package/dist/core/agent-session.js.map +1 -0
- package/dist/core/auth-storage.d.ts +132 -0
- package/dist/core/auth-storage.d.ts.map +1 -0
- package/dist/core/auth-storage.js +422 -0
- package/dist/core/auth-storage.js.map +1 -0
- package/dist/core/bash-executor.d.ts +46 -0
- package/dist/core/bash-executor.d.ts.map +1 -0
- package/dist/core/bash-executor.js +113 -0
- package/dist/core/bash-executor.js.map +1 -0
- package/dist/core/compaction/branch-summarization.d.ts +88 -0
- package/dist/core/compaction/branch-summarization.d.ts.map +1 -0
- package/dist/core/compaction/branch-summarization.js +243 -0
- package/dist/core/compaction/branch-summarization.js.map +1 -0
- package/dist/core/compaction/compaction.d.ts +121 -0
- package/dist/core/compaction/compaction.d.ts.map +1 -0
- package/dist/core/compaction/compaction.js +613 -0
- package/dist/core/compaction/compaction.js.map +1 -0
- package/dist/core/compaction/index.d.ts +7 -0
- package/dist/core/compaction/index.d.ts.map +1 -0
- package/dist/core/compaction/index.js +7 -0
- package/dist/core/compaction/index.js.map +1 -0
- package/dist/core/compaction/utils.d.ts +38 -0
- package/dist/core/compaction/utils.d.ts.map +1 -0
- package/dist/core/compaction/utils.js +153 -0
- package/dist/core/compaction/utils.js.map +1 -0
- package/dist/core/defaults.d.ts +3 -0
- package/dist/core/defaults.d.ts.map +1 -0
- package/dist/core/defaults.js +2 -0
- package/dist/core/defaults.js.map +1 -0
- package/dist/core/diagnostics.d.ts +15 -0
- package/dist/core/diagnostics.d.ts.map +1 -0
- package/dist/core/diagnostics.js +2 -0
- package/dist/core/diagnostics.js.map +1 -0
- package/dist/core/event-bus.d.ts +9 -0
- package/dist/core/event-bus.d.ts.map +1 -0
- package/dist/core/event-bus.js +25 -0
- package/dist/core/event-bus.js.map +1 -0
- package/dist/core/exec.d.ts +29 -0
- package/dist/core/exec.d.ts.map +1 -0
- package/dist/core/exec.js +75 -0
- package/dist/core/exec.js.map +1 -0
- package/dist/core/export-html/ansi-to-html.d.ts +22 -0
- package/dist/core/export-html/ansi-to-html.d.ts.map +1 -0
- package/dist/core/export-html/ansi-to-html.js +249 -0
- package/dist/core/export-html/ansi-to-html.js.map +1 -0
- package/dist/core/export-html/index.d.ts +37 -0
- package/dist/core/export-html/index.d.ts.map +1 -0
- package/dist/core/export-html/index.js +224 -0
- package/dist/core/export-html/index.js.map +1 -0
- package/dist/core/export-html/template.css +1001 -0
- package/dist/core/export-html/template.html +55 -0
- package/dist/core/export-html/template.js +1690 -0
- package/dist/core/export-html/tool-renderer.d.ts +38 -0
- package/dist/core/export-html/tool-renderer.d.ts.map +1 -0
- package/dist/core/export-html/tool-renderer.js +95 -0
- package/dist/core/export-html/tool-renderer.js.map +1 -0
- package/dist/core/export-html/vendor/highlight.min.js +1213 -0
- package/dist/core/export-html/vendor/marked.min.js +6 -0
- package/dist/core/extensions/index.d.ts +12 -0
- package/dist/core/extensions/index.d.ts.map +1 -0
- package/dist/core/extensions/index.js +9 -0
- package/dist/core/extensions/index.js.map +1 -0
- package/dist/core/extensions/loader.d.ts +25 -0
- package/dist/core/extensions/loader.d.ts.map +1 -0
- package/dist/core/extensions/loader.js +436 -0
- package/dist/core/extensions/loader.js.map +1 -0
- package/dist/core/extensions/runner.d.ts +148 -0
- package/dist/core/extensions/runner.d.ts.map +1 -0
- package/dist/core/extensions/runner.js +700 -0
- package/dist/core/extensions/runner.js.map +1 -0
- package/dist/core/extensions/types.d.ts +1085 -0
- package/dist/core/extensions/types.d.ts.map +1 -0
- package/dist/core/extensions/types.js +35 -0
- package/dist/core/extensions/types.js.map +1 -0
- package/dist/core/extensions/wrapper.d.ts +20 -0
- package/dist/core/extensions/wrapper.d.ts.map +1 -0
- package/dist/core/extensions/wrapper.js +22 -0
- package/dist/core/extensions/wrapper.js.map +1 -0
- package/dist/core/footer-data-provider.d.ts +44 -0
- package/dist/core/footer-data-provider.d.ts.map +1 -0
- package/dist/core/footer-data-provider.js +252 -0
- package/dist/core/footer-data-provider.js.map +1 -0
- package/dist/core/index.d.ts +10 -0
- package/dist/core/index.d.ts.map +1 -0
- package/dist/core/index.js +10 -0
- package/dist/core/index.js.map +1 -0
- package/dist/core/keybindings.d.ts +275 -0
- package/dist/core/keybindings.d.ts.map +1 -0
- package/dist/core/keybindings.js +241 -0
- package/dist/core/keybindings.js.map +1 -0
- package/dist/core/messages.d.ts +77 -0
- package/dist/core/messages.d.ts.map +1 -0
- package/dist/core/messages.js +123 -0
- package/dist/core/messages.js.map +1 -0
- package/dist/core/model-registry.d.ts +132 -0
- package/dist/core/model-registry.d.ts.map +1 -0
- package/dist/core/model-registry.js +565 -0
- package/dist/core/model-registry.js.map +1 -0
- package/dist/core/model-resolver.d.ts +110 -0
- package/dist/core/model-resolver.d.ts.map +1 -0
- package/dist/core/model-resolver.js +464 -0
- package/dist/core/model-resolver.js.map +1 -0
- package/dist/core/output-guard.d.ts +6 -0
- package/dist/core/output-guard.d.ts.map +1 -0
- package/dist/core/output-guard.js +59 -0
- package/dist/core/output-guard.js.map +1 -0
- package/dist/core/package-manager.d.ts +172 -0
- package/dist/core/package-manager.d.ts.map +1 -0
- package/dist/core/package-manager.js +1801 -0
- package/dist/core/package-manager.js.map +1 -0
- package/dist/core/prompt-templates.d.ts +51 -0
- package/dist/core/prompt-templates.d.ts.map +1 -0
- package/dist/core/prompt-templates.js +249 -0
- package/dist/core/prompt-templates.js.map +1 -0
- package/dist/core/resolve-config-value.d.ts +23 -0
- package/dist/core/resolve-config-value.d.ts.map +1 -0
- package/dist/core/resolve-config-value.js +126 -0
- package/dist/core/resolve-config-value.js.map +1 -0
- package/dist/core/resource-loader.d.ts +185 -0
- package/dist/core/resource-loader.d.ts.map +1 -0
- package/dist/core/resource-loader.js +698 -0
- package/dist/core/resource-loader.js.map +1 -0
- package/dist/core/sdk.d.ts +90 -0
- package/dist/core/sdk.d.ts.map +1 -0
- package/dist/core/sdk.js +233 -0
- package/dist/core/sdk.js.map +1 -0
- package/dist/core/self-update.d.ts +3 -0
- package/dist/core/self-update.d.ts.map +1 -0
- package/dist/core/self-update.js +46 -0
- package/dist/core/self-update.js.map +1 -0
- package/dist/core/session-manager.d.ts +329 -0
- package/dist/core/session-manager.d.ts.map +1 -0
- package/dist/core/session-manager.js +1097 -0
- package/dist/core/session-manager.js.map +1 -0
- package/dist/core/settings-manager.d.ts +237 -0
- package/dist/core/settings-manager.d.ts.map +1 -0
- package/dist/core/settings-manager.js +708 -0
- package/dist/core/settings-manager.js.map +1 -0
- package/dist/core/skills.d.ts +60 -0
- package/dist/core/skills.d.ts.map +1 -0
- package/dist/core/skills.js +409 -0
- package/dist/core/skills.js.map +1 -0
- package/dist/core/slash-commands.d.ts +14 -0
- package/dist/core/slash-commands.d.ts.map +1 -0
- package/dist/core/slash-commands.js +22 -0
- package/dist/core/slash-commands.js.map +1 -0
- package/dist/core/source-info.d.ts +18 -0
- package/dist/core/source-info.d.ts.map +1 -0
- package/dist/core/source-info.js +19 -0
- package/dist/core/source-info.js.map +1 -0
- package/dist/core/system-prompt.d.ts +28 -0
- package/dist/core/system-prompt.d.ts.map +1 -0
- package/dist/core/system-prompt.js +116 -0
- package/dist/core/system-prompt.js.map +1 -0
- package/dist/core/timings.d.ts +8 -0
- package/dist/core/timings.d.ts.map +1 -0
- package/dist/core/timings.js +31 -0
- package/dist/core/timings.js.map +1 -0
- package/dist/core/tools/bash.d.ts +73 -0
- package/dist/core/tools/bash.d.ts.map +1 -0
- package/dist/core/tools/bash.js +342 -0
- package/dist/core/tools/bash.js.map +1 -0
- package/dist/core/tools/edit-diff.d.ts +85 -0
- package/dist/core/tools/edit-diff.d.ts.map +1 -0
- package/dist/core/tools/edit-diff.js +337 -0
- package/dist/core/tools/edit-diff.js.map +1 -0
- package/dist/core/tools/edit.d.ts +53 -0
- package/dist/core/tools/edit.d.ts.map +1 -0
- package/dist/core/tools/edit.js +196 -0
- package/dist/core/tools/edit.js.map +1 -0
- package/dist/core/tools/file-mutation-queue.d.ts +6 -0
- package/dist/core/tools/file-mutation-queue.d.ts.map +1 -0
- package/dist/core/tools/file-mutation-queue.js +37 -0
- package/dist/core/tools/file-mutation-queue.js.map +1 -0
- package/dist/core/tools/find.d.ts +46 -0
- package/dist/core/tools/find.d.ts.map +1 -0
- package/dist/core/tools/find.js +258 -0
- package/dist/core/tools/find.js.map +1 -0
- package/dist/core/tools/grep.d.ts +56 -0
- package/dist/core/tools/grep.d.ts.map +1 -0
- package/dist/core/tools/grep.js +293 -0
- package/dist/core/tools/grep.js.map +1 -0
- package/dist/core/tools/index.d.ts +115 -0
- package/dist/core/tools/index.d.ts.map +1 -0
- package/dist/core/tools/index.js +86 -0
- package/dist/core/tools/index.js.map +1 -0
- package/dist/core/tools/ls.d.ts +46 -0
- package/dist/core/tools/ls.d.ts.map +1 -0
- package/dist/core/tools/ls.js +172 -0
- package/dist/core/tools/ls.js.map +1 -0
- package/dist/core/tools/path-utils.d.ts +8 -0
- package/dist/core/tools/path-utils.d.ts.map +1 -0
- package/dist/core/tools/path-utils.js +81 -0
- package/dist/core/tools/path-utils.js.map +1 -0
- package/dist/core/tools/read.d.ts +46 -0
- package/dist/core/tools/read.d.ts.map +1 -0
- package/dist/core/tools/read.js +225 -0
- package/dist/core/tools/read.js.map +1 -0
- package/dist/core/tools/render-utils.d.ts +21 -0
- package/dist/core/tools/render-utils.d.ts.map +1 -0
- package/dist/core/tools/render-utils.js +49 -0
- package/dist/core/tools/render-utils.js.map +1 -0
- package/dist/core/tools/tool-definition-wrapper.d.ts +14 -0
- package/dist/core/tools/tool-definition-wrapper.d.ts.map +1 -0
- package/dist/core/tools/tool-definition-wrapper.js +32 -0
- package/dist/core/tools/tool-definition-wrapper.js.map +1 -0
- package/dist/core/tools/truncate.d.ts +70 -0
- package/dist/core/tools/truncate.d.ts.map +1 -0
- package/dist/core/tools/truncate.js +205 -0
- package/dist/core/tools/truncate.js.map +1 -0
- package/dist/core/tools/write.d.ts +35 -0
- package/dist/core/tools/write.d.ts.map +1 -0
- package/dist/core/tools/write.js +216 -0
- package/dist/core/tools/write.js.map +1 -0
- package/dist/core/version-check.d.ts +2 -0
- package/dist/core/version-check.d.ts.map +1 -0
- package/dist/core/version-check.js +73 -0
- package/dist/core/version-check.js.map +1 -0
- package/dist/index.d.ts +28 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +43 -0
- package/dist/index.js.map +1 -0
- package/dist/main.d.ts +8 -0
- package/dist/main.d.ts.map +1 -0
- package/dist/main.js +811 -0
- package/dist/main.js.map +1 -0
- package/dist/migrations.d.ts +32 -0
- package/dist/migrations.d.ts.map +1 -0
- package/dist/migrations.js +258 -0
- package/dist/migrations.js.map +1 -0
- package/dist/modes/index.d.ts +9 -0
- package/dist/modes/index.d.ts.map +1 -0
- package/dist/modes/index.js +8 -0
- package/dist/modes/index.js.map +1 -0
- package/dist/modes/interactive/components/armin.d.ts +34 -0
- package/dist/modes/interactive/components/armin.d.ts.map +1 -0
- package/dist/modes/interactive/components/armin.js +333 -0
- package/dist/modes/interactive/components/armin.js.map +1 -0
- package/dist/modes/interactive/components/assistant-message.d.ts +18 -0
- package/dist/modes/interactive/components/assistant-message.d.ts.map +1 -0
- package/dist/modes/interactive/components/assistant-message.js +107 -0
- package/dist/modes/interactive/components/assistant-message.js.map +1 -0
- package/dist/modes/interactive/components/bash-execution.d.ts +34 -0
- package/dist/modes/interactive/components/bash-execution.d.ts.map +1 -0
- package/dist/modes/interactive/components/bash-execution.js +175 -0
- package/dist/modes/interactive/components/bash-execution.js.map +1 -0
- package/dist/modes/interactive/components/bordered-loader.d.ts +16 -0
- package/dist/modes/interactive/components/bordered-loader.d.ts.map +1 -0
- package/dist/modes/interactive/components/bordered-loader.js +51 -0
- package/dist/modes/interactive/components/bordered-loader.js.map +1 -0
- package/dist/modes/interactive/components/branch-summary-message.d.ts +16 -0
- package/dist/modes/interactive/components/branch-summary-message.d.ts.map +1 -0
- package/dist/modes/interactive/components/branch-summary-message.js +44 -0
- package/dist/modes/interactive/components/branch-summary-message.js.map +1 -0
- package/dist/modes/interactive/components/compaction-summary-message.d.ts +16 -0
- package/dist/modes/interactive/components/compaction-summary-message.d.ts.map +1 -0
- package/dist/modes/interactive/components/compaction-summary-message.js +45 -0
- package/dist/modes/interactive/components/compaction-summary-message.js.map +1 -0
- package/dist/modes/interactive/components/config-selector.d.ts +71 -0
- package/dist/modes/interactive/components/config-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/config-selector.js +479 -0
- package/dist/modes/interactive/components/config-selector.js.map +1 -0
- package/dist/modes/interactive/components/countdown-timer.d.ts +14 -0
- package/dist/modes/interactive/components/countdown-timer.d.ts.map +1 -0
- package/dist/modes/interactive/components/countdown-timer.js +33 -0
- package/dist/modes/interactive/components/countdown-timer.js.map +1 -0
- package/dist/modes/interactive/components/custom-editor.d.ts +21 -0
- package/dist/modes/interactive/components/custom-editor.d.ts.map +1 -0
- package/dist/modes/interactive/components/custom-editor.js +70 -0
- package/dist/modes/interactive/components/custom-editor.js.map +1 -0
- package/dist/modes/interactive/components/custom-message.d.ts +20 -0
- package/dist/modes/interactive/components/custom-message.d.ts.map +1 -0
- package/dist/modes/interactive/components/custom-message.js +79 -0
- package/dist/modes/interactive/components/custom-message.js.map +1 -0
- package/dist/modes/interactive/components/diff.d.ts +12 -0
- package/dist/modes/interactive/components/diff.d.ts.map +1 -0
- package/dist/modes/interactive/components/diff.js +133 -0
- package/dist/modes/interactive/components/diff.js.map +1 -0
- package/dist/modes/interactive/components/dynamic-border.d.ts +15 -0
- package/dist/modes/interactive/components/dynamic-border.d.ts.map +1 -0
- package/dist/modes/interactive/components/dynamic-border.js +21 -0
- package/dist/modes/interactive/components/dynamic-border.js.map +1 -0
- package/dist/modes/interactive/components/extension-editor.d.ts +20 -0
- package/dist/modes/interactive/components/extension-editor.d.ts.map +1 -0
- package/dist/modes/interactive/components/extension-editor.js +111 -0
- package/dist/modes/interactive/components/extension-editor.js.map +1 -0
- package/dist/modes/interactive/components/extension-input.d.ts +23 -0
- package/dist/modes/interactive/components/extension-input.d.ts.map +1 -0
- package/dist/modes/interactive/components/extension-input.js +61 -0
- package/dist/modes/interactive/components/extension-input.js.map +1 -0
- package/dist/modes/interactive/components/extension-selector.d.ts +24 -0
- package/dist/modes/interactive/components/extension-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/extension-selector.js +78 -0
- package/dist/modes/interactive/components/extension-selector.js.map +1 -0
- package/dist/modes/interactive/components/footer.d.ts +26 -0
- package/dist/modes/interactive/components/footer.d.ts.map +1 -0
- package/dist/modes/interactive/components/footer.js +198 -0
- package/dist/modes/interactive/components/footer.js.map +1 -0
- package/dist/modes/interactive/components/index.d.ts +31 -0
- package/dist/modes/interactive/components/index.d.ts.map +1 -0
- package/dist/modes/interactive/components/index.js +32 -0
- package/dist/modes/interactive/components/index.js.map +1 -0
- package/dist/modes/interactive/components/keybinding-hints.d.ts +8 -0
- package/dist/modes/interactive/components/keybinding-hints.d.ts.map +1 -0
- package/dist/modes/interactive/components/keybinding-hints.js +22 -0
- package/dist/modes/interactive/components/keybinding-hints.js.map +1 -0
- package/dist/modes/interactive/components/login-dialog.d.ts +42 -0
- package/dist/modes/interactive/components/login-dialog.d.ts.map +1 -0
- package/dist/modes/interactive/components/login-dialog.js +145 -0
- package/dist/modes/interactive/components/login-dialog.js.map +1 -0
- package/dist/modes/interactive/components/model-selector.d.ts +47 -0
- package/dist/modes/interactive/components/model-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/model-selector.js +275 -0
- package/dist/modes/interactive/components/model-selector.js.map +1 -0
- package/dist/modes/interactive/components/oauth-selector.d.ts +19 -0
- package/dist/modes/interactive/components/oauth-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/oauth-selector.js +97 -0
- package/dist/modes/interactive/components/oauth-selector.js.map +1 -0
- package/dist/modes/interactive/components/scoped-models-selector.d.ts +49 -0
- package/dist/modes/interactive/components/scoped-models-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/scoped-models-selector.js +275 -0
- package/dist/modes/interactive/components/scoped-models-selector.js.map +1 -0
- package/dist/modes/interactive/components/session-selector-search.d.ts +23 -0
- package/dist/modes/interactive/components/session-selector-search.d.ts.map +1 -0
- package/dist/modes/interactive/components/session-selector-search.js +155 -0
- package/dist/modes/interactive/components/session-selector-search.js.map +1 -0
- package/dist/modes/interactive/components/session-selector.d.ts +95 -0
- package/dist/modes/interactive/components/session-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/session-selector.js +848 -0
- package/dist/modes/interactive/components/session-selector.js.map +1 -0
- package/dist/modes/interactive/components/settings-selector.d.ts +58 -0
- package/dist/modes/interactive/components/settings-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/settings-selector.js +301 -0
- package/dist/modes/interactive/components/settings-selector.js.map +1 -0
- package/dist/modes/interactive/components/show-images-selector.d.ts +10 -0
- package/dist/modes/interactive/components/show-images-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/show-images-selector.js +39 -0
- package/dist/modes/interactive/components/show-images-selector.js.map +1 -0
- package/dist/modes/interactive/components/skill-invocation-message.d.ts +17 -0
- package/dist/modes/interactive/components/skill-invocation-message.d.ts.map +1 -0
- package/dist/modes/interactive/components/skill-invocation-message.js +47 -0
- package/dist/modes/interactive/components/skill-invocation-message.js.map +1 -0
- package/dist/modes/interactive/components/theme-selector.d.ts +11 -0
- package/dist/modes/interactive/components/theme-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/theme-selector.js +50 -0
- package/dist/modes/interactive/components/theme-selector.js.map +1 -0
- package/dist/modes/interactive/components/thinking-selector.d.ts +11 -0
- package/dist/modes/interactive/components/thinking-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/thinking-selector.js +51 -0
- package/dist/modes/interactive/components/thinking-selector.js.map +1 -0
- package/dist/modes/interactive/components/tool-execution.d.ts +58 -0
- package/dist/modes/interactive/components/tool-execution.d.ts.map +1 -0
- package/dist/modes/interactive/components/tool-execution.js +274 -0
- package/dist/modes/interactive/components/tool-execution.js.map +1 -0
- package/dist/modes/interactive/components/tree-selector.d.ts +87 -0
- package/dist/modes/interactive/components/tree-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/tree-selector.js +1051 -0
- package/dist/modes/interactive/components/tree-selector.js.map +1 -0
- package/dist/modes/interactive/components/user-message-selector.d.ts +30 -0
- package/dist/modes/interactive/components/user-message-selector.d.ts.map +1 -0
- package/dist/modes/interactive/components/user-message-selector.js +113 -0
- package/dist/modes/interactive/components/user-message-selector.js.map +1 -0
- package/dist/modes/interactive/components/user-message.d.ts +9 -0
- package/dist/modes/interactive/components/user-message.d.ts.map +1 -0
- package/dist/modes/interactive/components/user-message.js +28 -0
- package/dist/modes/interactive/components/user-message.js.map +1 -0
- package/dist/modes/interactive/components/visual-truncate.d.ts +24 -0
- package/dist/modes/interactive/components/visual-truncate.d.ts.map +1 -0
- package/dist/modes/interactive/components/visual-truncate.js +33 -0
- package/dist/modes/interactive/components/visual-truncate.js.map +1 -0
- package/dist/modes/interactive/interactive-mode.d.ts +311 -0
- package/dist/modes/interactive/interactive-mode.d.ts.map +1 -0
- package/dist/modes/interactive/interactive-mode.js +3798 -0
- package/dist/modes/interactive/interactive-mode.js.map +1 -0
- package/dist/modes/interactive/theme/dark.json +85 -0
- package/dist/modes/interactive/theme/light.json +84 -0
- package/dist/modes/interactive/theme/theme-schema.json +335 -0
- package/dist/modes/interactive/theme/theme.d.ts +81 -0
- package/dist/modes/interactive/theme/theme.d.ts.map +1 -0
- package/dist/modes/interactive/theme/theme.js +975 -0
- package/dist/modes/interactive/theme/theme.js.map +1 -0
- package/dist/modes/print-mode.d.ts +28 -0
- package/dist/modes/print-mode.d.ts.map +1 -0
- package/dist/modes/print-mode.js +107 -0
- package/dist/modes/print-mode.js.map +1 -0
- package/dist/modes/rpc/jsonl.d.ts +17 -0
- package/dist/modes/rpc/jsonl.d.ts.map +1 -0
- package/dist/modes/rpc/jsonl.js +49 -0
- package/dist/modes/rpc/jsonl.js.map +1 -0
- package/dist/modes/rpc/rpc-client.d.ts +217 -0
- package/dist/modes/rpc/rpc-client.d.ts.map +1 -0
- package/dist/modes/rpc/rpc-client.js +401 -0
- package/dist/modes/rpc/rpc-client.js.map +1 -0
- package/dist/modes/rpc/rpc-mode.d.ts +20 -0
- package/dist/modes/rpc/rpc-mode.d.ts.map +1 -0
- package/dist/modes/rpc/rpc-mode.js +522 -0
- package/dist/modes/rpc/rpc-mode.js.map +1 -0
- package/dist/modes/rpc/rpc-types.d.ts +408 -0
- package/dist/modes/rpc/rpc-types.d.ts.map +1 -0
- package/dist/modes/rpc/rpc-types.js +8 -0
- package/dist/modes/rpc/rpc-types.js.map +1 -0
- package/dist/utils/changelog.d.ts +21 -0
- package/dist/utils/changelog.d.ts.map +1 -0
- package/dist/utils/changelog.js +87 -0
- package/dist/utils/changelog.js.map +1 -0
- package/dist/utils/child-process.d.ts +11 -0
- package/dist/utils/child-process.d.ts.map +1 -0
- package/dist/utils/child-process.js +78 -0
- package/dist/utils/child-process.js.map +1 -0
- package/dist/utils/clipboard-image.d.ts +11 -0
- package/dist/utils/clipboard-image.d.ts.map +1 -0
- package/dist/utils/clipboard-image.js +245 -0
- package/dist/utils/clipboard-image.js.map +1 -0
- package/dist/utils/clipboard-native.d.ts +8 -0
- package/dist/utils/clipboard-native.d.ts.map +1 -0
- package/dist/utils/clipboard-native.js +14 -0
- package/dist/utils/clipboard-native.js.map +1 -0
- package/dist/utils/clipboard.d.ts +2 -0
- package/dist/utils/clipboard.d.ts.map +1 -0
- package/dist/utils/clipboard.js +78 -0
- package/dist/utils/clipboard.js.map +1 -0
- package/dist/utils/exif-orientation.d.ts +5 -0
- package/dist/utils/exif-orientation.d.ts.map +1 -0
- package/dist/utils/exif-orientation.js +158 -0
- package/dist/utils/exif-orientation.js.map +1 -0
- package/dist/utils/frontmatter.d.ts +8 -0
- package/dist/utils/frontmatter.d.ts.map +1 -0
- package/dist/utils/frontmatter.js +26 -0
- package/dist/utils/frontmatter.js.map +1 -0
- package/dist/utils/git.d.ts +26 -0
- package/dist/utils/git.d.ts.map +1 -0
- package/dist/utils/git.js +163 -0
- package/dist/utils/git.js.map +1 -0
- package/dist/utils/image-convert.d.ts +9 -0
- package/dist/utils/image-convert.d.ts.map +1 -0
- package/dist/utils/image-convert.js +39 -0
- package/dist/utils/image-convert.js.map +1 -0
- package/dist/utils/image-resize.d.ts +36 -0
- package/dist/utils/image-resize.d.ts.map +1 -0
- package/dist/utils/image-resize.js +137 -0
- package/dist/utils/image-resize.js.map +1 -0
- package/dist/utils/mime.d.ts +2 -0
- package/dist/utils/mime.d.ts.map +1 -0
- package/dist/utils/mime.js +26 -0
- package/dist/utils/mime.js.map +1 -0
- package/dist/utils/photon.d.ts +21 -0
- package/dist/utils/photon.d.ts.map +1 -0
- package/dist/utils/photon.js +121 -0
- package/dist/utils/photon.js.map +1 -0
- package/dist/utils/shell.d.ts +26 -0
- package/dist/utils/shell.d.ts.map +1 -0
- package/dist/utils/shell.js +186 -0
- package/dist/utils/shell.js.map +1 -0
- package/dist/utils/sleep.d.ts +5 -0
- package/dist/utils/sleep.d.ts.map +1 -0
- package/dist/utils/sleep.js +17 -0
- package/dist/utils/sleep.js.map +1 -0
- package/dist/utils/tools-manager.d.ts +3 -0
- package/dist/utils/tools-manager.d.ts.map +1 -0
- package/dist/utils/tools-manager.js +252 -0
- package/dist/utils/tools-manager.js.map +1 -0
- package/docs/compaction.md +394 -0
- package/docs/custom-provider.md +327 -0
- package/docs/extensions.md +2229 -0
- package/docs/images/doom-extension.png +0 -0
- package/docs/images/exy.png +0 -0
- package/docs/images/interactive-mode.png +0 -0
- package/docs/images/tree-view.png +0 -0
- package/docs/json.md +82 -0
- package/docs/keybindings.md +173 -0
- package/docs/models.md +197 -0
- package/docs/packages.md +218 -0
- package/docs/prompt-templates.md +67 -0
- package/docs/providers.md +98 -0
- package/docs/release.md +40 -0
- package/docs/rpc.md +1377 -0
- package/docs/sdk.md +971 -0
- package/docs/session.md +412 -0
- package/docs/settings.md +149 -0
- package/docs/shell-aliases.md +13 -0
- package/docs/skills.md +232 -0
- package/docs/terminal-setup.md +106 -0
- package/docs/termux.md +127 -0
- package/docs/themes.md +295 -0
- package/docs/tmux.md +61 -0
- package/docs/tree.md +228 -0
- package/docs/tui.md +887 -0
- package/docs/windows.md +17 -0
- package/examples/README.md +25 -0
- package/examples/extensions/README.md +204 -0
- package/examples/extensions/auto-commit-on-exit.ts +49 -0
- package/examples/extensions/bash-spawn-hook.ts +30 -0
- package/examples/extensions/bookmark.ts +50 -0
- package/examples/extensions/built-in-tool-renderer.ts +246 -0
- package/examples/extensions/claude-rules.ts +86 -0
- package/examples/extensions/commands.ts +72 -0
- package/examples/extensions/confirm-destructive.ts +59 -0
- package/examples/extensions/custom-compaction.ts +127 -0
- package/examples/extensions/custom-footer.ts +64 -0
- package/examples/extensions/custom-header.ts +73 -0
- package/examples/extensions/custom-provider-anthropic/index.ts +604 -0
- package/examples/extensions/custom-provider-anthropic/package.json +19 -0
- package/examples/extensions/custom-provider-gitlab-duo/index.ts +349 -0
- package/examples/extensions/custom-provider-gitlab-duo/package.json +16 -0
- package/examples/extensions/custom-provider-gitlab-duo/test.ts +82 -0
- package/examples/extensions/dirty-repo-guard.ts +56 -0
- package/examples/extensions/doom-overlay/README.md +46 -0
- package/examples/extensions/doom-overlay/doom/build/doom.js +21 -0
- package/examples/extensions/doom-overlay/doom/build/doom.wasm +0 -0
- package/examples/extensions/doom-overlay/doom/build.sh +152 -0
- package/examples/extensions/doom-overlay/doom/doomgeneric_pi.c +72 -0
- package/examples/extensions/doom-overlay/doom-component.ts +132 -0
- package/examples/extensions/doom-overlay/doom-engine.ts +173 -0
- package/examples/extensions/doom-overlay/doom-keys.ts +104 -0
- package/examples/extensions/doom-overlay/index.ts +74 -0
- package/examples/extensions/doom-overlay/wad-finder.ts +51 -0
- package/examples/extensions/dynamic-resources/SKILL.md +8 -0
- package/examples/extensions/dynamic-resources/dynamic.json +79 -0
- package/examples/extensions/dynamic-resources/dynamic.md +5 -0
- package/examples/extensions/dynamic-resources/index.ts +15 -0
- package/examples/extensions/dynamic-tools.ts +74 -0
- package/examples/extensions/event-bus.ts +43 -0
- package/examples/extensions/file-trigger.ts +41 -0
- package/examples/extensions/git-checkpoint.ts +53 -0
- package/examples/extensions/handoff.ts +153 -0
- package/examples/extensions/hello.ts +25 -0
- package/examples/extensions/hidden-thinking-label.ts +57 -0
- package/examples/extensions/inline-bash.ts +94 -0
- package/examples/extensions/input-transform.ts +43 -0
- package/examples/extensions/interactive-shell.ts +196 -0
- package/examples/extensions/mac-system-theme.ts +47 -0
- package/examples/extensions/message-renderer.ts +59 -0
- package/examples/extensions/minimal-mode.ts +426 -0
- package/examples/extensions/modal-editor.ts +85 -0
- package/examples/extensions/model-status.ts +31 -0
- package/examples/extensions/notify.ts +55 -0
- package/examples/extensions/overlay-qa-tests.ts +1348 -0
- package/examples/extensions/overlay-test.ts +150 -0
- package/examples/extensions/permission-gate.ts +34 -0
- package/examples/extensions/pirate.ts +47 -0
- package/examples/extensions/plan-mode/README.md +65 -0
- package/examples/extensions/plan-mode/index.ts +340 -0
- package/examples/extensions/plan-mode/utils.ts +166 -0
- package/examples/extensions/preset.ts +397 -0
- package/examples/extensions/protected-paths.ts +30 -0
- package/examples/extensions/provider-payload.ts +14 -0
- package/examples/extensions/qna.ts +122 -0
- package/examples/extensions/question.ts +264 -0
- package/examples/extensions/questionnaire.ts +427 -0
- package/examples/extensions/rainbow-editor.ts +88 -0
- package/examples/extensions/reload-runtime.ts +37 -0
- package/examples/extensions/rpc-demo.ts +124 -0
- package/examples/extensions/sandbox/index.ts +321 -0
- package/examples/extensions/sandbox/package.json +19 -0
- package/examples/extensions/send-user-message.ts +97 -0
- package/examples/extensions/session-name.ts +27 -0
- package/examples/extensions/shutdown-command.ts +63 -0
- package/examples/extensions/snake.ts +343 -0
- package/examples/extensions/space-invaders.ts +560 -0
- package/examples/extensions/ssh.ts +220 -0
- package/examples/extensions/status-line.ts +40 -0
- package/examples/extensions/subagent/README.md +172 -0
- package/examples/extensions/subagent/agents/planner.md +37 -0
- package/examples/extensions/subagent/agents/reviewer.md +35 -0
- package/examples/extensions/subagent/agents/scout.md +50 -0
- package/examples/extensions/subagent/agents/worker.md +24 -0
- package/examples/extensions/subagent/agents.ts +126 -0
- package/examples/extensions/subagent/index.ts +986 -0
- package/examples/extensions/subagent/prompts/implement-and-review.md +10 -0
- package/examples/extensions/subagent/prompts/implement.md +10 -0
- package/examples/extensions/subagent/prompts/scout-and-plan.md +9 -0
- package/examples/extensions/summarize.ts +206 -0
- package/examples/extensions/system-prompt-header.ts +17 -0
- package/examples/extensions/timed-confirm.ts +70 -0
- package/examples/extensions/titlebar-spinner.ts +58 -0
- package/examples/extensions/todo.ts +299 -0
- package/examples/extensions/tool-override.ts +144 -0
- package/examples/extensions/tools.ts +146 -0
- package/examples/extensions/trigger-compact.ts +50 -0
- package/examples/extensions/truncated-tool.ts +195 -0
- package/examples/extensions/widget-placement.ts +17 -0
- package/examples/extensions/with-deps/index.ts +32 -0
- package/examples/extensions/with-deps/package.json +22 -0
- package/examples/rpc-extension-ui.ts +632 -0
- package/examples/sdk/01-minimal.ts +22 -0
- package/examples/sdk/02-custom-model.ts +49 -0
- package/examples/sdk/03-custom-prompt.ts +55 -0
- package/examples/sdk/04-skills.ts +52 -0
- package/examples/sdk/05-tools.ts +56 -0
- package/examples/sdk/06-extensions.ts +88 -0
- package/examples/sdk/07-context-files.ts +40 -0
- package/examples/sdk/08-prompt-templates.ts +48 -0
- package/examples/sdk/09-api-keys-and-oauth.ts +48 -0
- package/examples/sdk/10-settings.ts +51 -0
- package/examples/sdk/11-sessions.ts +48 -0
- package/examples/sdk/12-full-control.ts +81 -0
- package/examples/sdk/README.md +144 -0
- package/package.json +95 -0
- package/src/bun/cli.ts +5 -0
- package/src/cli/args.ts +309 -0
- package/src/cli/config-selector.ts +52 -0
- package/src/cli/file-processor.ts +100 -0
- package/src/cli/initial-message.ts +43 -0
- package/src/cli/list-models.ts +104 -0
- package/src/cli/session-picker.ts +52 -0
- package/src/cli.ts +16 -0
- package/src/config.ts +214 -0
- package/src/core/agent-session.ts +3279 -0
- package/src/core/auth-storage.ts +488 -0
- package/src/core/bash-executor.ts +158 -0
- package/src/core/compaction/branch-summarization.ts +355 -0
- package/src/core/compaction/compaction.ts +823 -0
- package/src/core/compaction/index.ts +7 -0
- package/src/core/compaction/utils.ts +170 -0
- package/src/core/defaults.ts +3 -0
- package/src/core/diagnostics.ts +15 -0
- package/src/core/event-bus.ts +33 -0
- package/src/core/exec.ts +107 -0
- package/src/core/export-html/ansi-to-html.ts +258 -0
- package/src/core/export-html/index.ts +314 -0
- package/src/core/export-html/template.css +1001 -0
- package/src/core/export-html/template.html +55 -0
- package/src/core/export-html/template.js +1690 -0
- package/src/core/export-html/tool-renderer.ts +156 -0
- package/src/core/export-html/vendor/highlight.min.js +1213 -0
- package/src/core/export-html/vendor/marked.min.js +6 -0
- package/src/core/extensions/index.ts +168 -0
- package/src/core/extensions/loader.ts +557 -0
- package/src/core/extensions/runner.ts +915 -0
- package/src/core/extensions/types.ts +1461 -0
- package/src/core/extensions/wrapper.ts +27 -0
- package/src/core/footer-data-provider.ts +273 -0
- package/src/core/index.ts +61 -0
- package/src/core/keybindings.ts +302 -0
- package/src/core/messages.ts +195 -0
- package/src/core/model-registry.ts +766 -0
- package/src/core/model-resolver.ts +606 -0
- package/src/core/output-guard.ts +74 -0
- package/src/core/package-manager.ts +2222 -0
- package/src/core/prompt-templates.ts +294 -0
- package/src/core/resolve-config-value.ts +142 -0
- package/src/core/resource-loader.ts +886 -0
- package/src/core/sdk.ts +360 -0
- package/src/core/self-update.ts +57 -0
- package/src/core/session-manager.ts +1410 -0
- package/src/core/settings-manager.ts +973 -0
- package/src/core/skills.ts +508 -0
- package/src/core/slash-commands.ts +37 -0
- package/src/core/source-info.ts +40 -0
- package/src/core/system-prompt.ts +168 -0
- package/src/core/timings.ts +31 -0
- package/src/core/tools/bash.ts +431 -0
- package/src/core/tools/edit-diff.ts +445 -0
- package/src/core/tools/edit.ts +307 -0
- package/src/core/tools/file-mutation-queue.ts +39 -0
- package/src/core/tools/find.ts +314 -0
- package/src/core/tools/grep.ts +375 -0
- package/src/core/tools/index.ts +193 -0
- package/src/core/tools/ls.ts +233 -0
- package/src/core/tools/path-utils.ts +94 -0
- package/src/core/tools/read.ts +269 -0
- package/src/core/tools/render-utils.ts +64 -0
- package/src/core/tools/tool-definition-wrapper.ts +43 -0
- package/src/core/tools/truncate.ts +265 -0
- package/src/core/tools/write.ts +285 -0
- package/src/core/version-check.ts +85 -0
- package/src/index.ts +348 -0
- package/src/main.ts +958 -0
- package/src/migrations.ts +290 -0
- package/src/modes/index.ts +9 -0
- package/src/modes/interactive/components/armin.ts +382 -0
- package/src/modes/interactive/components/assistant-message.ts +130 -0
- package/src/modes/interactive/components/bash-execution.ts +218 -0
- package/src/modes/interactive/components/bordered-loader.ts +66 -0
- package/src/modes/interactive/components/branch-summary-message.ts +58 -0
- package/src/modes/interactive/components/compaction-summary-message.ts +59 -0
- package/src/modes/interactive/components/config-selector.ts +592 -0
- package/src/modes/interactive/components/countdown-timer.ts +38 -0
- package/src/modes/interactive/components/custom-editor.ts +80 -0
- package/src/modes/interactive/components/custom-message.ts +99 -0
- package/src/modes/interactive/components/diff.ts +147 -0
- package/src/modes/interactive/components/dynamic-border.ts +25 -0
- package/src/modes/interactive/components/extension-editor.ts +147 -0
- package/src/modes/interactive/components/extension-input.ts +87 -0
- package/src/modes/interactive/components/extension-selector.ts +107 -0
- package/src/modes/interactive/components/footer.ts +216 -0
- package/src/modes/interactive/components/index.ts +31 -0
- package/src/modes/interactive/components/keybinding-hints.ts +24 -0
- package/src/modes/interactive/components/login-dialog.ts +178 -0
- package/src/modes/interactive/components/model-selector.ts +328 -0
- package/src/modes/interactive/components/oauth-selector.ts +121 -0
- package/src/modes/interactive/components/scoped-models-selector.ts +346 -0
- package/src/modes/interactive/components/session-selector-search.ts +194 -0
- package/src/modes/interactive/components/session-selector.ts +1010 -0
- package/src/modes/interactive/components/settings-selector.ts +432 -0
- package/src/modes/interactive/components/show-images-selector.ts +50 -0
- package/src/modes/interactive/components/skill-invocation-message.ts +55 -0
- package/src/modes/interactive/components/theme-selector.ts +67 -0
- package/src/modes/interactive/components/thinking-selector.ts +74 -0
- package/src/modes/interactive/components/tool-execution.ts +328 -0
- package/src/modes/interactive/components/tree-selector.ts +1197 -0
- package/src/modes/interactive/components/user-message-selector.ts +143 -0
- package/src/modes/interactive/components/user-message.ts +33 -0
- package/src/modes/interactive/components/visual-truncate.ts +50 -0
- package/src/modes/interactive/interactive-mode.ts +4501 -0
- package/src/modes/interactive/theme/dark.json +85 -0
- package/src/modes/interactive/theme/light.json +84 -0
- package/src/modes/interactive/theme/theme-schema.json +335 -0
- package/src/modes/interactive/theme/theme.ts +1137 -0
- package/src/modes/print-mode.ts +131 -0
- package/src/modes/rpc/jsonl.ts +58 -0
- package/src/modes/rpc/rpc-client.ts +505 -0
- package/src/modes/rpc/rpc-mode.ts +654 -0
- package/src/modes/rpc/rpc-types.ts +262 -0
- package/src/utils/changelog.ts +99 -0
- package/src/utils/child-process.ts +86 -0
- package/src/utils/clipboard-image.ts +300 -0
- package/src/utils/clipboard-native.ts +22 -0
- package/src/utils/clipboard.ts +81 -0
- package/src/utils/exif-orientation.ts +183 -0
- package/src/utils/frontmatter.ts +39 -0
- package/src/utils/git.ts +192 -0
- package/src/utils/image-convert.ts +41 -0
- package/src/utils/image-resize.ts +176 -0
- package/src/utils/mime.ts +30 -0
- package/src/utils/photon.ts +139 -0
- package/src/utils/shell.ts +202 -0
- package/src/utils/sleep.ts +18 -0
- package/src/utils/tools-manager.ts +287 -0
|
@@ -0,0 +1,307 @@
|
|
|
1
|
+
import type { AgentTool } from "@lenylvt/pi-agent-core";
|
|
2
|
+
import { Container, Text } from "@lenylvt/pi-tui";
|
|
3
|
+
import { type Static, Type } from "@sinclair/typebox";
|
|
4
|
+
import { constants } from "fs";
|
|
5
|
+
import { access as fsAccess, readFile as fsReadFile, writeFile as fsWriteFile } from "fs/promises";
|
|
6
|
+
import { renderDiff } from "../../modes/interactive/components/diff.js";
|
|
7
|
+
import type { ToolDefinition } from "../extensions/types.js";
|
|
8
|
+
import {
|
|
9
|
+
applyEditsToNormalizedContent,
|
|
10
|
+
detectLineEnding,
|
|
11
|
+
type Edit,
|
|
12
|
+
generateDiffString,
|
|
13
|
+
normalizeToLF,
|
|
14
|
+
restoreLineEndings,
|
|
15
|
+
stripBom,
|
|
16
|
+
} from "./edit-diff.js";
|
|
17
|
+
import { withFileMutationQueue } from "./file-mutation-queue.js";
|
|
18
|
+
import { resolveToCwd } from "./path-utils.js";
|
|
19
|
+
import { invalidArgText, shortenPath, str } from "./render-utils.js";
|
|
20
|
+
import { wrapToolDefinition } from "./tool-definition-wrapper.js";
|
|
21
|
+
|
|
22
|
+
type EditRenderState = Record<string, never>;
|
|
23
|
+
|
|
24
|
+
const replaceEditSchema = Type.Object(
|
|
25
|
+
{
|
|
26
|
+
oldText: Type.String({
|
|
27
|
+
description:
|
|
28
|
+
"Exact text for one targeted replacement. It must be unique in the original file and must not overlap with any other edits[].oldText in the same call.",
|
|
29
|
+
}),
|
|
30
|
+
newText: Type.String({ description: "Replacement text for this targeted edit." }),
|
|
31
|
+
},
|
|
32
|
+
{ additionalProperties: false },
|
|
33
|
+
);
|
|
34
|
+
|
|
35
|
+
const editSchema = Type.Object(
|
|
36
|
+
{
|
|
37
|
+
path: Type.String({ description: "Path to the file to edit (relative or absolute)" }),
|
|
38
|
+
edits: Type.Array(replaceEditSchema, {
|
|
39
|
+
description:
|
|
40
|
+
"One or more targeted replacements. Each edit is matched against the original file, not incrementally. Do not include overlapping or nested edits. If two changes touch the same block or nearby lines, merge them into one edit instead.",
|
|
41
|
+
}),
|
|
42
|
+
},
|
|
43
|
+
{ additionalProperties: false },
|
|
44
|
+
);
|
|
45
|
+
|
|
46
|
+
export type EditToolInput = Static<typeof editSchema>;
|
|
47
|
+
type LegacyEditToolInput = EditToolInput & {
|
|
48
|
+
oldText?: unknown;
|
|
49
|
+
newText?: unknown;
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
export interface EditToolDetails {
|
|
53
|
+
/** Unified diff of the changes made */
|
|
54
|
+
diff: string;
|
|
55
|
+
/** Line number of the first change in the new file (for editor navigation) */
|
|
56
|
+
firstChangedLine?: number;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* Pluggable operations for the edit tool.
|
|
61
|
+
* Override these to delegate file editing to remote systems (for example SSH).
|
|
62
|
+
*/
|
|
63
|
+
export interface EditOperations {
|
|
64
|
+
/** Read file contents as a Buffer */
|
|
65
|
+
readFile: (absolutePath: string) => Promise<Buffer>;
|
|
66
|
+
/** Write content to a file */
|
|
67
|
+
writeFile: (absolutePath: string, content: string) => Promise<void>;
|
|
68
|
+
/** Check if file is readable and writable (throw if not) */
|
|
69
|
+
access: (absolutePath: string) => Promise<void>;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
const defaultEditOperations: EditOperations = {
|
|
73
|
+
readFile: (path) => fsReadFile(path),
|
|
74
|
+
writeFile: (path, content) => fsWriteFile(path, content, "utf-8"),
|
|
75
|
+
access: (path) => fsAccess(path, constants.R_OK | constants.W_OK),
|
|
76
|
+
};
|
|
77
|
+
|
|
78
|
+
export interface EditToolOptions {
|
|
79
|
+
/** Custom operations for file editing. Default: local filesystem */
|
|
80
|
+
operations?: EditOperations;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
function prepareEditArguments(input: unknown): EditToolInput {
|
|
84
|
+
if (!input || typeof input !== "object") {
|
|
85
|
+
return input as EditToolInput;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
const args = input as LegacyEditToolInput;
|
|
89
|
+
if (typeof args.oldText !== "string" || typeof args.newText !== "string") {
|
|
90
|
+
return input as EditToolInput;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
const edits = Array.isArray(args.edits) ? [...args.edits] : [];
|
|
94
|
+
edits.push({ oldText: args.oldText, newText: args.newText });
|
|
95
|
+
const { oldText: _oldText, newText: _newText, ...rest } = args;
|
|
96
|
+
return { ...rest, edits } as EditToolInput;
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
function validateEditInput(input: EditToolInput): { path: string; edits: Edit[] } {
|
|
100
|
+
if (!Array.isArray(input.edits) || input.edits.length === 0) {
|
|
101
|
+
throw new Error("Edit tool input is invalid. edits must contain at least one replacement.");
|
|
102
|
+
}
|
|
103
|
+
return { path: input.path, edits: input.edits };
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
type RenderableEditArgs = {
|
|
107
|
+
path?: string;
|
|
108
|
+
file_path?: string;
|
|
109
|
+
edits?: Edit[];
|
|
110
|
+
oldText?: string;
|
|
111
|
+
newText?: string;
|
|
112
|
+
};
|
|
113
|
+
|
|
114
|
+
function formatEditCall(
|
|
115
|
+
args: RenderableEditArgs | undefined,
|
|
116
|
+
theme: typeof import("../../modes/interactive/theme/theme.js").theme,
|
|
117
|
+
): string {
|
|
118
|
+
const invalidArg = invalidArgText(theme);
|
|
119
|
+
const rawPath = str(args?.file_path ?? args?.path);
|
|
120
|
+
const path = rawPath !== null ? shortenPath(rawPath) : null;
|
|
121
|
+
const pathDisplay = path === null ? invalidArg : path ? theme.fg("accent", path) : theme.fg("toolOutput", "...");
|
|
122
|
+
return `${theme.fg("toolTitle", theme.bold("edit"))} ${pathDisplay}`;
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
function formatEditResult(
|
|
126
|
+
args: RenderableEditArgs | undefined,
|
|
127
|
+
result: {
|
|
128
|
+
content: Array<{ type: string; text?: string; data?: string; mimeType?: string }>;
|
|
129
|
+
details?: EditToolDetails;
|
|
130
|
+
},
|
|
131
|
+
theme: typeof import("../../modes/interactive/theme/theme.js").theme,
|
|
132
|
+
isError: boolean,
|
|
133
|
+
): string | undefined {
|
|
134
|
+
const rawPath = str(args?.file_path ?? args?.path);
|
|
135
|
+
if (isError) {
|
|
136
|
+
const errorText = result.content
|
|
137
|
+
.filter((c) => c.type === "text")
|
|
138
|
+
.map((c) => c.text || "")
|
|
139
|
+
.join("\n");
|
|
140
|
+
if (!errorText) {
|
|
141
|
+
return undefined;
|
|
142
|
+
}
|
|
143
|
+
return `\n${theme.fg("error", errorText)}`;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
const resultDiff = result.details?.diff;
|
|
147
|
+
if (!resultDiff) {
|
|
148
|
+
return undefined;
|
|
149
|
+
}
|
|
150
|
+
return `\n${renderDiff(resultDiff, { filePath: rawPath ?? undefined })}`;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
export function createEditToolDefinition(
|
|
154
|
+
cwd: string,
|
|
155
|
+
options?: EditToolOptions,
|
|
156
|
+
): ToolDefinition<typeof editSchema, EditToolDetails | undefined, EditRenderState> {
|
|
157
|
+
const ops = options?.operations ?? defaultEditOperations;
|
|
158
|
+
return {
|
|
159
|
+
name: "edit",
|
|
160
|
+
label: "edit",
|
|
161
|
+
description:
|
|
162
|
+
"Edit a single file using exact text replacement. Every edits[].oldText must match a unique, non-overlapping region of the original file. If two changes affect the same block or nearby lines, merge them into one edit instead of emitting overlapping edits. Do not include large unchanged regions just to connect distant changes.",
|
|
163
|
+
promptSnippet:
|
|
164
|
+
"Make precise file edits with exact text replacement, including multiple disjoint edits in one call",
|
|
165
|
+
promptGuidelines: [
|
|
166
|
+
"Use edit for precise changes (edits[].oldText must match exactly)",
|
|
167
|
+
"When changing multiple separate locations in one file, use one edit call with multiple entries in edits[] instead of multiple edit calls",
|
|
168
|
+
"Each edits[].oldText is matched against the original file, not after earlier edits are applied. Do not emit overlapping or nested edits. Merge nearby changes into one edit.",
|
|
169
|
+
"Keep edits[].oldText as small as possible while still being unique in the file. Do not pad with large unchanged regions.",
|
|
170
|
+
],
|
|
171
|
+
parameters: editSchema,
|
|
172
|
+
prepareArguments: prepareEditArguments,
|
|
173
|
+
async execute(_toolCallId, input: EditToolInput, signal?: AbortSignal, _onUpdate?, _ctx?) {
|
|
174
|
+
const { path, edits } = validateEditInput(input);
|
|
175
|
+
const absolutePath = resolveToCwd(path, cwd);
|
|
176
|
+
|
|
177
|
+
return withFileMutationQueue(
|
|
178
|
+
absolutePath,
|
|
179
|
+
() =>
|
|
180
|
+
new Promise<{
|
|
181
|
+
content: Array<{ type: "text"; text: string }>;
|
|
182
|
+
details: EditToolDetails | undefined;
|
|
183
|
+
}>((resolve, reject) => {
|
|
184
|
+
// Check if already aborted.
|
|
185
|
+
if (signal?.aborted) {
|
|
186
|
+
reject(new Error("Operation aborted"));
|
|
187
|
+
return;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
let aborted = false;
|
|
191
|
+
|
|
192
|
+
// Set up abort handler.
|
|
193
|
+
const onAbort = () => {
|
|
194
|
+
aborted = true;
|
|
195
|
+
reject(new Error("Operation aborted"));
|
|
196
|
+
};
|
|
197
|
+
|
|
198
|
+
if (signal) {
|
|
199
|
+
signal.addEventListener("abort", onAbort, { once: true });
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
// Perform the edit operation.
|
|
203
|
+
void (async () => {
|
|
204
|
+
try {
|
|
205
|
+
// Check if file exists.
|
|
206
|
+
try {
|
|
207
|
+
await ops.access(absolutePath);
|
|
208
|
+
} catch {
|
|
209
|
+
if (signal) {
|
|
210
|
+
signal.removeEventListener("abort", onAbort);
|
|
211
|
+
}
|
|
212
|
+
reject(new Error(`File not found: ${path}`));
|
|
213
|
+
return;
|
|
214
|
+
}
|
|
215
|
+
|
|
216
|
+
// Check if aborted before reading.
|
|
217
|
+
if (aborted) {
|
|
218
|
+
return;
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
// Read the file.
|
|
222
|
+
const buffer = await ops.readFile(absolutePath);
|
|
223
|
+
const rawContent = buffer.toString("utf-8");
|
|
224
|
+
|
|
225
|
+
// Check if aborted after reading.
|
|
226
|
+
if (aborted) {
|
|
227
|
+
return;
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
// Strip BOM before matching. The model will not include an invisible BOM in oldText.
|
|
231
|
+
const { bom, text: content } = stripBom(rawContent);
|
|
232
|
+
const originalEnding = detectLineEnding(content);
|
|
233
|
+
const normalizedContent = normalizeToLF(content);
|
|
234
|
+
const { baseContent, newContent } = applyEditsToNormalizedContent(
|
|
235
|
+
normalizedContent,
|
|
236
|
+
edits,
|
|
237
|
+
path,
|
|
238
|
+
);
|
|
239
|
+
|
|
240
|
+
// Check if aborted before writing.
|
|
241
|
+
if (aborted) {
|
|
242
|
+
return;
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
const finalContent = bom + restoreLineEndings(newContent, originalEnding);
|
|
246
|
+
await ops.writeFile(absolutePath, finalContent);
|
|
247
|
+
|
|
248
|
+
// Check if aborted after writing.
|
|
249
|
+
if (aborted) {
|
|
250
|
+
return;
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
// Clean up abort handler.
|
|
254
|
+
if (signal) {
|
|
255
|
+
signal.removeEventListener("abort", onAbort);
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
const diffResult = generateDiffString(baseContent, newContent);
|
|
259
|
+
resolve({
|
|
260
|
+
content: [
|
|
261
|
+
{
|
|
262
|
+
type: "text",
|
|
263
|
+
text: `Successfully replaced ${edits.length} block(s) in ${path}.`,
|
|
264
|
+
},
|
|
265
|
+
],
|
|
266
|
+
details: { diff: diffResult.diff, firstChangedLine: diffResult.firstChangedLine },
|
|
267
|
+
});
|
|
268
|
+
} catch (error: unknown) {
|
|
269
|
+
// Clean up abort handler.
|
|
270
|
+
if (signal) {
|
|
271
|
+
signal.removeEventListener("abort", onAbort);
|
|
272
|
+
}
|
|
273
|
+
|
|
274
|
+
if (!aborted) {
|
|
275
|
+
reject(error instanceof Error ? error : new Error(String(error)));
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
})();
|
|
279
|
+
}),
|
|
280
|
+
);
|
|
281
|
+
},
|
|
282
|
+
renderCall(args, theme, context) {
|
|
283
|
+
const text = (context.lastComponent as Text | undefined) ?? new Text("", 0, 0);
|
|
284
|
+
text.setText(formatEditCall(args, theme));
|
|
285
|
+
return text;
|
|
286
|
+
},
|
|
287
|
+
renderResult(result, _options, theme, context) {
|
|
288
|
+
const output = formatEditResult(context.args, result as any, theme, context.isError);
|
|
289
|
+
if (!output) {
|
|
290
|
+
const component = (context.lastComponent as Container | undefined) ?? new Container();
|
|
291
|
+
component.clear();
|
|
292
|
+
return component;
|
|
293
|
+
}
|
|
294
|
+
const text = (context.lastComponent as Text | undefined) ?? new Text("", 0, 0);
|
|
295
|
+
text.setText(output);
|
|
296
|
+
return text;
|
|
297
|
+
},
|
|
298
|
+
};
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
export function createEditTool(cwd: string, options?: EditToolOptions): AgentTool<typeof editSchema> {
|
|
302
|
+
return wrapToolDefinition(createEditToolDefinition(cwd, options));
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
/** Default edit tool using process.cwd() for backwards compatibility. */
|
|
306
|
+
export const editToolDefinition = createEditToolDefinition(process.cwd());
|
|
307
|
+
export const editTool = createEditTool(process.cwd());
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { realpathSync } from "node:fs";
|
|
2
|
+
import { resolve } from "node:path";
|
|
3
|
+
|
|
4
|
+
const fileMutationQueues = new Map<string, Promise<void>>();
|
|
5
|
+
|
|
6
|
+
function getMutationQueueKey(filePath: string): string {
|
|
7
|
+
const resolvedPath = resolve(filePath);
|
|
8
|
+
try {
|
|
9
|
+
return realpathSync.native(resolvedPath);
|
|
10
|
+
} catch {
|
|
11
|
+
return resolvedPath;
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Serialize file mutation operations targeting the same file.
|
|
17
|
+
* Operations for different files still run in parallel.
|
|
18
|
+
*/
|
|
19
|
+
export async function withFileMutationQueue<T>(filePath: string, fn: () => Promise<T>): Promise<T> {
|
|
20
|
+
const key = getMutationQueueKey(filePath);
|
|
21
|
+
const currentQueue = fileMutationQueues.get(key) ?? Promise.resolve();
|
|
22
|
+
|
|
23
|
+
let releaseNext!: () => void;
|
|
24
|
+
const nextQueue = new Promise<void>((resolveQueue) => {
|
|
25
|
+
releaseNext = resolveQueue;
|
|
26
|
+
});
|
|
27
|
+
const chainedQueue = currentQueue.then(() => nextQueue);
|
|
28
|
+
fileMutationQueues.set(key, chainedQueue);
|
|
29
|
+
|
|
30
|
+
await currentQueue;
|
|
31
|
+
try {
|
|
32
|
+
return await fn();
|
|
33
|
+
} finally {
|
|
34
|
+
releaseNext();
|
|
35
|
+
if (fileMutationQueues.get(key) === chainedQueue) {
|
|
36
|
+
fileMutationQueues.delete(key);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
}
|
|
@@ -0,0 +1,314 @@
|
|
|
1
|
+
import type { AgentTool } from "@lenylvt/pi-agent-core";
|
|
2
|
+
import { Text } from "@lenylvt/pi-tui";
|
|
3
|
+
import { type Static, Type } from "@sinclair/typebox";
|
|
4
|
+
import { spawnSync } from "child_process";
|
|
5
|
+
import { existsSync } from "fs";
|
|
6
|
+
import { globSync } from "glob";
|
|
7
|
+
import path from "path";
|
|
8
|
+
import { keyHint } from "../../modes/interactive/components/keybinding-hints.js";
|
|
9
|
+
import { ensureTool } from "../../utils/tools-manager.js";
|
|
10
|
+
import type { ToolDefinition, ToolRenderResultOptions } from "../extensions/types.js";
|
|
11
|
+
import { resolveToCwd } from "./path-utils.js";
|
|
12
|
+
import { getTextOutput, invalidArgText, shortenPath, str } from "./render-utils.js";
|
|
13
|
+
import { wrapToolDefinition } from "./tool-definition-wrapper.js";
|
|
14
|
+
import { DEFAULT_MAX_BYTES, formatSize, type TruncationResult, truncateHead } from "./truncate.js";
|
|
15
|
+
|
|
16
|
+
function toPosixPath(value: string): string {
|
|
17
|
+
return value.split(path.sep).join("/");
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
const findSchema = Type.Object({
|
|
21
|
+
pattern: Type.String({
|
|
22
|
+
description: "Glob pattern to match files, e.g. '*.ts', '**/*.json', or 'src/**/*.spec.ts'",
|
|
23
|
+
}),
|
|
24
|
+
path: Type.Optional(Type.String({ description: "Directory to search in (default: current directory)" })),
|
|
25
|
+
limit: Type.Optional(Type.Number({ description: "Maximum number of results (default: 1000)" })),
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
export type FindToolInput = Static<typeof findSchema>;
|
|
29
|
+
|
|
30
|
+
const DEFAULT_LIMIT = 1000;
|
|
31
|
+
|
|
32
|
+
export interface FindToolDetails {
|
|
33
|
+
truncation?: TruncationResult;
|
|
34
|
+
resultLimitReached?: number;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* Pluggable operations for the find tool.
|
|
39
|
+
* Override these to delegate file search to remote systems (for example SSH).
|
|
40
|
+
*/
|
|
41
|
+
export interface FindOperations {
|
|
42
|
+
/** Check if path exists */
|
|
43
|
+
exists: (absolutePath: string) => Promise<boolean> | boolean;
|
|
44
|
+
/** Find files matching glob pattern. Returns relative or absolute paths. */
|
|
45
|
+
glob: (pattern: string, cwd: string, options: { ignore: string[]; limit: number }) => Promise<string[]> | string[];
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
const defaultFindOperations: FindOperations = {
|
|
49
|
+
exists: existsSync,
|
|
50
|
+
// This is a placeholder. Actual fd execution happens in execute() when no custom glob is provided.
|
|
51
|
+
glob: () => [],
|
|
52
|
+
};
|
|
53
|
+
|
|
54
|
+
export interface FindToolOptions {
|
|
55
|
+
/** Custom operations for find. Default: local filesystem plus fd */
|
|
56
|
+
operations?: FindOperations;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
function formatFindCall(
|
|
60
|
+
args: { pattern: string; path?: string; limit?: number } | undefined,
|
|
61
|
+
theme: typeof import("../../modes/interactive/theme/theme.js").theme,
|
|
62
|
+
): string {
|
|
63
|
+
const pattern = str(args?.pattern);
|
|
64
|
+
const rawPath = str(args?.path);
|
|
65
|
+
const path = rawPath !== null ? shortenPath(rawPath || ".") : null;
|
|
66
|
+
const limit = args?.limit;
|
|
67
|
+
const invalidArg = invalidArgText(theme);
|
|
68
|
+
let text =
|
|
69
|
+
theme.fg("toolTitle", theme.bold("find")) +
|
|
70
|
+
" " +
|
|
71
|
+
(pattern === null ? invalidArg : theme.fg("accent", pattern || "")) +
|
|
72
|
+
theme.fg("toolOutput", ` in ${path === null ? invalidArg : path}`);
|
|
73
|
+
if (limit !== undefined) {
|
|
74
|
+
text += theme.fg("toolOutput", ` (limit ${limit})`);
|
|
75
|
+
}
|
|
76
|
+
return text;
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
function formatFindResult(
|
|
80
|
+
result: {
|
|
81
|
+
content: Array<{ type: string; text?: string; data?: string; mimeType?: string }>;
|
|
82
|
+
details?: FindToolDetails;
|
|
83
|
+
},
|
|
84
|
+
options: ToolRenderResultOptions,
|
|
85
|
+
theme: typeof import("../../modes/interactive/theme/theme.js").theme,
|
|
86
|
+
showImages: boolean,
|
|
87
|
+
): string {
|
|
88
|
+
const output = getTextOutput(result, showImages).trim();
|
|
89
|
+
let text = "";
|
|
90
|
+
if (output) {
|
|
91
|
+
const lines = output.split("\n");
|
|
92
|
+
const maxLines = options.expanded ? lines.length : 20;
|
|
93
|
+
const displayLines = lines.slice(0, maxLines);
|
|
94
|
+
const remaining = lines.length - maxLines;
|
|
95
|
+
text += `\n${displayLines.map((line) => theme.fg("toolOutput", line)).join("\n")}`;
|
|
96
|
+
if (remaining > 0) {
|
|
97
|
+
text += `${theme.fg("muted", `\n... (${remaining} more lines,`)} ${keyHint("app.tools.expand", "to expand")})`;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
const resultLimit = result.details?.resultLimitReached;
|
|
102
|
+
const truncation = result.details?.truncation;
|
|
103
|
+
if (resultLimit || truncation?.truncated) {
|
|
104
|
+
const warnings: string[] = [];
|
|
105
|
+
if (resultLimit) warnings.push(`${resultLimit} results limit`);
|
|
106
|
+
if (truncation?.truncated) warnings.push(`${formatSize(truncation.maxBytes ?? DEFAULT_MAX_BYTES)} limit`);
|
|
107
|
+
text += `\n${theme.fg("warning", `[Truncated: ${warnings.join(", ")}]`)}`;
|
|
108
|
+
}
|
|
109
|
+
return text;
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
export function createFindToolDefinition(
|
|
113
|
+
cwd: string,
|
|
114
|
+
options?: FindToolOptions,
|
|
115
|
+
): ToolDefinition<typeof findSchema, FindToolDetails | undefined> {
|
|
116
|
+
const customOps = options?.operations;
|
|
117
|
+
return {
|
|
118
|
+
name: "find",
|
|
119
|
+
label: "find",
|
|
120
|
+
description: `Search for files by glob pattern. Returns matching file paths relative to the search directory. Respects .gitignore. Output is truncated to ${DEFAULT_LIMIT} results or ${DEFAULT_MAX_BYTES / 1024}KB (whichever is hit first).`,
|
|
121
|
+
promptSnippet: "Find files by glob pattern (respects .gitignore)",
|
|
122
|
+
parameters: findSchema,
|
|
123
|
+
async execute(
|
|
124
|
+
_toolCallId,
|
|
125
|
+
{ pattern, path: searchDir, limit }: { pattern: string; path?: string; limit?: number },
|
|
126
|
+
signal?: AbortSignal,
|
|
127
|
+
_onUpdate?,
|
|
128
|
+
_ctx?,
|
|
129
|
+
) {
|
|
130
|
+
return new Promise((resolve, reject) => {
|
|
131
|
+
if (signal?.aborted) {
|
|
132
|
+
reject(new Error("Operation aborted"));
|
|
133
|
+
return;
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
const onAbort = () => reject(new Error("Operation aborted"));
|
|
137
|
+
signal?.addEventListener("abort", onAbort, { once: true });
|
|
138
|
+
|
|
139
|
+
(async () => {
|
|
140
|
+
try {
|
|
141
|
+
const searchPath = resolveToCwd(searchDir || ".", cwd);
|
|
142
|
+
const effectiveLimit = limit ?? DEFAULT_LIMIT;
|
|
143
|
+
const ops = customOps ?? defaultFindOperations;
|
|
144
|
+
|
|
145
|
+
// If custom operations provide glob(), use that instead of fd.
|
|
146
|
+
if (customOps?.glob) {
|
|
147
|
+
if (!(await ops.exists(searchPath))) {
|
|
148
|
+
reject(new Error(`Path not found: ${searchPath}`));
|
|
149
|
+
return;
|
|
150
|
+
}
|
|
151
|
+
const results = await ops.glob(pattern, searchPath, {
|
|
152
|
+
ignore: ["**/node_modules/**", "**/.git/**"],
|
|
153
|
+
limit: effectiveLimit,
|
|
154
|
+
});
|
|
155
|
+
signal?.removeEventListener("abort", onAbort);
|
|
156
|
+
if (results.length === 0) {
|
|
157
|
+
resolve({
|
|
158
|
+
content: [{ type: "text", text: "No files found matching pattern" }],
|
|
159
|
+
details: undefined,
|
|
160
|
+
});
|
|
161
|
+
return;
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
// Relativize paths against the search root for stable output.
|
|
165
|
+
const relativized = results.map((p) => {
|
|
166
|
+
if (p.startsWith(searchPath)) return toPosixPath(p.slice(searchPath.length + 1));
|
|
167
|
+
return toPosixPath(path.relative(searchPath, p));
|
|
168
|
+
});
|
|
169
|
+
const resultLimitReached = relativized.length >= effectiveLimit;
|
|
170
|
+
const rawOutput = relativized.join("\n");
|
|
171
|
+
const truncation = truncateHead(rawOutput, { maxLines: Number.MAX_SAFE_INTEGER });
|
|
172
|
+
let resultOutput = truncation.content;
|
|
173
|
+
const details: FindToolDetails = {};
|
|
174
|
+
const notices: string[] = [];
|
|
175
|
+
if (resultLimitReached) {
|
|
176
|
+
notices.push(`${effectiveLimit} results limit reached`);
|
|
177
|
+
details.resultLimitReached = effectiveLimit;
|
|
178
|
+
}
|
|
179
|
+
if (truncation.truncated) {
|
|
180
|
+
notices.push(`${formatSize(DEFAULT_MAX_BYTES)} limit reached`);
|
|
181
|
+
details.truncation = truncation;
|
|
182
|
+
}
|
|
183
|
+
if (notices.length > 0) {
|
|
184
|
+
resultOutput += `\n\n[${notices.join(". ")}]`;
|
|
185
|
+
}
|
|
186
|
+
resolve({
|
|
187
|
+
content: [{ type: "text", text: resultOutput }],
|
|
188
|
+
details: Object.keys(details).length > 0 ? details : undefined,
|
|
189
|
+
});
|
|
190
|
+
return;
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
// Default implementation uses fd.
|
|
194
|
+
const fdPath = await ensureTool("fd", true);
|
|
195
|
+
if (!fdPath) {
|
|
196
|
+
reject(new Error("fd is not available and could not be downloaded"));
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
// Build fd arguments.
|
|
201
|
+
const args: string[] = [
|
|
202
|
+
"--glob",
|
|
203
|
+
"--color=never",
|
|
204
|
+
"--hidden",
|
|
205
|
+
"--max-results",
|
|
206
|
+
String(effectiveLimit),
|
|
207
|
+
];
|
|
208
|
+
// Include .gitignore files from the search tree.
|
|
209
|
+
const gitignoreFiles = new Set<string>();
|
|
210
|
+
const rootGitignore = path.join(searchPath, ".gitignore");
|
|
211
|
+
if (existsSync(rootGitignore)) gitignoreFiles.add(rootGitignore);
|
|
212
|
+
try {
|
|
213
|
+
const nestedGitignores = globSync("**/.gitignore", {
|
|
214
|
+
cwd: searchPath,
|
|
215
|
+
dot: true,
|
|
216
|
+
absolute: true,
|
|
217
|
+
ignore: ["**/node_modules/**", "**/.git/**"],
|
|
218
|
+
});
|
|
219
|
+
for (const file of nestedGitignores) gitignoreFiles.add(file);
|
|
220
|
+
} catch {
|
|
221
|
+
// ignore
|
|
222
|
+
}
|
|
223
|
+
for (const gitignorePath of gitignoreFiles) args.push("--ignore-file", gitignorePath);
|
|
224
|
+
args.push(pattern, searchPath);
|
|
225
|
+
|
|
226
|
+
const result = spawnSync(fdPath, args, { encoding: "utf-8", maxBuffer: 10 * 1024 * 1024 });
|
|
227
|
+
signal?.removeEventListener("abort", onAbort);
|
|
228
|
+
if (result.error) {
|
|
229
|
+
reject(new Error(`Failed to run fd: ${result.error.message}`));
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
const output = result.stdout?.trim() || "";
|
|
234
|
+
if (result.status !== 0) {
|
|
235
|
+
const errorMsg = result.stderr?.trim() || `fd exited with code ${result.status}`;
|
|
236
|
+
if (!output) {
|
|
237
|
+
reject(new Error(errorMsg));
|
|
238
|
+
return;
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
if (!output) {
|
|
242
|
+
resolve({
|
|
243
|
+
content: [{ type: "text", text: "No files found matching pattern" }],
|
|
244
|
+
details: undefined,
|
|
245
|
+
});
|
|
246
|
+
return;
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
const lines = output.split("\n");
|
|
250
|
+
const relativized: string[] = [];
|
|
251
|
+
for (const rawLine of lines) {
|
|
252
|
+
const line = rawLine.replace(/\r$/, "").trim();
|
|
253
|
+
if (!line) continue;
|
|
254
|
+
const hadTrailingSlash = line.endsWith("/") || line.endsWith("\\");
|
|
255
|
+
let relativePath = line;
|
|
256
|
+
if (line.startsWith(searchPath)) {
|
|
257
|
+
relativePath = line.slice(searchPath.length + 1);
|
|
258
|
+
} else {
|
|
259
|
+
relativePath = path.relative(searchPath, line);
|
|
260
|
+
}
|
|
261
|
+
if (hadTrailingSlash && !relativePath.endsWith("/")) relativePath += "/";
|
|
262
|
+
relativized.push(toPosixPath(relativePath));
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
const resultLimitReached = relativized.length >= effectiveLimit;
|
|
266
|
+
const rawOutput = relativized.join("\n");
|
|
267
|
+
const truncation = truncateHead(rawOutput, { maxLines: Number.MAX_SAFE_INTEGER });
|
|
268
|
+
let resultOutput = truncation.content;
|
|
269
|
+
const details: FindToolDetails = {};
|
|
270
|
+
const notices: string[] = [];
|
|
271
|
+
if (resultLimitReached) {
|
|
272
|
+
notices.push(
|
|
273
|
+
`${effectiveLimit} results limit reached. Use limit=${effectiveLimit * 2} for more, or refine pattern`,
|
|
274
|
+
);
|
|
275
|
+
details.resultLimitReached = effectiveLimit;
|
|
276
|
+
}
|
|
277
|
+
if (truncation.truncated) {
|
|
278
|
+
notices.push(`${formatSize(DEFAULT_MAX_BYTES)} limit reached`);
|
|
279
|
+
details.truncation = truncation;
|
|
280
|
+
}
|
|
281
|
+
if (notices.length > 0) {
|
|
282
|
+
resultOutput += `\n\n[${notices.join(". ")}]`;
|
|
283
|
+
}
|
|
284
|
+
resolve({
|
|
285
|
+
content: [{ type: "text", text: resultOutput }],
|
|
286
|
+
details: Object.keys(details).length > 0 ? details : undefined,
|
|
287
|
+
});
|
|
288
|
+
} catch (e: any) {
|
|
289
|
+
signal?.removeEventListener("abort", onAbort);
|
|
290
|
+
reject(e);
|
|
291
|
+
}
|
|
292
|
+
})();
|
|
293
|
+
});
|
|
294
|
+
},
|
|
295
|
+
renderCall(args, theme, context) {
|
|
296
|
+
const text = (context.lastComponent as Text | undefined) ?? new Text("", 0, 0);
|
|
297
|
+
text.setText(formatFindCall(args, theme));
|
|
298
|
+
return text;
|
|
299
|
+
},
|
|
300
|
+
renderResult(result, options, theme, context) {
|
|
301
|
+
const text = (context.lastComponent as Text | undefined) ?? new Text("", 0, 0);
|
|
302
|
+
text.setText(formatFindResult(result as any, options, theme, context.showImages));
|
|
303
|
+
return text;
|
|
304
|
+
},
|
|
305
|
+
};
|
|
306
|
+
}
|
|
307
|
+
|
|
308
|
+
export function createFindTool(cwd: string, options?: FindToolOptions): AgentTool<typeof findSchema> {
|
|
309
|
+
return wrapToolDefinition(createFindToolDefinition(cwd, options));
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
/** Default find tool using process.cwd() for backwards compatibility. */
|
|
313
|
+
export const findToolDefinition = createFindToolDefinition(process.cwd());
|
|
314
|
+
export const findTool = createFindTool(process.cwd());
|