wave-agent-sdk 0.17.8 → 0.17.10

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 (76) hide show
  1. package/builtin/skills/settings/ENV.md +1 -1
  2. package/dist/agent.d.ts +5 -0
  3. package/dist/agent.d.ts.map +1 -1
  4. package/dist/agent.js +7 -0
  5. package/dist/managers/aiManager.d.ts +10 -4
  6. package/dist/managers/aiManager.d.ts.map +1 -1
  7. package/dist/managers/aiManager.js +214 -200
  8. package/dist/managers/backgroundTaskManager.js +1 -1
  9. package/dist/managers/bangManager.js +1 -1
  10. package/dist/managers/hookManager.js +2 -4
  11. package/dist/managers/mcpManager.d.ts.map +1 -1
  12. package/dist/managers/mcpManager.js +1 -3
  13. package/dist/managers/messageManager.d.ts.map +1 -1
  14. package/dist/managers/messageManager.js +1 -8
  15. package/dist/managers/toolManager.d.ts +13 -0
  16. package/dist/managers/toolManager.d.ts.map +1 -1
  17. package/dist/managers/toolManager.js +33 -12
  18. package/dist/services/aiService.d.ts.map +1 -1
  19. package/dist/services/aiService.js +20 -12
  20. package/dist/services/configurationService.d.ts.map +1 -1
  21. package/dist/services/configurationService.js +13 -0
  22. package/dist/services/jsonlHandler.d.ts +1 -1
  23. package/dist/services/jsonlHandler.d.ts.map +1 -1
  24. package/dist/services/jsonlHandler.js +7 -22
  25. package/dist/services/session.d.ts +2 -9
  26. package/dist/services/session.d.ts.map +1 -1
  27. package/dist/services/session.js +16 -46
  28. package/dist/tools/bashTool.d.ts.map +1 -1
  29. package/dist/tools/bashTool.js +3 -1
  30. package/dist/tools/editTool.d.ts.map +1 -1
  31. package/dist/tools/editTool.js +28 -1
  32. package/dist/tools/enterPlanMode.d.ts.map +1 -1
  33. package/dist/tools/enterPlanMode.js +14 -4
  34. package/dist/tools/exitPlanMode.d.ts.map +1 -1
  35. package/dist/tools/exitPlanMode.js +8 -0
  36. package/dist/tools/readTool.d.ts.map +1 -1
  37. package/dist/tools/readTool.js +18 -10
  38. package/dist/tools/types.d.ts +8 -2
  39. package/dist/tools/types.d.ts.map +1 -1
  40. package/dist/tools/writeTool.d.ts.map +1 -1
  41. package/dist/tools/writeTool.js +14 -1
  42. package/dist/types/agent.d.ts +0 -2
  43. package/dist/types/agent.d.ts.map +1 -1
  44. package/dist/types/config.d.ts +1 -0
  45. package/dist/types/config.d.ts.map +1 -1
  46. package/dist/utils/cacheControlUtils.d.ts +20 -15
  47. package/dist/utils/cacheControlUtils.d.ts.map +1 -1
  48. package/dist/utils/cacheControlUtils.js +69 -66
  49. package/dist/utils/constants.d.ts +1 -1
  50. package/dist/utils/constants.js +1 -1
  51. package/dist/utils/containerSetup.js +5 -6
  52. package/package.json +1 -1
  53. package/src/agent.ts +8 -0
  54. package/src/managers/aiManager.ts +292 -263
  55. package/src/managers/backgroundTaskManager.ts +1 -1
  56. package/src/managers/bangManager.ts +1 -1
  57. package/src/managers/hookManager.ts +6 -6
  58. package/src/managers/mcpManager.ts +2 -4
  59. package/src/managers/messageManager.ts +1 -9
  60. package/src/managers/toolManager.ts +37 -12
  61. package/src/services/aiService.ts +23 -12
  62. package/src/services/configurationService.ts +21 -0
  63. package/src/services/jsonlHandler.ts +7 -27
  64. package/src/services/session.ts +16 -57
  65. package/src/tools/bashTool.ts +3 -1
  66. package/src/tools/editTool.ts +31 -1
  67. package/src/tools/enterPlanMode.ts +15 -4
  68. package/src/tools/exitPlanMode.ts +10 -0
  69. package/src/tools/readTool.ts +20 -10
  70. package/src/tools/types.ts +15 -3
  71. package/src/tools/writeTool.ts +15 -1
  72. package/src/types/agent.ts +0 -2
  73. package/src/types/config.ts +1 -0
  74. package/src/utils/cacheControlUtils.ts +77 -95
  75. package/src/utils/constants.ts +1 -1
  76. package/src/utils/containerSetup.ts +7 -7
@@ -27,7 +27,7 @@ Wave uses several environment variables to control its core functionality.
27
27
  | `WAVE_CUSTOM_HEADERS` | Custom HTTP headers for the AI gateway. Newline-separated `Key: Value` pairs (e.g., `"X-Foo: bar\nAuthorization: Bearer xxx"`). | - |
28
28
  | `WAVE_MODEL` | The primary AI model to use for the agent. | `gemini-3-flash` |
29
29
  | `WAVE_FAST_MODEL` | The fast AI model to use for quick tasks. | `gemini-2.5-flash` |
30
- | `WAVE_MAX_INPUT_TOKENS` | Maximum number of input tokens allowed. | `128000` |
30
+ | `WAVE_MAX_INPUT_TOKENS` | Maximum number of input tokens allowed. | `200000` |
31
31
  | `WAVE_MAX_OUTPUT_TOKENS` | Maximum number of output tokens allowed. | `16384` |
32
32
  | `WAVE_DISABLE_AUTO_MEMORY` | Set to `1` or `true` to disable the auto-memory feature. | `false` |
33
33
  | `WAVE_AUTO_MEMORY_FREQUENCY` | Auto memory update frequency. `1` = every turn, `2` = every 2 turns, etc. | `1` |
