@oh-my-pi/pi-coding-agent 13.3.13 → 13.4.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.
Files changed (63) hide show
  1. package/CHANGELOG.md +97 -7
  2. package/examples/sdk/README.md +22 -0
  3. package/package.json +7 -7
  4. package/src/capability/index.ts +1 -11
  5. package/src/commit/analysis/index.ts +4 -4
  6. package/src/config/settings-schema.ts +18 -15
  7. package/src/config/settings.ts +2 -20
  8. package/src/discovery/index.ts +1 -11
  9. package/src/exa/index.ts +1 -10
  10. package/src/extensibility/custom-commands/index.ts +2 -15
  11. package/src/extensibility/custom-tools/index.ts +3 -18
  12. package/src/extensibility/custom-tools/loader.ts +28 -5
  13. package/src/extensibility/custom-tools/types.ts +18 -1
  14. package/src/extensibility/extensions/index.ts +9 -130
  15. package/src/extensibility/extensions/types.ts +2 -1
  16. package/src/extensibility/hooks/index.ts +3 -14
  17. package/src/extensibility/plugins/index.ts +6 -31
  18. package/src/index.ts +28 -220
  19. package/src/internal-urls/docs-index.generated.ts +3 -2
  20. package/src/internal-urls/index.ts +11 -16
  21. package/src/mcp/index.ts +11 -37
  22. package/src/mcp/tool-bridge.ts +3 -42
  23. package/src/mcp/transports/index.ts +2 -2
  24. package/src/modes/components/extensions/index.ts +3 -3
  25. package/src/modes/components/index.ts +35 -40
  26. package/src/modes/interactive-mode.ts +4 -1
  27. package/src/modes/rpc/rpc-mode.ts +1 -7
  28. package/src/modes/theme/theme.ts +11 -10
  29. package/src/modes/types.ts +1 -1
  30. package/src/patch/index.ts +4 -20
  31. package/src/prompts/system/system-prompt.md +18 -4
  32. package/src/prompts/tools/ast-edit.md +33 -0
  33. package/src/prompts/tools/ast-grep.md +34 -0
  34. package/src/prompts/tools/bash.md +2 -2
  35. package/src/prompts/tools/hashline.md +1 -0
  36. package/src/prompts/tools/resolve.md +8 -0
  37. package/src/sdk.ts +27 -7
  38. package/src/session/agent-session.ts +25 -36
  39. package/src/session/session-manager.ts +0 -30
  40. package/src/slash-commands/builtin-registry.ts +4 -2
  41. package/src/stt/index.ts +3 -3
  42. package/src/task/types.ts +2 -2
  43. package/src/tools/ast-edit.ts +480 -0
  44. package/src/tools/ast-grep.ts +435 -0
  45. package/src/tools/bash.ts +3 -2
  46. package/src/tools/gemini-image.ts +3 -3
  47. package/src/tools/grep.ts +26 -8
  48. package/src/tools/index.ts +55 -57
  49. package/src/tools/pending-action.ts +33 -0
  50. package/src/tools/render-utils.ts +10 -0
  51. package/src/tools/renderers.ts +6 -4
  52. package/src/tools/resolve.ts +156 -0
  53. package/src/tools/submit-result.ts +1 -1
  54. package/src/web/search/index.ts +6 -4
  55. package/src/web/search/providers/anthropic.ts +2 -2
  56. package/src/web/search/providers/base.ts +3 -0
  57. package/src/web/search/providers/exa.ts +11 -5
  58. package/src/web/search/providers/gemini.ts +112 -24
  59. package/src/patch/normative.ts +0 -72
  60. package/src/prompts/tools/ast-find.md +0 -20
  61. package/src/prompts/tools/ast-replace.md +0 -21
  62. package/src/tools/ast-find.ts +0 -316
  63. package/src/tools/ast-replace.ts +0 -294
package/CHANGELOG.md CHANGED
@@ -2,6 +2,75 @@
2
2
 
3
3
  ## [Unreleased]
4
4
 