package/dist/agent.d.ts CHANGED
@@ -316,6 +316,11 @@ export declare class Agent {
316
316
  * Get the current permission mode
317
317
  */
318
318
  getPermissionMode(): PermissionMode;
319
+ /**
320
+ * Get the names of tools currently visible to the AI model (filtered by
321
+ * permission mode, denied rules, etc.)
322
+ */
323
+ getAvailableToolNames(): string[];
319
324
  /**
320
325
  * Set the permission mode
321
326
  * @param mode - The new permission mode
@@ -1 +1 @@
1
- {"version":3,"file":"agent.d.ts","sourceRoot":"","sources":["../src/agent.ts"],"names":[],"mappings":"AAaA,OAAO,EAAgB,KAAK,aAAa,EAAE,MAAM,4BAA4B,CAAC;AAO9E,OAAO,EACL,YAAY,EACZ,kBAAkB,EAElB,YAAY,EACb,MAAM,kBAAkB,CAAC;AAC1B,OAAO,KAAK,EACV,OAAO,EAEP,eAAe,EACf,aAAa,EACb,WAAW,EACX,KAAK,EACL,cAAc,EACd,cAAc,EACf,MAAM,kBAAkB,CAAC;AAqB1B,qBAAa,KAAK;IAChB,OAAO,CAAC,cAAc,CAAiB;IACvC,OAAO,CAAC,SAAS,CAAY;IAE7B,OAAO,CAAC,WAAW,CAA4B;IAC/C,OAAO,CAAC,qBAAqB,CAAwB;IACrD,OAAO,CAAC,MAAM,CAAC,CAAS;IACxB,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,UAAU,CAAa;IAC/B,OAAO,CAAC,UAAU,CAAc;IAChC,OAAO,CAAC,iBAAiB,CAAoB;IAC7C,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,eAAe,CAAkB;IACzC,OAAO,CAAC,kBAAkB,CAAqB;IAC/C,OAAO,CAAC,mBAAmB,CAAsB;IACjD,OAAO,CAAC,aAAa,CAAgB;IACrC,OAAO,CAAC,YAAY,CAAe;IACnC,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,gBAAgB,CAAmB;IAC3C,OAAO,CAAC,iBAAiB,CAAoB;IAC7C,OAAO,CAAC,YAAY,CAAe;IACnC,OAAO,CAAC,2BAA2B,CAAuB;IAC1D,OAAO,CAAC,iBAAiB,CAAoB;IAC7C,OAAO,CAAC,iBAAiB,CAAoB;IAC7C,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,qBAAqB,CAAwB;IACrD,OAAO,CAAC,SAAS,CAAY;IAC7B,OAAO,CAAC,oBAAoB,CAAuB;IACnD,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,YAAY,CAAC,CAAS;IAC9B,OAAO,CAAC,MAAM,CAAU;IACxB,OAAO,CAAC,gBAAgB,CAAsB;IAG9C,OAAO,CAAC,OAAO,CAAe;IAGvB,gBAAgB,IAAI,aAAa;IAIjC,cAAc,IAAI,WAAW;IAS7B,iBAAiB,IAAI,MAAM;IAI3B,WAAW,IAAI,MAAM,GAAG,SAAS;IAIxC;;;OAGG;IACI,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAKpC;;;OAGG;IACI,mBAAmB,IAAI,MAAM,EAAE;IAItC;;;;;;;;OAQG;IACH,OAAO;IA0HP,IAAW,SAAS,IAAI,MAAM,CAE7B;IAED,IAAW,QAAQ,IAAI,OAAO,EAAE,CAE/B;IAED,IAAW,MAAM,IAAI,KAAK,EAAE,CAE3B;IAED,IAAW,eAAe,IAAI,MAAM,CAEnC;IAED,IAAW,iBAAiB,IAAI,MAAM,CAErC;IAED,4BAA4B;IAC5B,IAAW,gBAAgB,IAAI,MAAM,CAEpC;IAED;;;OAGG;IACI,UAAU,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI;IAMvC,iCAAiC;IACjC,IAAW,aAAa,IAAI,MAAM,CAMjC;IAED,8BAA8B;IAC9B,IAAW,UAAU,IAAI,MAAM,CAM9B;IAED,mEAAmE;IACtD,iBAAiB,IAAI,OAAO,CAAC,MAAM,CAAC;IAIjD,4BAA4B;IAC5B,IAAW,SAAS,IAAI,OAAO,CAE9B;IAED,oCAAoC;IACpC,IAAW,YAAY,IAAI,OAAO,CAEjC;IAED,wCAAwC;IACxC,IAAW,gBAAgB,IAAI,OAAO,CAErC;IAED,0BAA0B;IAC1B,IAAW,cAAc,IAAI,aAAa,EAAE,CAE3C;IAED,6BAA6B;IAC7B,IAAW,UAAU,IAAI,MAAM,CAE9B;IAED,gCAAgC;IAChC,IAAW,YAAY,IAAI,OAAO,CAEjC;IAED;;;;OAIG;IACI,mBAAmB,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO;IAQlD;;;OAGG;IACI,mBAAmB,IAAI,aAAa,GAAG,IAAI;IAQlD;;;;OAIG;IACI,uBAAuB,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;IAQnD;;;;OAIG;IACH,OAAO,CAAC,UAAU;IAgBlB;;OAEG;YACW,oBAAoB;IAelC,uCAAuC;IAChC,wBAAwB,CAC7B,EAAE,EAAE,MAAM,EACV,MAAM,CAAC,EAAE,MAAM,GACd;QACD,MAAM,EAAE,MAAM,CAAC;QACf,MAAM,EAAE,MAAM,CAAC;QACf,MAAM,EAAE,MAAM,CAAC;QACf,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,IAAI,EAAE,MAAM,CAAC;QACb,QAAQ,CAAC,EAAE,MAAM,CAAC;KACnB,GAAG,IAAI;IAIR,iCAAiC;IAC1B,mBAAmB,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;IAI/C,iCAAiC;IAC1B,uBAAuB,CAC5B,EAAE,EAAE,MAAM,EACV,MAAM,CAAC,EAAE,MAAM,GACd;QACD,MAAM,EAAE,MAAM,CAAC;QACf,MAAM,EAAE,MAAM,CAAC;QACf,MAAM,EAAE,MAAM,CAAC;QACf,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,IAAI,EAAE,MAAM,CAAC;QACb,QAAQ,CAAC,EAAE,MAAM,CAAC;KACnB,GAAG,IAAI;IAIR,2BAA2B;IACpB,kBAAkB,CAAC,EAAE,EAAE,MAAM,GAAG,OAAO;IAI9C,4BAA4B;IACf,eAAe,IAAI,OAAO,CACrC,OAAO,qBAAqB,EAAE,WAAW,EAAE,CAC5C;IASD,wCAAwC;IACjC,cAAc,CACnB,KAAK,EAAE,MAAM,GACZ,OAAO,qBAAqB,EAAE,WAAW,GAAG,SAAS;IASxD,0BAA0B;IACnB,eAAe,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI;IAS3C;;;;;;;;OAQG;IACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;OA8BG;WACU,MAAM,CAAC,OAAO,EAAE,YAAY,GAAG,OAAO,CAAC,KAAK,CAAC;IAW1D;;;;;OAKG;IACH,OAAO,CAAC,wBAAwB;IAUhC,wEAAwE;YAC1D,UAAU;IAkDxB;;;OAGG;IACU,cAAc,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAmBtD,cAAc,IAAI,IAAI;IAI7B;;;OAGG;YACW,2BAA2B;IAqBzC,0CAA0C;IAC7B,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAYpC,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC;IAkE3C;;;OAGG;IACU,OAAO,CAAC,kBAAkB,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAUhE;;;OAGG;IACU,OAAO,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAyBtD;;OAEG;IACU,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;IAiBvC;;OAEG;IACU,cAAc,IAAI,OAAO,CAAC,IAAI,CAAC;IAiB5C,kFAAkF;IAC3E,YAAY,IAAI,IAAI;IAa3B,uCAAuC;IAChC,gBAAgB,IAAI,IAAI;IAI/B,wCAAwC;IACjC,iBAAiB,IAAI,IAAI;IAIhC;;OAEG;IACI,sBAAsB,CAAC,IAAI,EAAE,cAAc,GAAG,IAAI;IAIzD;;OAEG;IACI,wBAAwB,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI;IAIjD;;OAEG;IACU,qBAAqB,IAAI,OAAO,CAAC,IAAI,CAAC;IAKnD;;;;OAIG;IACU,yBAAyB,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAiC3E,2CAA2C;IAC9B,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAkErC;;OAEG;IACI,iBAAiB,IAAI,IAAI;IAIhC;;;;OAIG;IACU,MAAM,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAWtD;;;;;;;;;;;;;;;;;;;;;;;;;OAyBG;IACU,WAAW,CACtB,OAAO,EAAE,MAAM,EACf,MAAM,CAAC,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAA;KAAE,CAAC,GACjD,OAAO,CAAC,IAAI,CAAC;IA2ChB,gCAAgC;IACzB,aAAa,IAAI,eAAe,EAAE;IAIzC,yBAAyB;IACZ,gBAAgB,CAAC,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAInE,4BAA4B;IACf,mBAAmB,CAAC,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAMtE,uCAAuC;IAChC,gBAAgB,IAAI,YAAY,EAAE;IAIzC,oCAAoC;IAC7B,eAAe,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO;IAIlD,6BAA6B;IAChB,oBAAoB,IAAI,OAAO,CAAC,IAAI,CAAC;IAQlD,iCAAiC;IAC1B,gBAAgB,CAAC,SAAS,EAAE,MAAM,GAAG,kBAAkB,GAAG,SAAS;IAI1E,8BAA8B;IACvB,iBAAiB,IAAI,kBAAkB,EAAE;IAIhD;;OAEG;IACI,oBAAoB,CAAC,OAAO,EAAE,YAAY,GAAG,IAAI;IAIxD;;OAEG;IACI,iBAAiB,IAAI,cAAc;IAI1C;;;OAGG;IACI,iBAAiB,CAAC,IAAI,EAAE,cAAc,GAAG,IAAI;IASpD;;;OAGG;IACU,eAAe,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAQ1D;;OAEG;IACU,oBAAoB,IAAI,OAAO,CAAC;QAC3C,QAAQ,EAAE,OAAO,EAAE,CAAC;QACpB,UAAU,EAAE,MAAM,EAAE,CAAC;KACtB,CAAC;IAIF;;OAEG;IACI,eAAe,IAAI,MAAM,GAAG,SAAS;IAI5C;;OAEG;IACI,eAAe,IAAI,MAAM,EAAE;IAOlC;;OAEG;IACI,mBAAmB,IAAI,MAAM,EAAE;IAItC;;OAEG;IACU,eAAe,CAC1B,OAAO,EAAE,OAAO,wBAAwB,EAAE,qBAAqB,GAC9D,OAAO,CAAC,OAAO,wBAAwB,EAAE,kBAAkB,CAAC;IAI/D;;;OAGG;IACU,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAI3D;;;;OAIG;IACI,mBAAmB,CACxB,UAAU,EAAE,MAAM,GACjB,OAAO,+BAA+B,EAAE,gBAAgB,GAAG,IAAI;IAIlE;;OAEG;IACH,IAAW,UAAU,IAAI,MAAM,CAE9B;IAED;;OAEG;IACH,IAAW,wBAAwB,IAAI,OAAO,CAO7C;CACF"}
1
+ {"version":3,"file":"agent.d.ts","sourceRoot":"","sources":["../src/agent.ts"],"names":[],"mappings":"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"}
package/dist/agent.js CHANGED
@@ -867,6 +867,13 @@ export class Agent {
867
867
  getPermissionMode() {
868
868
  return this.toolManager.getPermissionMode();
869
869
  }
870
+ /**
871
+ * Get the names of tools currently visible to the AI model (filtered by
872
+ * permission mode, denied rules, etc.)
873
+ */
874
+ getAvailableToolNames() {
875
+ return this.toolManager.getToolsConfig().map((t) => t.function.name);
876
+ }
870
877
  /**
871
878
  * Set the permission mode
872
879
  * @param mode - The new permission mode
@@ -31,6 +31,8 @@ export declare class AIManager {
31
31
  private originalWorkdir;
32
32
  private consecutiveCompactionFailures;
33
33
  private readonly maxTurns?;
34
+ /** Tracks file mtime/hash at read time for staleness detection on Edit/Write */
35
+ private readFileState;
34
36
  /** Override tool_choice for this AI manager (e.g. for structured output) */
35
37
  toolChoiceOverride?: "auto" | "none" | "required" | {
36
38
  type: "function";
@@ -69,11 +71,10 @@ export declare class AIManager {
69
71
  */
70
72
  private getFilteredToolsConfig;
71
73
  /**
72
- * Build plan mode system-reminder messages to inject into the API message stream.
73
- * These are transient messages not stored in the message history.
74
- * This preserves prompt caching by keeping the system prompt constant.
74
+ * Add plan mode reminder as a persistent meta message to the message manager.
75
+ * Called before getMessages() so the stored message is included in the API call.
75
76
  */
76
- private buildPlanModeMessages;
77
+ private maybeAddPlanModeMessage;
77
78
  setIsLoading(isLoading: boolean): void;
78
79
  abortAIMessage(): void;
79
80
  private generateCompactParams;
@@ -108,6 +109,11 @@ export declare class AIManager {
108
109
  * @returns Promise<boolean> - true if should continue conversation, false if should stop
109
110
  */
110
111
  private executeStopHooks;
112
+ /**
113
+ * Execute a single tool call: arg parsing, block emission, PreToolUse hooks,
114
+ * tool execution, PostToolUse hooks, and error handling.
115
+ */
116
+ private executeToolCall;
111
117
  /**
112
118
  * Execute PreToolUse hooks before tool execution
113
119
  * Returns true if hooks allow tool execution, false if blocked
@@ -1 +1 @@
1
- {"version":3,"file":"aiManager.d.ts","sourceRoot":"","sources":["../../src/managers/aiManager.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"aiManager.d.ts","sourceRoot":"","sources":["../../src/managers/aiManager.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EACV,aAAa,EACb,WAAW,EACX,KAAK,EAGN,MAAM,mBAAmB,CAAC;AAiB3B,OAAO,EAAE,SAAS,EAAE,MAAM,uBAAuB,CAAC;AAclD,MAAM,WAAW,kBAAkB;IACjC,uBAAuB,CAAC,EAAE,CAAC,YAAY,EAAE,OAAO,KAAK,IAAI,CAAC;IAC1D,YAAY,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,KAAK,IAAI,CAAC;IACtC,WAAW,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;CACxC;AAED,MAAM,WAAW,gBAAgB;IAC/B,SAAS,CAAC,EAAE,kBAAkB,CAAC;IAC/B,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,uEAAuE;IACvE,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,kDAAkD;IAClD,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,6FAA6F;IAC7F,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,qBAAa,SAAS;IA2BlB,OAAO,CAAC,SAAS;IA1BZ,SAAS,EAAE,OAAO,CAAS;IAClC,OAAO,CAAC,eAAe,CAAgC;IACvD,eAAe,CAAC,EAAE,CAAC,OAAO,EAAE,OAAO,KAAK,IAAI,CAAC;IAC7C,OAAO,CAAC,mBAAmB,CAAgC;IAC3D,OAAO,CAAC,YAAY,CAAC,CAAS;IAC9B,OAAO,CAAC,YAAY,CAAC,CAAS;IAC9B,OAAO,CAAC,MAAM,CAAU;IACxB,OAAO,CAAC,aAAa,CAAC,CAAS;IAC/B,OAAO,CAAC,YAAY,CAAC,CAA2B;IAChD,OAAO,CAAC,eAAe,CAAS;IAChC,OAAO,CAAC,6BAA6B,CAAa;IAClD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAS;IACnC,gFAAgF;IAChF,OAAO,CAAC,aAAa,CAGjB;IACJ,4EAA4E;IACrE,kBAAkB,CAAC,EACtB,MAAM,GACN,MAAM,GACN,UAAU,GACV;QAAE,IAAI,EAAE,UAAU,CAAC;QAAC,QAAQ,EAAE;YAAE,IAAI,EAAE,MAAM,CAAA;SAAE,CAAA;KAAE,CAAC;gBAI3C,SAAS,EAAE,SAAS,EAC5B,OAAO,EAAE,gBAAgB;IAY3B,OAAO,KAAK,WAAW,GAEtB;IAED,OAAO,KAAK,cAAc,GAEzB;IAED,OAAO,KAAK,aAAa,GAIxB;IAED,OAAO,KAAK,WAAW,GAItB;IAED,OAAO,KAAK,qBAAqB,GAEhC;IAED,OAAO,KAAK,WAAW,GAEtB;IAED,OAAO,KAAK,gBAAgB,GAM3B;IAED,OAAO,KAAK,iBAAiB,GAE5B;IAED,OAAO,KAAK,WAAW,GAMtB;IAED,OAAO,KAAK,oBAAoB,GAE/B;IAGM,gBAAgB,IAAI,aAAa;IAIjC,cAAc,IAAI,WAAW;IA6B7B,iBAAiB,IAAI,MAAM;IAI3B,WAAW,IAAI,MAAM,GAAG,SAAS;IAIjC,oBAAoB,IAAI,OAAO;IAI/B,UAAU,IAAI,MAAM;IAIpB,kBAAkB,IAAI,MAAM;IAInC;;;OAGG;IACI,UAAU,CAAC,UAAU,EAAE,MAAM,GAAG,IAAI;IAKpC,cAAc,CAAC,QAAQ,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,IAAI,GAAG,IAAI;IAI/D,OAAO,CAAC,YAAY,CAAkB;IACtC,OAAO,CAAC,SAAS,CAAqB;IAEtC;;OAEG;IACH,OAAO,CAAC,sBAAsB;IAe9B;;;OAGG;IACH,OAAO,CAAC,uBAAuB;IA+CxB,YAAY,CAAC,SAAS,EAAE,OAAO,GAAG,IAAI;IAUtC,cAAc,IAAI,IAAI;IAuB7B,OAAO,CAAC,qBAAqB;YAuBf,6BAA6B;IAsC3C;;;OAGG;IACU,mBAAmB,CAC9B,OAAO,GAAE;QACP,kBAAkB,CAAC,EAAE,MAAM,CAAC;QAC5B,WAAW,CAAC,EAAE,WAAW,CAAC;KACtB,GACL,OAAO,CAAC,IAAI,CAAC;IAuKhB;;;OAGG;YACW,uBAAuB;IAwH9B,eAAe,IAAI,OAAO;IAI1B,eAAe,CAAC,YAAY,EAAE,OAAO,GAAG,IAAI;IAOnD,OAAO,KAAK,eAAe,GAE1B;IAED,OAAO,KAAK,YAAY,GAEvB;IAEY,aAAa,CACxB,OAAO,GAAE;QACP,cAAc,CAAC,EAAE,MAAM,CAAC;QACxB,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,oEAAoE;QACpE,YAAY,CAAC,EAAE,MAAM,EAAE,CAAC;QACxB,SAAS,CAAC,EAAE,MAAM,CAAC;KACf,GACL,OAAO,CAAC,IAAI,CAAC;IAqmBhB;;;;OAIG;YACW,gBAAgB;IAkF9B;;;OAGG;YACW,eAAe;IAoM7B;;;OAGG;YACW,sBAAsB;IAsEpC;;OAEG;YACW,uBAAuB;CA2DtC"}
@@ -3,7 +3,6 @@ import { convertMessagesForAPI } from "../utils/convertMessagesForAPI.js";
3
3
  import { microcompactMessages } from "../utils/microcompact.js";
4
4
  import { parseTaskNotificationXml } from "../utils/notificationXml.js";
5
5
  import { calculateComprehensiveTotalTokens } from "../utils/tokenCalculation.js";
6
- import * as fs from "node:fs/promises";
7
6
  import { existsSync } from "node:fs";
8
7
  import { buildSystemPrompt } from "../prompts/index.js";
9
8
  import { buildPlanModeReminder, buildPlanModeReEntryReminder, buildExitedPlanModeReminder, } from "../prompts/planModeReminders.js";
@@ -19,6 +18,8 @@ export class AIManager {
19
18
  this.abortController = null;
20
19
  this.toolAbortController = null;
21
20
  this.consecutiveCompactionFailures = 0;
21
+ /** Tracks file mtime/hash at read time for staleness detection on Edit/Write */
22
+ this.readFileState = new Map();
22
23
  this.isCompacting = false;
23
24
  this.systemPrompt = options.systemPrompt;
24
25
  this.subagentType = options.subagentType; // Store subagent type
@@ -122,50 +123,47 @@ export class AIManager {
122
123
  });
123
124
  }
124
125
  /**
125
- * Build plan mode system-reminder messages to inject into the API message stream.
126
- * These are transient messages not stored in the message history.
127
- * This preserves prompt caching by keeping the system prompt constant.
126
+ * Add plan mode reminder as a persistent meta message to the message manager.
127
+ * Called before getMessages() so the stored message is included in the API call.
128
128
  */
129
- buildPlanModeMessages(currentMode) {
130
- const messages = [];
129
+ maybeAddPlanModeMessage(currentMode) {
131
130
  if (!this.permissionManager)
132
- return messages;
131
+ return;
133
132
  // Handle exit notification (one-time after leaving plan mode)
134
133
  if (this.permissionManager.getNeedsPlanModeExitAttachment()) {
135
134
  const planFilePath = this.permissionManager.getPlanFilePath();
136
135
  const planExists = planFilePath ? existsSync(planFilePath) : false;
137
- messages.push({
138
- role: "user",
136
+ this.messageManager.addUserMessage({
139
137
  content: buildExitedPlanModeReminder(planFilePath, planExists),
138
+ isMeta: true,
140
139
  });
141
140
  this.permissionManager.setNeedsPlanModeExitAttachment(false);
142
141
  }
143
142
  if (currentMode !== "plan")
144
- return messages;
143
+ return;
145
144
  const planFilePath = this.permissionManager.getPlanFilePath();
146
145
  if (!planFilePath)
147
- return messages;
146
+ return;
148
147
  const planExists = existsSync(planFilePath);
149
148
  // One-time plan entry reminder
150
149
  const planMgr = this.planManager;
151
150
  if (planMgr?.isPlanEntryReminderPending()) {
152
151
  if (this.permissionManager.hasExitedPlanModeInSession() && planExists) {
153
152
  // Re-entry: use small reminder
154
- messages.push({
155
- role: "user",
153
+ this.messageManager.addUserMessage({
156
154
  content: buildPlanModeReEntryReminder(planFilePath),
155
+ isMeta: true,
157
156
  });
158
157
  }
159
158
  else {
160
159
  // First entry: use full reminder
161
- messages.push({
162
- role: "user",
160
+ this.messageManager.addUserMessage({
163
161
  content: buildPlanModeReminder(planFilePath, planExists, !!this.subagentType),
162
+ isMeta: true,
164
163
  });
165
164
  }
166
165
  planMgr.consumePlanEntryReminder();
167
166
  }
168
- return messages;
169
167
  }
170
168
  setIsLoading(isLoading) {
171
169
  this.isLoading = isLoading;
@@ -299,6 +297,18 @@ export class AIManager {
299
297
  const enhancedSummary = await this.buildPostCompactContext(compactResult.content);
300
298
  // 7. Execute message reconstruction
301
299
  this.messageManager.compactMessagesAndUpdateSession(enhancedSummary, compactUsage);
300
+ // Re-add plan mode reminder as persistent meta message after compaction
301
+ const postCompactMode = this.permissionManager?.getCurrentEffectiveMode(this.getModelConfig().permissionMode);
302
+ if (postCompactMode === "plan") {
303
+ const planFilePath = this.permissionManager?.getPlanFilePath();
304
+ if (planFilePath) {
305
+ const planExists = existsSync(planFilePath);
306
+ this.messageManager.addUserMessage({
307
+ content: buildPlanModeReminder(planFilePath, planExists, !!this.subagentType),
308
+ isMeta: true,
309
+ });
310
+ }
311
+ }
302
312
  // 8. Track usage
303
313
  if (compactUsage && this.callbacks?.onUsageAdded) {
304
314
  this.callbacks.onUsageAdded(compactUsage);
@@ -376,22 +386,6 @@ export class AIManager {
376
386
  if (usedTokens >= POST_COMPACT_TOKEN_BUDGET)
377
387
  break;
378
388
  }
379
- // 2. Plan mode context
380
- const currentMode = this.permissionManager?.getCurrentEffectiveMode(this.getModelConfig().permissionMode);
381
- if (currentMode === "plan") {
382
- const planFilePath = this.permissionManager?.getPlanFilePath();
383
- if (planFilePath) {
384
- let planExists = false;
385
- try {
386
- await fs.access(planFilePath);
387
- planExists = true;
388
- }
389
- catch {
390
- // Plan file doesn't exist yet
391
- }
392
- contextParts.push(`\n\n${buildPlanModeReminder(planFilePath, planExists, !!this.subagentType)}`);
393
- }
394
- }
395
389
  // 4. Invoked skills context (with token budget, matching Claude Code)
396
390
  const POST_COMPACT_SKILLS_TOKEN_BUDGET = 25000;
397
391
  const POST_COMPACT_MAX_TOKENS_PER_SKILL = 5000;
@@ -549,6 +543,10 @@ export class AIManager {
549
543
  abortController = this.abortController;
550
544
  toolAbortController = this.toolAbortController;
551
545
  }
546
+ // Get current permission mode
547
+ const currentMode = this.permissionManager?.getCurrentEffectiveMode(this.getModelConfig().permissionMode);
548
+ // Add plan mode reminder as persistent meta message before getting messages
549
+ this.maybeAddPlanModeMessage(currentMode);
552
550
  // Get recent message history with microcompact applied
553
551
  const rawMessages = this.messageManager.getMessages();
554
552
  const microcompactedMessages = microcompactMessages(rawMessages, {
@@ -562,19 +560,11 @@ export class AIManager {
562
560
  // Track if assistant message has been created
563
561
  let assistantMessageCreated = false;
564
562
  logger?.debug("modelConfig in sendAIMessage", this.getModelConfig());
565
- // Get current permission mode and plan file path
566
- const currentMode = this.permissionManager?.getCurrentEffectiveMode(this.getModelConfig().permissionMode);
567
563
  const toolsConfig = this.getFilteredToolsConfig();
568
564
  const toolNames = new Set(toolsConfig.map((t) => t.function.name));
569
565
  const filteredToolPlugins = this.toolManager
570
566
  .getTools()
571
567
  .filter((t) => toolNames.has(t.name));
572
- // Inject plan mode system-reminder messages (not system prompt)
573
- // This preserves prompt caching by keeping the system prompt constant
574
- const planModeMessages = this.buildPlanModeMessages(currentMode);
575
- if (planModeMessages.length > 0) {
576
- recentMessages.push(...planModeMessages);
577
- }
578
568
  let autoMemoryOptions;
579
569
  if (this.getAutoMemoryEnabled()) {
580
570
  const directory = this.memoryService.getAutoMemoryDirectory(this.getWorkdir());
@@ -719,170 +709,34 @@ export class AIManager {
719
709
  }
720
710
  }
721
711
  if (toolCalls.length > 0) {
722
- // Execute all tools in parallel using Promise.all
723
- const toolExecutionPromises = toolCalls.map(async (functionToolCall) => {
724
- const toolId = functionToolCall.id || "";
725
- // Check if already interrupted, skip tool execution if so
726
- if (abortController.signal.aborted ||
727
- toolAbortController.signal.aborted) {
728
- return;
729
- }
730
- const toolName = functionToolCall.function?.name || "";
731
- // Safely parse tool parameters, handle tools without parameters
732
- let toolArgs = {};
733
- let jsonRecovered = false;
734
- const argsString = functionToolCall.function?.arguments?.trim();
735
- if (!argsString || argsString === "") {
736
- // Tool without parameters, use empty object
737
- toolArgs = {};
712
+ // Partition tool calls into batches: consecutive concurrency-safe
713
+ // tools run in parallel, non-safe tools (Edit, Write, MCP) run one
714
+ // at a time to prevent read-modify-write races on the same file.
715
+ const batches = [];
716
+ for (const call of toolCalls) {
717
+ const toolName = call.function?.name || "";
718
+ const safe = this.toolManager.isConcurrencySafe(toolName);
719
+ const lastBatch = batches[batches.length - 1];
720
+ if (lastBatch && lastBatch.safe && safe) {
721
+ lastBatch.calls.push(call);
738
722
  }
739
723
  else {
740
- let recoveredArgs = argsString;
741
- try {
742
- toolArgs = JSON.parse(argsString);
743
- }
744
- catch {
745
- // Attempt to recover truncated JSON (e.g., missing closing braces)
746
- recoveredArgs = recoverTruncatedJson(argsString);
747
- try {
748
- toolArgs = JSON.parse(recoveredArgs);
749
- jsonRecovered = true;
750
- logger.warn(`Recovered truncated JSON for tool "${toolName}"`);
751
- }
752
- catch (parseError) {
753
- let errorMessage = `Failed to parse tool arguments`;
754
- if (result.finish_reason === "length") {
755
- errorMessage +=
756
- " (output truncated, please reduce your output)";
757
- }
758
- logger?.error(errorMessage, parseError);
759
- this.messageManager.updateToolBlock({
760
- id: toolId,
761
- parameters: argsString,
762
- result: errorMessage,
763
- success: false,
764
- error: errorMessage,
765
- stage: "end",
766
- name: toolName,
767
- compactParams: "",
768
- timestamp: Date.now(),
769
- });
770
- return;
771
- }
772
- }
724
+ batches.push({ calls: [call], safe });
773
725
  }
774
- const compactParams = this.generateCompactParams(toolName, toolArgs);
775
- // Emit start stage for non-streaming tool calls
776
- if (!this.stream) {
777
- this.messageManager.updateToolBlock({
778
- id: toolId,
779
- stage: "start",
780
- name: toolName,
781
- compactParams,
782
- parameters: argsString,
783
- });
726
+ }
727
+ // Execute batches sequentially; within a safe batch, tools run in parallel
728
+ for (const batch of batches) {
729
+ if (abortController.signal.aborted ||
730
+ toolAbortController.signal.aborted) {
731
+ break;
784
732
  }
785
- // Emit running stage (tool execution about to start)
786
- this.messageManager.updateToolBlock({
787
- id: toolId,
788
- stage: "running",
789
- name: toolName,
790
- compactParams,
791
- parameters: argsString,
792
- parametersChunk: "",
793
- });
794
- try {
795
- // Execute PreToolUse hooks before tool execution
796
- const shouldExecuteTool = await this.executePreToolUseHooks(toolName, toolArgs, toolId);
797
- // If PreToolUse hooks blocked execution, skip tool execution
798
- if (!shouldExecuteTool) {
799
- logger?.info(`Tool ${toolName} execution blocked by PreToolUse hooks`);
800
- return; // Skip this tool and return from this map function
801
- }
802
- // Create tool execution context
803
- const context = {
804
- abortSignal: toolAbortController.signal,
805
- backgroundTaskManager: this.backgroundTaskManager,
806
- workdir: this.getWorkdir(),
807
- originalWorkdir: this.originalWorkdir,
808
- env: this.container.get("MergedEnv"),
809
- messageId: this.messageManager.getMessages().slice(-1)[0]?.id,
810
- sessionId: this.messageManager.getSessionId(),
811
- toolCallId: toolId,
812
- taskManager: this.taskManager,
813
- onShortResultUpdate: (shortResult) => {
814
- this.messageManager.updateToolBlock({
815
- id: toolId,
816
- shortResult,
817
- stage: "running", // Keep it in running stage while updating shortResult
818
- });
819
- },
820
- onResultUpdate: (result) => {
821
- this.messageManager.updateToolBlock({
822
- id: toolId,
823
- result,
824
- stage: "running", // Keep it in running stage while updating result
825
- });
826
- },
827
- onCwdChange: async (newCwd) => {
828
- const oldCwd = this.getWorkdir();
829
- this.container.register("Workdir", newCwd);
830
- this._onCwdChange?.(newCwd);
831
- if (this.hookManager) {
832
- const sessionId = this.messageManager.getSessionId();
833
- const transcriptPath = this.messageManager.getTranscriptPath();
834
- const env = Object.fromEntries(Object.entries(process.env).filter((e) => e[1] !== undefined));
835
- await this.hookManager.executeCwdChangedHooks(oldCwd, newCwd, sessionId, transcriptPath, env);
836
- }
837
- },
838
- };
839
- // Execute tool
840
- const toolResult = await this.toolManager.execute(functionToolCall.function?.name || "", toolArgs, context);
841
- // Build result content, adding truncation warning if JSON was recovered
842
- let toolResultContent = toolResult.content ||
843
- (toolResult.error ? `Error: ${toolResult.error}` : "");
844
- if (jsonRecovered) {
845
- toolResultContent +=
846
- "\n\nTool arguments were truncated (likely exceeded max output tokens). Please reduce your output or split into multiple tool calls.";
847
- }
848
- // Update message state - tool execution completed
849
- this.messageManager.updateToolBlock({
850
- id: toolId,
851
- parameters: argsString,
852
- result: toolResultContent,
853
- success: toolResult.success,
854
- error: toolResult.error,
855
- stage: "end",
856
- name: toolName,
857
- compactParams,
858
- shortResult: toolResult.shortResult,
859
- isManuallyBackgrounded: toolResult.isManuallyBackgrounded,
860
- startLineNumber: toolResult.startLineNumber,
861
- timestamp: Date.now(),
862
- });
863
- // Execute PostToolUse hooks after successful tool completion
864
- await this.executePostToolUseHooks(toolId, toolName, toolArgs, toolResult);
733
+ if (batch.calls.length === 1) {
734
+ await this.executeToolCall(batch.calls[0], abortController, toolAbortController, result.finish_reason);
865
735
  }
866
- catch (toolError) {
867
- const errorMessage = toolError instanceof Error
868
- ? toolError.message
869
- : String(toolError);
870
- this.messageManager.updateToolBlock({
871
- id: toolId,
872
- parameters: JSON.stringify(toolArgs, null, 2),
873
- result: `Tool execution failed: ${errorMessage}`,
874
- success: false,
875
- error: errorMessage,
876
- stage: "end",
877
- name: toolName,
878
- compactParams,
879
- isManuallyBackgrounded: false,
880
- timestamp: Date.now(),
881
- });
736
+ else {
737
+ await Promise.all(batch.calls.map((call) => this.executeToolCall(call, abortController, toolAbortController, result.finish_reason)));
882
738
  }
883
- });
884
- // Wait for all tools to complete execution in parallel
885
- await Promise.all(toolExecutionPromises);
739
+ }
886
740
  }
887
741
  // Handle token statistics and message compaction
888
742
  await this.handleTokenUsageAndCompaction(result.usage, abortController);
@@ -1172,6 +1026,167 @@ export class AIManager {
1172
1026
  return false;
1173
1027
  }
1174
1028
  }
1029
+ /**
1030
+ * Execute a single tool call: arg parsing, block emission, PreToolUse hooks,
1031
+ * tool execution, PostToolUse hooks, and error handling.
1032
+ */
1033
+ async executeToolCall(functionToolCall, abortController, toolAbortController, finishReason) {
1034
+ const toolId = functionToolCall.id || "";
1035
+ // Check if already interrupted, skip tool execution if so
1036
+ if (abortController.signal.aborted || toolAbortController.signal.aborted) {
1037
+ return;
1038
+ }
1039
+ const toolName = functionToolCall.function?.name || "";
1040
+ // Safely parse tool parameters, handle tools without parameters
1041
+ let toolArgs = {};
1042
+ let jsonRecovered = false;
1043
+ const argsString = functionToolCall.function?.arguments?.trim();
1044
+ if (!argsString || argsString === "") {
1045
+ // Tool without parameters, use empty object
1046
+ toolArgs = {};
1047
+ }
1048
+ else {
1049
+ let recoveredArgs = argsString;
1050
+ try {
1051
+ toolArgs = JSON.parse(argsString);
1052
+ }
1053
+ catch {
1054
+ // Attempt to recover truncated JSON (e.g., missing closing braces)
1055
+ recoveredArgs = recoverTruncatedJson(argsString);
1056
+ try {
1057
+ toolArgs = JSON.parse(recoveredArgs);
1058
+ jsonRecovered = true;
1059
+ logger.warn(`Recovered truncated JSON for tool "${toolName}"`);
1060
+ }
1061
+ catch (parseError) {
1062
+ let errorMessage = `Failed to parse tool arguments`;
1063
+ if (finishReason === "length") {
1064
+ errorMessage += " (output truncated, please reduce your output)";
1065
+ }
1066
+ logger?.error(errorMessage, parseError);
1067
+ this.messageManager.updateToolBlock({
1068
+ id: toolId,
1069
+ parameters: argsString,
1070
+ result: errorMessage,
1071
+ success: false,
1072
+ error: errorMessage,
1073
+ stage: "end",
1074
+ name: toolName,
1075
+ compactParams: "",
1076
+ timestamp: Date.now(),
1077
+ });
1078
+ return;
1079
+ }
1080
+ }
1081
+ }
1082
+ const compactParams = this.generateCompactParams(toolName, toolArgs);
1083
+ // Emit start stage for non-streaming tool calls
1084
+ if (!this.stream) {
1085
+ this.messageManager.updateToolBlock({
1086
+ id: toolId,
1087
+ stage: "start",
1088
+ name: toolName,
1089
+ compactParams,
1090
+ parameters: argsString,
1091
+ });
1092
+ }
1093
+ // Emit running stage (tool execution about to start)
1094
+ this.messageManager.updateToolBlock({
1095
+ id: toolId,
1096
+ stage: "running",
1097
+ name: toolName,
1098
+ compactParams,
1099
+ parameters: argsString,
1100
+ parametersChunk: "",
1101
+ });
1102
+ try {
1103
+ // Execute PreToolUse hooks before tool execution
1104
+ const shouldExecuteTool = await this.executePreToolUseHooks(toolName, toolArgs, toolId);
1105
+ // If PreToolUse hooks blocked execution, skip tool execution
1106
+ if (!shouldExecuteTool) {
1107
+ logger?.info(`Tool ${toolName} execution blocked by PreToolUse hooks`);
1108
+ return;
1109
+ }
1110
+ // Create tool execution context
1111
+ const context = {
1112
+ abortSignal: toolAbortController.signal,
1113
+ backgroundTaskManager: this.backgroundTaskManager,
1114
+ workdir: this.getWorkdir(),
1115
+ originalWorkdir: this.originalWorkdir,
1116
+ messageId: this.messageManager.getMessages().slice(-1)[0]?.id,
1117
+ sessionId: this.messageManager.getSessionId(),
1118
+ toolCallId: toolId,
1119
+ taskManager: this.taskManager,
1120
+ readFileState: this.readFileState,
1121
+ onShortResultUpdate: (shortResult) => {
1122
+ this.messageManager.updateToolBlock({
1123
+ id: toolId,
1124
+ shortResult,
1125
+ stage: "running",
1126
+ });
1127
+ },
1128
+ onResultUpdate: (result) => {
1129
+ this.messageManager.updateToolBlock({
1130
+ id: toolId,
1131
+ result,
1132
+ stage: "running",
1133
+ });
1134
+ },
1135
+ onCwdChange: async (newCwd) => {
1136
+ const oldCwd = this.getWorkdir();
1137
+ this.container.register("Workdir", newCwd);
1138
+ this._onCwdChange?.(newCwd);
1139
+ if (this.hookManager) {
1140
+ const sessionId = this.messageManager.getSessionId();
1141
+ const transcriptPath = this.messageManager.getTranscriptPath();
1142
+ const env = Object.fromEntries(Object.entries(process.env).filter((e) => e[1] !== undefined));
1143
+ await this.hookManager.executeCwdChangedHooks(oldCwd, newCwd, sessionId, transcriptPath, env);
1144
+ }
1145
+ },
1146
+ };
1147
+ // Execute tool
1148
+ const toolResult = await this.toolManager.execute(functionToolCall.function?.name || "", toolArgs, context);
1149
+ // Build result content, adding truncation warning if JSON was recovered
1150
+ let toolResultContent = toolResult.content ||
1151
+ (toolResult.error ? `Error: ${toolResult.error}` : "");
1152
+ if (jsonRecovered) {
1153
+ toolResultContent +=
1154
+ "\n\nTool arguments were truncated (likely exceeded max output tokens). Please reduce your output or split into multiple tool calls.";
1155
+ }
1156
+ // Update message state - tool execution completed
1157
+ this.messageManager.updateToolBlock({
1158
+ id: toolId,
1159
+ parameters: argsString,
1160
+ result: toolResultContent,
1161
+ success: toolResult.success,
1162
+ error: toolResult.error,
1163
+ stage: "end",
1164
+ name: toolName,
1165
+ compactParams,
1166
+ shortResult: toolResult.shortResult,
1167
+ isManuallyBackgrounded: toolResult.isManuallyBackgrounded,
1168
+ startLineNumber: toolResult.startLineNumber,
1169
+ timestamp: Date.now(),
1170
+ });
1171
+ // Execute PostToolUse hooks after successful tool completion
1172
+ await this.executePostToolUseHooks(toolId, toolName, toolArgs, toolResult);
1173
+ }
1174
+ catch (toolError) {
1175
+ const errorMessage = toolError instanceof Error ? toolError.message : String(toolError);
1176
+ this.messageManager.updateToolBlock({
1177
+ id: toolId,
1178
+ parameters: JSON.stringify(toolArgs, null, 2),
1179
+ result: `Tool execution failed: ${errorMessage}`,
1180
+ success: false,
1181
+ error: errorMessage,
1182
+ stage: "end",
1183
+ name: toolName,
1184
+ compactParams,
1185
+ isManuallyBackgrounded: false,
1186
+ timestamp: Date.now(),
1187
+ });
1188
+ }
1189
+ }
1175
1190
  /**
1176
1191
  * Execute PreToolUse hooks before tool execution
1177
1192
  * Returns true if hooks allow tool execution, false if blocked
@@ -1243,8 +1258,7 @@ export class AIManager {
1243
1258
  toolResponse,
1244
1259
  subagentType: this.subagentType, // Include subagent type in hook context
1245
1260
  planFilePath: this.permissionManager?.getPlanFilePath(),
1246
- env: this.container.get("MergedEnv") ||
1247
- process.env,
1261
+ env: Object.fromEntries(Object.entries(process.env).filter((e) => e[1] !== undefined)), // Include environment variables
1248
1262
  };
1249
1263
  const results = await this.hookManager.executeHooks("PostToolUse", context);
1250
1264
  // Process hook results to handle exit codes and update tool results
@@ -39,7 +39,7 @@ export class BackgroundTaskManager {
39
39
  stdio: "pipe",
40
40
  detached: true,
41
41
  cwd: this.workdir,
42
- env: this.container.get("MergedEnv") || {
42
+ env: {
43
43
  ...process.env,
44
44
  },
45
45
  });