5
+ ## [13.4.0] - 2026-03-01
6
+
7
+ ### Breaking Changes
8
+
9
+ - `ast_grep` parameter `pattern` (string) replaced by `patterns` (string[])
10
+ - `ast_edit` parameters `pattern` + `rewrite` replaced by `ops: Array<{ pat: string; out: string }>`
11
+
12
+ ### Added
13
+
14
+ - Added `resolve` tool to apply or discard pending preview actions with required reasoning
15
+ - AST edit now registers pending actions after preview, allowing explicit apply/discard workflow via `resolve` tool
16
+ - Custom tools can register pending actions via `pushPendingAction(action)` in `CustomToolAPI`, enabling the `resolve` workflow for custom preview-apply flows
17
+ - `deferrable?: boolean` field added to `AgentTool`, `CustomTool`, and `ToolDefinition` interfaces; tools that set it signal they may stage pending actions
18
+ - `HIDDEN_TOOLS` and `ResolveTool` exported from `@oh-my-pi/pi-coding-agent` SDK for manual tool composition
19
+ - `PendingActionStore` now uses a LIFO stack (`push`/`peek`/`pop`); multiple deferrable tools can stage actions that resolve in reverse order of registration
20
+ - Added `gemini`, `codex`, and `synthetic` as supported values for the `providers.webSearch` setting
21
+ - `ast_grep` tool now accepts a `patterns` array (replaces single `pattern`); multiple patterns run in one native pass and results are merged before offset/limit
22
+ - `ast_edit` tool now accepts an `ops` array of `{ pat, out }` entries (replaces `pattern` + `rewrite`); duplicate patterns are rejected upfront
23
+ - AST find output now uses `>>` prefix on match-start lines and pads line numbers; directory-tree grouping with `# dir` / `## └─ file` headers for directory-scoped searches
24
+ - AST replace output now renders diff-style (`-before` / `+after`) change previews grouped by directory
25
+ - Both AST tools now report `scopePath`, `files`, and per-file match/replacement counts in tool details
26
+ - Task item `id` max length raised from 32 to 48 characters
27
+ - Anthropic web search provider now uses `buildAnthropicSearchHeaders` (dedicated search header builder separate from inference headers)
28
+ - Gemini web search provider: endpoint fallback (daily → sandbox) with retry on 429/5xx
29
+ - Gemini web search now injects Antigravity system instruction and aligned request metadata (`requestType`, `userAgent`, `requestId`) for Antigravity credentials
30
+ - `buildGeminiRequestTools()` helper for composable Gemini tool configuration (googleSearch, codeExecution, urlContext)
31
+ - Web search schema exposes `max_tokens`, `temperature`, and `num_search_results` as tool parameters
32
+ - Web search provider fallback: when an explicit provider is unavailable, resolves the auto chain instead of returning empty results
33
+
34
+ ### Changed
35
+
36
+ - Simplified `resolve` tool output rendering to use inline highlighted format instead of boxed layout
37
+ - Updated `resolve` tool to parse source tool name from label using colon separator for cleaner display
38
+ - `resolve` tool is now conditionally injected: included only when at least one active tool has `deferrable: true` (previously always included)
39
+ - `discoverAndLoadCustomTools` / `loadCustomTools` accept an optional `pendingActionStore` parameter to wire `pushPendingAction` for custom tools
40
+ - AST edit tool no longer accepts `preview` parameter; all AST edit calls now return previews by default
41
+ - AST edit workflow changed: preview is always shown, then use `resolve` tool to apply or discard changes
42
+ - Agent now suggests calling `resolve` tool after AST edit preview with system reminder
43
+ - `ast_grep`: `include_meta` parameter removed; metavariable captures are now always included in output
44
+ - `ast_edit`: `dry_run` renamed to `preview`; `max_files` removed from schema and capped globally via `$PI_MAX_AST_FILES` (default 1000); `max_replacements` renamed to `limit`
45
+ - `ast_grep` and `ast_edit`: parse errors in tool output are now capped at `PARSE_ERRORS_LIMIT` (20); excess errors are summarised as `N / total parse issues` rather than flooding the context
46
+ - Updated `ast_grep` and `ast_edit` tool prompt examples to use concise, idiomatic patterns
47
+
48
+ ### Removed
49
+
50
+ - Removed `normativeRewrite` setting that rewrote tool call arguments to normalized format in session history
51
+ - Removed `buildNormativeUpdateInput()` helper and normative patch transformation logic
52
+
53
+ ### Fixed
54
+
55
+ - `ast_edit` no longer rejects empty `out` values; an empty string now deletes matched nodes
56
+ - `ast_edit` no longer trims `pat` and `out` values, preserving intentional whitespace
57
+ - `gemini_image` tool: corrected `responseModalities` values from `'Image'`/`'Text'` to uppercase `'IMAGE'`/`'TEXT'` matching the API enum
58
+
59
+ ## [13.3.14] - 2026-02-28
60
+
61
+ ### Added
62
+
63
+ - Expanded AST tool language support from 7 to all 25 ast-grep tree-sitter languages (Bash, C, C++, C#, CSS, Elixir, Go, Haskell, HCL, HTML, Java, JavaScript, JSON, Kotlin, Lua, Nix, PHP, Python, Ruby, Rust, Scala, Solidity, Swift, TSX, TypeScript, YAML)
64
+ - AST find now emits all lines of multiline matches with hashline tags (LINE#HASH:content) consistent with read/grep output
65
+ - Added AST pattern syntax reference (metavariables, wildcards, variadics) to system prompt
66
+ - Added examples and scoping guidance to ast-grep and ast-edit tool prompts
67
+ - Added `provider-schema-compatibility.test.ts`: integration test that instantiates every builtin and hidden tool, runs their parameter schemas through `adaptSchemaForStrict`, `sanitizeSchemaForGoogle`, and `prepareSchemaForCCA`, and asserts zero violations against each provider's compatibility rules
68
+
69
+ ### Fixed
70
+
71
+ - Non-code files (.md, .zip, .bin, .gitignore, etc.) are now silently skipped by AST tools instead of producing misleading parse errors
72
+ - Fixed `grep` path wildcard handling so file patterns passed via `path` (for example `schema-review-*.test.ts`) are resolved as glob filters instead of failing path existence checks
73
+
5
74
  ## [13.3.11] - 2026-02-28
6
75
 
7
76
  ### Fixed
@@ -13,9 +82,9 @@
13
82
 
14
83
  ### Added
15
84
 
16
- - Added `ast_find` tool for structural code search using AST matching via ast-grep, enabling syntax-aware pattern discovery across codebases
17
- - Added `ast_replace` tool for structural AST-aware rewrites via ast-grep, enabling safe syntax-level codemods without text-based fragility
18
- - Added `astFind.enabled` and `astReplace.enabled` settings to control availability of AST tools
85
+ - Added `ast_grep` tool for structural code search using AST matching via ast-grep, enabling syntax-aware pattern discovery across codebases
86
+ - Added `ast_edit` tool for structural AST-aware rewrites via ast-grep, enabling safe syntax-level codemods without text-based fragility
87
+ - Added `astGrep.enabled` and `astEdit.enabled` settings to control availability of AST tools
19
88
  - Added system prompt guidance to prefer AST tools over bash text manipulation (grep/sed/awk/perl) for syntax-aware operations
20
89
  - Extracted prompt formatting logic into reusable `formatPromptContent()` utility with configurable render phases and formatting options
21
90
  - Added `type_definition` action to navigate to symbol type definitions with source context
@@ -42,10 +111,10 @@
42
111
  - Updated HTML parsing API calls from `node-html-parser` to `linkedom` across all web scrapers (arXiv, IACR, Go pkg, Read the Docs, Twitter, Wikipedia)
43
112
  - Changed element text extraction from `.text` property to `.textContent` property for compatibility with linkedom DOM API
44
113
  - Optimized document link extraction to use regex-based parsing with deduplication and a 20-link limit instead of full DOM traversal
45
- - Unified `path` parameter in ast_find and ast_replace tools to accept files, directories, or glob patterns directly, eliminating the separate `glob` parameter
46
- - Removed `strictness` parameter from ast_find and ast_replace tools
47
- - Removed `fail_on_parse_error` parameter from ast_replace tool (now always false)
48
- - Updated ast_find and ast_replace prompt guidance to clarify that `path` accepts glob patterns and no longer requires separate glob specification
114
+ - Unified `path` parameter in ast_grep and ast_edit tools to accept files, directories, or glob patterns directly, eliminating the separate `glob` parameter
115
+ - Removed `strictness` parameter from ast_grep and ast_edit tools
116
+ - Removed `fail_on_parse_error` parameter from ast_edit tool (now always false)
117
+ - Updated ast_grep and ast_edit prompt guidance to clarify that `path` accepts glob patterns and no longer requires separate glob specification
49
118
  - Refactored prompt template rendering to use unified `formatPromptContent()` function with phase-aware formatting (pre-render vs post-render)
50
119
  - Updated `format-prompts.ts` script to use centralized prompt formatting utility instead of inline implementation
51
120
  - Replaced `column` parameter with `symbol` parameter for more intuitive position specification
@@ -92,6 +161,7 @@
92
161
  - Fixed `todo_write` task normalization to auto-activate the first remaining task and include explicit remaining-items output in tool results, removing the need for an immediate follow-up start update
93
162
 
94
163
  ## [13.3.7] - 2026-02-27
164
+
95
165
  ### Breaking Changes
96
166
 
97
167
  - Removed `preloadedSkills` option from `CreateAgentSessionOptions`; skills are no longer inlined into system prompts
@@ -125,11 +195,13 @@
125
195
  - Fixed handling of union type schemas (e.g., object|null) to normalize them into strict-mode compatible variants
126
196
 
127
197
  ## [13.3.6] - 2026-02-26
198
+
128
199
  ### Breaking Changes
129
200
 
130
201
  - Changed `submit_result` tool parameter structure from top-level `data` or `error` fields to nested `result` object containing either `result.data` or `result.error`
131
202
 
132
203
  ## [13.3.5] - 2026-02-26
204
+
133
205
  ### Added
134
206
 
135
207
  - Added support for setting array and record configuration values using JSON syntax
@@ -144,6 +216,7 @@
144
216
  - Enhanced type display in config list output to show correct type indicators for number, array, and record settings
145
217
 
146
218
  ## [13.3.3] - 2026-02-26
219
+
147
220
  ### Added
148
221
 
149
222
  - Support for `move` parameter in `computeHashlineDiff` to enable file move operations alongside content edits
@@ -195,13 +268,16 @@
195
268
  ## [13.2.1] - 2026-02-24
196
269
 
197
270
  ### Fixed
271
+
198
272
  - Fixed changelog tools to enforce category-specific arrays and reuse the shared category list for generation
199
273
  - Non-interactive environment variables (pager, editor, prompt suppression) were not applied to non-PTY bash execution, causing commands to potentially block on pagers or prompts
200
274
 
201
275
  ### Changed
202
276
 
203
277
  - Extracted non-interactive environment config from `bash-interactive.ts` into shared `non-interactive-env.ts` module, applied consistently to all bash execution paths
278
+
204
279
  ## [13.2.0] - 2026-02-23
280
+
205
281
  ### Breaking Changes
206
282
 
207
283
  - Made `description` field required in CustomTool interface
@@ -225,19 +301,24 @@
225
301
  ## [13.1.2] - 2026-02-23
226
302
 
227
303
  ### Breaking Changes
304
+
228
305
  - Removed `timeout` parameter from await tool—tool now waits indefinitely until jobs complete or the call is aborted
229
306
  - Renamed `job_ids` parameter to `jobs` in await tool schema
230
307
  - Removed `timedOut` field from await tool result details
231
308
 
232
309
  ### Changed
310
+
233
311
  - Resolved docs index generation paths using path.resolve relative to the script directory
312
+
234
313
  ## [13.1.1] - 2026-02-23
235
314
 
236
315
  ### Fixed
237
316
 
238
317
  - Fixed bash internal URL expansion to resolve `local://` targets to concrete filesystem paths, including newly created destination files for commands like `mv src.json local://dest.json`
239
318
  - Fixed bash local URL resolution to create missing parent directories under the session local root before command execution, preventing `mv` destination failures for new paths
319
+
240
320
  ## [13.1.0] - 2026-02-23
321
+
241
322
  ### Breaking Changes
242
323
 
243
324
  - Renamed `file` parameter to `path` in replace, patch, and hashline edit operations
@@ -254,6 +335,7 @@
254
335
  - Moved intent field documentation from per-tool JSON schema descriptions into a single system prompt block, reducing token overhead proportional to tool count
255
336
 
256
337
  ## [13.0.1] - 2026-02-22
338
+
257
339
  ### Changed
258
340
 
259
341
  - Simplified hashline edit schema to use unified `first`/`last` anchor fields instead of operation-specific field names (`tag`, `before`, `after`)
@@ -261,6 +343,7 @@
261
343
  - Updated hashline tool documentation to reflect new unified anchor syntax across all operations (replace, append, prepend, insert)
262
344
 
263
345
  ## [13.0.0] - 2026-02-22
346
+
264
347
  ### Added
265
348
 
266
349
  - Added `getTodoPhases()` and `setTodoPhases()` methods to ToolSession API for managing todo state programmatically
@@ -301,6 +384,7 @@
301
384
  - Fixed todo reminder XML tags from underscore to kebab-case format (`system-reminder`)
302
385
 
303
386
  ## [12.19.3] - 2026-02-22
387
+
304
388
  ### Added
305
389
 
306
390
  - Added `pty` parameter to bash tool to enable PTY mode for commands requiring a real terminal (e.g., sudo, ssh, top, less)
@@ -314,12 +398,14 @@
314
398
  - Removed `bash.virtualTerminal` setting; use the `pty` parameter on individual bash commands instead
315
399
 
316
400
  ## [12.19.1] - 2026-02-22
401
+
317
402
  ### Removed
318
403
 
319
404
  - Removed `replaceText` edit operation from hashline mode (substring-based text replacement)
320
405
  - Removed autocorrect heuristics that attempted to detect and fix line merges and formatting rewrites in hashline edits
321
406
 
322
407
  ## [12.19.0] - 2026-02-22
408
+
323
409
  ### Added
324
410
 
325
411
  - Added `poll_jobs` tool to block until background jobs complete, providing an alternative to polling `read jobs://` in loops
@@ -367,6 +453,7 @@
367
453
  - Fixed `submit_result` schema generation to use valid JSON Schema when no explicit output schema is provided
368
454
 
369
455
  ## [12.18.1] - 2026-02-21
456
+
370
457
  ### Added
371
458
 
372
459
  - Added Buffer.toBase64() polyfill for Bun compatibility to enable base64 encoding of buffers
@@ -395,6 +482,7 @@
395
482
  - Fixed potential race condition in bash interactive component where output could be appended after the component was closed
396
483
 
397
484
  ## [12.17.2] - 2026-02-21
485
+
398
486
  ### Changed
399
487
 
400
488
  - Modified bash command normalization to only apply explicit head/tail parameters from tool input, removing automatic extraction from command pipes
@@ -406,6 +494,7 @@
406
494
  - Fixed hard timeout handling to properly interrupt long-running commands that exceed the grace period beyond the configured timeout
407
495
 
408
496
  ## [12.17.1] - 2026-02-21
497
+
409
498
  ### Added
410
499
 
411
500
  - Added `filterBrowser` option to filter out browser automation MCP servers when builtin browser tool is enabled
@@ -414,6 +503,7 @@
414
503
  - Added `BrowserFilterResult` type for browser MCP server filtering results
415
504
 
416
505
  ## [12.17.0] - 2026-02-21
506
+
417
507
  ### Added
418
508
 
419
509
  - Added timeout protection (5 seconds) for system prompt preparation with graceful fallback to minimal context on timeout
@@ -45,7 +45,9 @@ import {
45
45
  ModelRegistry,
46
46
  SessionManager,
47
47
  BUILTIN_TOOLS,
48
+ HIDDEN_TOOLS,
48
49
  createTools,
50
+ ResolveTool,
49
51
  } from "@oh-my-pi/pi-coding-agent";
50
52
 
51
53
  // Auth and models setup
@@ -104,6 +106,26 @@ session.subscribe((event) => {
104
106
  await session.prompt("Hello");
105
107
  ```
106
108
 
109
+ ## Resolve preview workflow (AST edit apply/discard)
110
+
111
+ `ast_edit` now always returns a preview. To finalize, call hidden `resolve` with a required reason.
112
+
113
+ - `action: "apply"` → commit pending preview changes
114
+ - `action: "discard"` → drop pending preview changes
115
+ - `reason: string` is required for both paths
116
+
117
+ `createAgentSession()` / `createTools()` include `resolve` automatically, even when filtering `toolNames`.
118
+ If you are composing tools manually, use `HIDDEN_TOOLS.resolve` (or `ResolveTool`) and wire the same `pendingActionStore`.
119
+
120
+ ```typescript
121
+ const tools = await createTools(toolSession, ["ast_edit"]); // resolve is auto-included
122
+ const resolveTool = tools.find(t => t.name === "resolve") as ResolveTool;
123
+
124
+ await resolveTool.execute("call-1", {
125
+ action: "apply",
126
+ reason: "Preview matches expected replacements",
127
+ });
128
+ ```
107
129
  ## Options
108
130
 
109
131
  | Option | Default | Description |
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "type": "module",
3
3
  "name": "@oh-my-pi/pi-coding-agent",
4
- "version": "13.3.13",
4
+ "version": "13.4.0",
5
5
  "description": "Coding agent CLI with read, bash, edit, write tools and session management",
6
6
  "homepage": "https://github.com/can1357/oh-my-pi",
7
7
  "author": "Can Boluk",
@@ -41,12 +41,12 @@
41
41
  },
42
42
  "dependencies": {
43
43
  "@mozilla/readability": "^0.6",
44
- "@oh-my-pi/omp-stats": "13.3.13",
45
- "@oh-my-pi/pi-agent-core": "13.3.13",
46
- "@oh-my-pi/pi-ai": "13.3.13",
47
- "@oh-my-pi/pi-natives": "13.3.13",
48
- "@oh-my-pi/pi-tui": "13.3.13",
49
- "@oh-my-pi/pi-utils": "13.3.13",
44
+ "@oh-my-pi/omp-stats": "13.4.0",
45
+ "@oh-my-pi/pi-agent-core": "13.4.0",
46
+ "@oh-my-pi/pi-ai": "13.4.0",
47
+ "@oh-my-pi/pi-natives": "13.4.0",
48
+ "@oh-my-pi/pi-tui": "13.4.0",
49
+ "@oh-my-pi/pi-utils": "13.4.0",
50
50
  "@sinclair/typebox": "^0.34",
51
51
  "@xterm/headless": "^6.0",
52
52
  "ajv": "^8.18",
@@ -419,14 +419,4 @@ export function cacheStats(): { content: number; dir: number } {
419
419
  // Re-exports
420
420
  // =============================================================================
421
421
 
422
- export type {
423
- Capability,
424
- CapabilityInfo,
425
- CapabilityResult,
426
- LoadContext,
427
- LoadOptions,
428
- LoadResult,
429
- Provider,
430
- ProviderInfo,
431
- SourceMeta,
432
- } from "./types";
422
+ export type * from "./types";
@@ -1,4 +1,4 @@
1
- export { generateConventionalAnalysis } from "./conventional";
2
- export { extractScopeCandidates } from "./scope";
3
- export { generateSummary, stripTypePrefix } from "./summary";
4
- export { validateAnalysis, validateScope, validateSummary } from "./validation";
1
+ export * from "./conventional";
2
+ export * from "./scope";
3
+ export * from "./summary";
4
+ export * from "./validation";
@@ -254,15 +254,6 @@ export const SETTINGS_SCHEMA = {
254
254
  submenu: true,
255
255
  },
256
256
  },
257
- normativeRewrite: {
258
- type: "boolean",
259
- default: false,
260
- ui: {
261
- tab: "agent",
262
- label: "Normative rewrite",
263
- description: "Rewrite tool call arguments to normalized format in session history",
264
- },
265
- },
266
257
  repeatToolDescriptions: {
267
258
  type: "boolean",
268
259
  default: false,
@@ -455,18 +446,18 @@ export const SETTINGS_SCHEMA = {
455
446
  submenu: true,
456
447
  },
457
448
  },
458
- "astFind.enabled": {
449
+ "astGrep.enabled": {
459
450
  type: "boolean",
460
451
  default: true,
461
- ui: { tab: "tools", label: "Enable AST Find", description: "Enable the ast_find tool for structural AST search" },
452
+ ui: { tab: "tools", label: "Enable AST Grep", description: "Enable the ast_grep tool for structural AST search" },
462
453
  },
463
- "astReplace.enabled": {
454
+ "astEdit.enabled": {
464
455
  type: "boolean",
465
456
  default: true,
466
457
  ui: {
467
458
  tab: "tools",
468
- label: "Enable AST Replace",
469
- description: "Enable the ast_replace tool for structural AST rewrites",
459
+ label: "Enable AST Edit",
460
+ description: "Enable the ast_edit tool for structural AST rewrites",
470
461
  },
471
462
  },
472
463
  "notebook.enabled": {
@@ -737,7 +728,19 @@ export const SETTINGS_SCHEMA = {
737
728
  // ─────────────────────────────────────────────────────────────────────────
738
729
  "providers.webSearch": {
739
730
  type: "enum",
740
- values: ["auto", "exa", "brave", "jina", "kimi", "zai", "perplexity", "anthropic"] as const,
731
+ values: [
732
+ "auto",
733
+ "exa",
734
+ "brave",
735
+ "jina",
736
+ "kimi",
737
+ "zai",
738
+ "perplexity",
739
+ "anthropic",
740
+ "gemini",
741
+ "codex",
742
+ "synthetic",
743
+ ] as const,
741
744
  default: "auto",
742
745
  ui: { tab: "services", label: "Web search provider", description: "Provider for web search tool", submenu: true },
743
746
  },
@@ -41,26 +41,8 @@ import {
41
41
  } from "./settings-schema";
42
42
 
43
43
  // Re-export types that callers need
44
- export type {
45
- BashInterceptorRule,
46
- BranchSummarySettings,
47
- CommitSettings,
48
- CompactionSettings,
49
- ContextPromotionSettings,
50
- ExaSettings,
51
- GroupPrefix,
52
- GroupTypeMap,
53
- MemoriesSettings,
54
- RetrySettings,
55
- SettingPath,
56
- SettingValue,
57
- SkillsSettings,
58
- StatusLineSettings,
59
- ThinkingBudgetsSettings,
60
- TodoCompletionSettings,
61
- TtsrSettings,
62
- } from "./settings-schema";
63
- export { getDefault, getEnumValues, getPathsForTab, getType, getUi, hasUi } from "./settings-schema";
44
+ export type * from "./settings-schema";
45
+ export * from "./settings-schema";
64
46
 
65
47
  // ═══════════════════════════════════════════════════════════════════════════
66
48
  // Types
@@ -76,14 +76,4 @@ export type { SSHHost } from "../capability/ssh";
76
76
  export type { SystemPrompt } from "../capability/system-prompt";
77
77
  export type { CustomTool } from "../capability/tool";
78
78
  // Re-export types
79
- export type {
80
- Capability,
81
- CapabilityInfo,
82
- CapabilityResult,
83
- LoadContext,
84
- LoadOptions,
85
- LoadResult,
86
- Provider,
87
- ProviderInfo,
88
- SourceMeta,
89
- } from "../capability/types";
79
+ export type * from "../capability/types";
package/src/exa/index.ts CHANGED
@@ -27,16 +27,7 @@ export const exaTools: CustomTool<any, ExaRenderDetails>[] = [
27
27
 
28
28
  export { companyTool } from "./company";
29
29
  export { linkedinTool } from "./linkedin";
30
- export {
31
- callExaTool,
32
- callWebsetsTool,
33
- createMCPToolFromServer,
34
- fetchMCPToolSchema,
35
- findApiKey,
36
- formatSearchResults,
37
- isSearchResponse,
38
- MCPWrappedTool,
39
- } from "./mcp-client";
30
+ export * from "./mcp-client";
40
31
  export { renderExaCall, renderExaResult } from "./render";
41
32
  export { researcherTools } from "./researcher";
42
33
  // Re-export individual modules for selective importing
@@ -1,15 +1,2 @@
1
- export {
2
- type DiscoverCustomCommandsOptions,
3
- type DiscoverCustomCommandsResult,
4
- discoverCustomCommands,
5
- type LoadCustomCommandsOptions,
6
- loadCustomCommands,
7
- } from "./loader";
8
- export type {
9
- CustomCommand,
10
- CustomCommandAPI,
11
- CustomCommandFactory,
12
- CustomCommandSource,
13
- CustomCommandsLoadResult,
14
- LoadedCustomCommand,
15
- } from "./types";
1
+ export * from "./loader";
2
+ export type * from "./types";
@@ -2,21 +2,6 @@
2
2
  * Custom tools module.
3
3
  */
4
4
 
5
- export { CustomToolLoader, discoverAndLoadCustomTools, loadCustomTools } from "./loader";
6
- export type {
7
- AgentToolResult,
8
- AgentToolUpdateCallback,
9
- CustomTool,
10
- CustomToolAPI,
11
- CustomToolContext,
12
- CustomToolFactory,
13
- CustomToolResult,
14
- CustomToolSessionEvent,
15
- CustomToolsLoadResult,
16
- CustomToolUIContext,
17
- ExecResult,
18
- LoadedCustomTool,
19
- RenderResultOptions,
20
- ToolLoadError,
21
- } from "./types";
22
- export { CustomToolAdapter } from "./wrapper";
5
+ export * from "./loader";
6
+ export type * from "./types";
7
+ export * from "./wrapper";
@@ -14,6 +14,7 @@ import type { ExecOptions } from "../../exec/exec";
14
14
  import { execCommand } from "../../exec/exec";
15
15
  import type { HookUIContext } from "../../extensibility/hooks/types";
16
16
  import { getAllPluginToolPaths } from "../../extensibility/plugins/loader";
17
+ import type { PendingActionStore } from "../../tools/pending-action";
17
18
  import { createNoOpUIContext, resolvePath } from "../utils";
18
19
  import type { CustomToolAPI, CustomToolFactory, LoadedCustomTool, ToolLoadError } from "./types";
19
20
 
@@ -84,7 +85,7 @@ export class CustomToolLoader {
84
85
  #sharedApi: CustomToolAPI;
85
86
  #seenNames: Set<string>;
86
87
 
87
- constructor(cwd: string, builtInToolNames: string[]) {
88
+ constructor(cwd: string, builtInToolNames: string[], pendingActionStore?: PendingActionStore) {
88
89
  this.#sharedApi = {
89
90
  cwd,
90
91
  exec: (command: string, args: string[], options?: ExecOptions) =>
@@ -94,6 +95,18 @@ export class CustomToolLoader {
94
95
  logger,
95
96
  typebox,
96
97
  pi: piCodingAgent,
98
+ pushPendingAction: action => {
99
+ if (!pendingActionStore) {
100
+ throw new Error("Pending action store unavailable for custom tools in this runtime.");
101
+ }
102
+ pendingActionStore.push({
103
+ label: action.label,
104
+ sourceToolName: action.sourceToolName ?? "custom_tool",
105
+ apply: action.apply,
106
+ reject: action.reject,
107
+ details: action.details,
108
+ });
109
+ },
97
110
  };
98
111
  this.#seenNames = new Set<string>(builtInToolNames);
99
112
  }
@@ -138,8 +151,13 @@ export class CustomToolLoader {
138
151
  * @param cwd - Current working directory for resolving relative paths
139
152
  * @param builtInToolNames - Names of built-in tools to check for conflicts
140
153
  */
141
- export async function loadCustomTools(pathsWithSources: ToolPathWithSource[], cwd: string, builtInToolNames: string[]) {
142
- const loader = new CustomToolLoader(cwd, builtInToolNames);
154
+ export async function loadCustomTools(
155
+ pathsWithSources: ToolPathWithSource[],
156
+ cwd: string,
157
+ builtInToolNames: string[],
158
+ pendingActionStore?: PendingActionStore,
159
+ ) {
160
+ const loader = new CustomToolLoader(cwd, builtInToolNames, pendingActionStore);
143
161
  await loader.load(pathsWithSources);
144
162
  return {
145
163
  tools: loader.tools,
@@ -160,7 +178,12 @@ export async function loadCustomTools(pathsWithSources: ToolPathWithSource[], cw
160
178
  * @param cwd - Current working directory
161
179
  * @param builtInToolNames - Names of built-in tools to check for conflicts
162
180
  */
163
- export async function discoverAndLoadCustomTools(configuredPaths: string[], cwd: string, builtInToolNames: string[]) {
181
+ export async function discoverAndLoadCustomTools(
182
+ configuredPaths: string[],
183
+ cwd: string,
184
+ builtInToolNames: string[],
185
+ pendingActionStore?: PendingActionStore,
186
+ ) {
164
187
  const allPathsWithSources: ToolPathWithSource[] = [];
165
188
  const seen = new Set<string>();
166
189
 
@@ -193,5 +216,5 @@ export async function discoverAndLoadCustomTools(configuredPaths: string[], cwd:
193
216
  addPath(resolvePath(configPath, cwd), { provider: "config", providerName: "Config", level: "project" });
194
217
  }
195
218
 
196
- return loadCustomTools(allPathsWithSources, cwd, builtInToolNames);
219
+ return loadCustomTools(allPathsWithSources, cwd, builtInToolNames, pendingActionStore);
197
220
  }
@@ -26,6 +26,20 @@ export type { AgentToolResult, AgentToolUpdateCallback };
26
26
  // Re-export for backward compatibility
27
27
  export type { ExecOptions, ExecResult } from "../../exec/exec";
28
28
 
29
+ /** Pending action entry consumed by the hidden resolve tool */
30
+ export interface CustomToolPendingAction {
31
+ /** Human-readable preview label shown in resolve flow */
32
+ label: string;
33
+ /** Apply callback invoked when resolve(action="apply") is called */
34
+ apply(reason: string): Promise<AgentToolResult<unknown>>;
35
+ /** Optional reject callback invoked when resolve(action="discard") is called */
36
+ reject?(reason: string): Promise<AgentToolResult<unknown> | undefined>;
37
+ /** Optional details metadata stored with the pending action */
38
+ details?: unknown;
39
+ /** Optional source tool name shown by resolve renderer (defaults to "custom_tool") */
40
+ sourceToolName?: string;
41
+ }
42
+
29
43
  /** API passed to custom tool factory (stable across session changes) */
30
44
  export interface CustomToolAPI {
31
45
  /** Current working directory */
@@ -42,6 +56,8 @@ export interface CustomToolAPI {
42
56
  typebox: typeof import("@sinclair/typebox");
43
57
  /** Injected pi-coding-agent exports */
44
58
  pi: typeof import("../..");
59
+ /** Push a preview action that can later be resolved with the hidden resolve tool */
60
+ pushPendingAction(action: CustomToolPendingAction): void;
45
61
  }
46
62
 
47
63
  /**
@@ -162,7 +178,8 @@ export interface CustomTool<TParams extends TSchema = TSchema, TDetails = any> {
162
178
  parameters: TParams;
163
179
  /** If true, tool is excluded unless explicitly listed in --tools or agent's tools field */
164
180
  hidden?: boolean;
165
-
181
+ /** If true, tool may stage deferred changes that require explicit resolve/discard. */
182
+ deferrable?: boolean;
166
183
  /**
167
184
  * Execute the tool.
168
185
  * @param toolCallId - Unique ID for this tool call