dexto 1.5.8 → 1.6.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 (127) hide show
  1. package/README.md +3 -3
  2. package/dist/agents/agent-template.yml +2 -2
  3. package/dist/agents/coding-agent/README.md +10 -10
  4. package/dist/agents/coding-agent/coding-agent.yml +81 -82
  5. package/dist/agents/default-agent.yml +32 -47
  6. package/dist/agents/explore-agent/explore-agent.yml +3 -6
  7. package/dist/agents/image-editor-agent/image-editor-agent.yml +1 -1
  8. package/dist/agents/nano-banana-agent/nano-banana-agent.yml +1 -1
  9. package/dist/agents/podcast-agent/podcast-agent.yml +1 -1
  10. package/dist/agents/product-name-researcher/product-name-researcher.yml +1 -1
  11. package/dist/agents/sora-video-agent/sora-video-agent.yml +4 -6
  12. package/dist/agents/triage-demo/triage-agent.yml +1 -1
  13. package/dist/analytics/events.d.ts +1 -1
  14. package/dist/analytics/events.d.ts.map +1 -1
  15. package/dist/api/mcp/tool-aggregation-handler.d.ts +2 -2
  16. package/dist/api/server-hono.d.ts +2 -2
  17. package/dist/api/server-hono.d.ts.map +1 -1
  18. package/dist/api/server-hono.js +37 -60
  19. package/dist/cli/approval/cli-approval-handler.d.ts +10 -3
  20. package/dist/cli/approval/cli-approval-handler.d.ts.map +1 -1
  21. package/dist/cli/approval/cli-approval-handler.js +1 -1
  22. package/dist/cli/commands/create-app.d.ts +1 -11
  23. package/dist/cli/commands/create-app.d.ts.map +1 -1
  24. package/dist/cli/commands/create-app.js +21 -545
  25. package/dist/cli/commands/create-image.d.ts.map +1 -1
  26. package/dist/cli/commands/create-image.js +54 -53
  27. package/dist/cli/commands/image.d.ts +52 -0
  28. package/dist/cli/commands/image.d.ts.map +1 -0
  29. package/dist/cli/commands/image.js +118 -0
  30. package/dist/cli/commands/index.d.ts +2 -1
  31. package/dist/cli/commands/index.d.ts.map +1 -1
  32. package/dist/cli/commands/index.js +3 -1
  33. package/dist/cli/commands/init-app.d.ts +4 -8
  34. package/dist/cli/commands/init-app.d.ts.map +1 -1
  35. package/dist/cli/commands/init-app.js +37 -161
  36. package/dist/cli/commands/interactive-commands/command-parser.d.ts +2 -0
  37. package/dist/cli/commands/interactive-commands/command-parser.d.ts.map +1 -1
  38. package/dist/cli/commands/interactive-commands/commands.d.ts +1 -1
  39. package/dist/cli/commands/interactive-commands/commands.d.ts.map +1 -1
  40. package/dist/cli/commands/interactive-commands/commands.js +2 -2
  41. package/dist/cli/commands/interactive-commands/general-commands.js +2 -2
  42. package/dist/cli/commands/interactive-commands/prompt-commands.d.ts.map +1 -1
  43. package/dist/cli/commands/interactive-commands/prompt-commands.js +2 -7
  44. package/dist/cli/commands/interactive-commands/session/index.d.ts +2 -1
  45. package/dist/cli/commands/interactive-commands/session/index.d.ts.map +1 -1
  46. package/dist/cli/commands/interactive-commands/session/index.js +2 -1
  47. package/dist/cli/commands/interactive-commands/session/session-commands.d.ts +2 -2
  48. package/dist/cli/commands/interactive-commands/session/session-commands.js +2 -2
  49. package/dist/cli/commands/interactive-commands/system/system-commands.d.ts.map +1 -1
  50. package/dist/cli/commands/interactive-commands/system/system-commands.js +7 -29
  51. package/dist/cli/commands/plugin.d.ts +4 -4
  52. package/dist/cli/commands/sync-agents.d.ts +2 -12
  53. package/dist/cli/commands/sync-agents.d.ts.map +1 -1
  54. package/dist/cli/commands/sync-agents.js +2 -50
  55. package/dist/cli/ink-cli/InkCLIRefactored.d.ts +7 -1
  56. package/dist/cli/ink-cli/InkCLIRefactored.d.ts.map +1 -1
  57. package/dist/cli/ink-cli/InkCLIRefactored.js +6 -6
  58. package/dist/cli/ink-cli/components/ApprovalPrompt.d.ts +2 -2
  59. package/dist/cli/ink-cli/components/ApprovalPrompt.d.ts.map +1 -1
  60. package/dist/cli/ink-cli/components/ApprovalPrompt.js +15 -14
  61. package/dist/cli/ink-cli/components/BackgroundTasksPanel.js +1 -1
  62. package/dist/cli/ink-cli/components/Footer.d.ts.map +1 -1
  63. package/dist/cli/ink-cli/components/Footer.js +1 -2
  64. package/dist/cli/ink-cli/components/StatusBar.d.ts.map +1 -1
  65. package/dist/cli/ink-cli/components/StatusBar.js +10 -6
  66. package/dist/cli/ink-cli/components/TodoPanel.js +1 -1
  67. package/dist/cli/ink-cli/components/chat/styled-boxes/ConfigBox.js +1 -1
  68. package/dist/cli/ink-cli/components/modes/AlternateBufferCLI.d.ts +3 -1
  69. package/dist/cli/ink-cli/components/modes/AlternateBufferCLI.d.ts.map +1 -1
  70. package/dist/cli/ink-cli/components/modes/AlternateBufferCLI.js +2 -2
  71. package/dist/cli/ink-cli/components/modes/StaticCLI.d.ts +3 -1
  72. package/dist/cli/ink-cli/components/modes/StaticCLI.d.ts.map +1 -1
  73. package/dist/cli/ink-cli/components/modes/StaticCLI.js +2 -2
  74. package/dist/cli/ink-cli/components/overlays/ToolBrowser.d.ts +1 -1
  75. package/dist/cli/ink-cli/components/overlays/ToolBrowser.js +8 -8
  76. package/dist/cli/ink-cli/constants/tips.js +1 -1
  77. package/dist/cli/ink-cli/containers/InputContainer.d.ts +4 -0
  78. package/dist/cli/ink-cli/containers/InputContainer.d.ts.map +1 -1
  79. package/dist/cli/ink-cli/containers/InputContainer.js +28 -6
  80. package/dist/cli/ink-cli/containers/OverlayContainer.d.ts +2 -0
  81. package/dist/cli/ink-cli/containers/OverlayContainer.d.ts.map +1 -1
  82. package/dist/cli/ink-cli/containers/OverlayContainer.js +81 -36
  83. package/dist/cli/ink-cli/hooks/useAgentEvents.d.ts.map +1 -1
  84. package/dist/cli/ink-cli/hooks/useAgentEvents.js +15 -16
  85. package/dist/cli/ink-cli/hooks/useTokenCounter.d.ts.map +1 -1
  86. package/dist/cli/ink-cli/hooks/useTokenCounter.js +7 -4
  87. package/dist/cli/ink-cli/services/CommandService.d.ts +1 -1
  88. package/dist/cli/ink-cli/services/CommandService.d.ts.map +1 -1
  89. package/dist/cli/ink-cli/services/CommandService.js +2 -2
  90. package/dist/cli/ink-cli/services/processStream.d.ts +2 -2
  91. package/dist/cli/ink-cli/services/processStream.d.ts.map +1 -1
  92. package/dist/cli/ink-cli/services/processStream.js +12 -13
  93. package/dist/cli/ink-cli/state/types.d.ts +2 -2
  94. package/dist/cli/ink-cli/state/types.d.ts.map +1 -1
  95. package/dist/cli/ink-cli/utils/messageFormatting.d.ts +9 -3
  96. package/dist/cli/ink-cli/utils/messageFormatting.d.ts.map +1 -1
  97. package/dist/cli/ink-cli/utils/messageFormatting.js +42 -155
  98. package/dist/cli/ink-cli/utils/toolUtils.d.ts.map +1 -1
  99. package/dist/cli/ink-cli/utils/toolUtils.js +2 -9
  100. package/dist/cli/utils/config-validation.d.ts +11 -11
  101. package/dist/cli/utils/config-validation.d.ts.map +1 -1
  102. package/dist/cli/utils/config-validation.js +56 -290
  103. package/dist/cli/utils/image-store.d.ts +16 -0
  104. package/dist/cli/utils/image-store.d.ts.map +1 -0
  105. package/dist/cli/utils/image-store.js +289 -0
  106. package/dist/cli/utils/scaffolding-utils.d.ts +5 -0
  107. package/dist/cli/utils/scaffolding-utils.d.ts.map +1 -1
  108. package/dist/cli/utils/scaffolding-utils.js +46 -4
  109. package/dist/cli/utils/template-engine.d.ts +28 -16
  110. package/dist/cli/utils/template-engine.d.ts.map +1 -1
  111. package/dist/cli/utils/template-engine.js +339 -479
  112. package/dist/config/cli-overrides.d.ts +4 -3
  113. package/dist/config/cli-overrides.d.ts.map +1 -1
  114. package/dist/config/cli-overrides.js +7 -9
  115. package/dist/index-main.d.ts +2 -0
  116. package/dist/index-main.d.ts.map +1 -0
  117. package/dist/index-main.js +1554 -0
  118. package/dist/index.js +2 -1589
  119. package/dist/utils/session-logger-factory.d.ts +3 -0
  120. package/dist/utils/session-logger-factory.d.ts.map +1 -0
  121. package/dist/utils/session-logger-factory.js +19 -0
  122. package/dist/webui/assets/{index-Cz2z7NQ8.js → index-DwtueA8l.js} +231 -231
  123. package/dist/webui/index.html +1 -1
  124. package/package.json +10 -7
  125. package/dist/cli/cli-subscriber.d.ts +0 -45
  126. package/dist/cli/cli-subscriber.d.ts.map +0 -1
  127. package/dist/cli/cli-subscriber.js +0 -204
@@ -17,9 +17,10 @@ import { capture } from '../../../analytics/index.js';
17
17
  * Smart container for input area
18
18
  * Manages submission, history, and overlay triggers
19
19
  */
20
- export const InputContainer = forwardRef(function InputContainer({ buffer, input, ui, session, approval, queuedMessages, setInput, setUi, setSession, setMessages, setPendingMessages, setDequeuedBuffer, setQueuedMessages, setApproval, setApprovalQueue, setTodos, agent, inputService, onKeyboardScroll, useStreaming = true, }, ref) {
20
+ export const InputContainer = forwardRef(function InputContainer({ buffer, input, ui, session, initialPrompt, approval, queuedMessages, setInput, setUi, setSession, setMessages, setPendingMessages, setDequeuedBuffer, setQueuedMessages, setApproval, setApprovalQueue, setTodos, agent, inputService, configFilePath, onKeyboardScroll, useStreaming = true, }, ref) {
21
21
  // Track pending session creation to prevent race conditions
22
22
  const sessionCreationPromiseRef = useRef(null);
23
+ const didAutoSubmitInitialPromptRef = useRef(false);
23
24
  // Sound notification service from context
24
25
  const soundService = useSoundService();
25
26
  // Ref to track autoApproveEdits so processStream can read latest value mid-stream
@@ -329,7 +330,7 @@ export const InputContainer = forwardRef(function InputContainer({ buffer, input
329
330
  const { CommandService } = await import('../services/CommandService.js');
330
331
  const commandService = new CommandService();
331
332
  try {
332
- const result = await commandService.executeCommand(parsed.command, parsed.args || [], agent, session.id || undefined);
333
+ const result = await commandService.executeCommand(parsed.command, parsed.args || [], agent, session.id || undefined, configFilePath);
333
334
  if (result.type === 'output' && result.output) {
334
335
  const output = result.output;
335
336
  setMessages((prev) => [
@@ -398,7 +399,7 @@ export const InputContainer = forwardRef(function InputContainer({ buffer, input
398
399
  }, {
399
400
  useStreaming,
400
401
  autoApproveEditsRef,
401
- eventBus: agent.agentEventBus,
402
+ eventBus: agent,
402
403
  setTodos,
403
404
  ...(soundService && { soundService }),
404
405
  });
@@ -473,7 +474,7 @@ export const InputContainer = forwardRef(function InputContainer({ buffer, input
473
474
  let messageText = trimmed;
474
475
  if (ui.planModeActive && !ui.planModeInitialized) {
475
476
  try {
476
- const planSkill = await agent.resolvePrompt('plan', {});
477
+ const planSkill = await agent.resolvePrompt('config:dexto-plan-mode', {});
477
478
  if (planSkill.text) {
478
479
  messageText = `<plan-mode>\n${planSkill.text}\n</plan-mode>\n\n${trimmed}`;
479
480
  // Mark plan mode as initialized after injection
@@ -482,7 +483,7 @@ export const InputContainer = forwardRef(function InputContainer({ buffer, input
482
483
  }
483
484
  catch {
484
485
  // Plan skill not found - continue without injection
485
- // This can happen if the plan-tools plugin is not enabled
486
+ // This can happen if the agent config/image doesn't include `config:dexto-plan-mode`.
486
487
  }
487
488
  }
488
489
  if (pendingImages.length > 0) {
@@ -529,7 +530,7 @@ export const InputContainer = forwardRef(function InputContainer({ buffer, input
529
530
  }, {
530
531
  useStreaming,
531
532
  autoApproveEditsRef,
532
- eventBus: agent.agentEventBus,
533
+ eventBus: agent,
533
534
  setTodos,
534
535
  ...(soundService && { soundService }),
535
536
  });
@@ -579,6 +580,27 @@ export const InputContainer = forwardRef(function InputContainer({ buffer, input
579
580
  useStreaming,
580
581
  soundService,
581
582
  ]);
583
+ useEffect(() => {
584
+ if (!initialPrompt || didAutoSubmitInitialPromptRef.current) {
585
+ return;
586
+ }
587
+ didAutoSubmitInitialPromptRef.current = true;
588
+ handleSubmit(initialPrompt, true).catch((error) => {
589
+ agent.logger.error('InputContainer initial prompt submission failed', {
590
+ error,
591
+ initialPrompt,
592
+ });
593
+ setMessages((prev) => [
594
+ ...prev,
595
+ {
596
+ id: generateMessageId('error'),
597
+ role: 'system',
598
+ content: `Failed to submit initial prompt: ${error instanceof Error ? error.message : String(error)}`,
599
+ timestamp: new Date(),
600
+ },
601
+ ]);
602
+ });
603
+ }, [agent.logger, handleSubmit, initialPrompt, setMessages]);
582
604
  // Determine if input should be active (not blocked by approval/overlay/history search)
583
605
  // Input stays active for filter-type overlays (so user can keep typing to filter)
584
606
  // Disable for approval prompts, overlays with their own text input, and history search mode
@@ -26,6 +26,8 @@ interface OverlayContainerProps {
26
26
  agent: DextoAgent;
27
27
  inputService: InputService;
28
28
  buffer: TextBuffer;
29
+ /** Source agent config file path (if available) */
30
+ configFilePath: string | null;
29
31
  /** Callback to refresh static content (clear terminal and force re-render) */
30
32
  refreshStatic?: () => void;
31
33
  /** Callback to submit a prompt command through the normal streaming flow */
@@ -1 +1 @@
1
- {"version":3,"file":"OverlayContainer.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/containers/OverlayContainer.tsx"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAyE,MAAM,OAAO,CAAC;AAG9F,OAAO,KAAK,EAAE,UAAU,EAAmD,MAAM,aAAa,CAAC;AAC/F,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,qCAAqC,CAAC;AACtE,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,kCAAkC,CAAC;AAE5D,OAAO,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACpF,OAAO,EAGH,KAAK,eAAe,EACvB,MAAM,iCAAiC,CAAC;AAuGzC,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAK3D,MAAM,WAAW,sBAAsB;IACnC,WAAW,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,GAAG,KAAK,OAAO,CAAC;CACrD;AAED,UAAU,qBAAqB;IAC3B,EAAE,EAAE,OAAO,CAAC;IACZ,KAAK,EAAE,UAAU,CAAC;IAClB,OAAO,EAAE,YAAY,CAAC;IACtB,QAAQ,EAAE,eAAe,GAAG,IAAI,CAAC;IACjC,QAAQ,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC;IAC3D,KAAK,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC;IACrD,UAAU,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,YAAY,CAAC,CAAC,CAAC;IAC/D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC7D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC,CAAC;IAC1E,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC;IAC1E,KAAK,EAAE,UAAU,CAAC;IAClB,YAAY,EAAE,YAAY,CAAC;IAC3B,MAAM,EAAE,UAAU,CAAC;IACnB,8EAA8E;IAC9E,aAAa,CAAC,EAAE,MAAM,IAAI,CAAC;IAC3B,4EAA4E;IAC5E,qBAAqB,CAAC,EAAE,CAAC,WAAW,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CAClE;AAED;;;GAGG;AACH,eAAO,MAAM,gBAAgB,sGA07E5B,CAAC"}
1
+ {"version":3,"file":"OverlayContainer.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/containers/OverlayContainer.tsx"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAyE,MAAM,OAAO,CAAC;AAG9F,OAAO,KAAK,EAAE,UAAU,EAAmD,MAAM,aAAa,CAAC;AAC/F,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,qCAAqC,CAAC;AACtE,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,kCAAkC,CAAC;AAE5D,OAAO,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACpF,OAAO,EAGH,KAAK,eAAe,EACvB,MAAM,iCAAiC,CAAC;AAuGzC,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAK3D,MAAM,WAAW,sBAAsB;IACnC,WAAW,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,GAAG,KAAK,OAAO,CAAC;CACrD;AAED,UAAU,qBAAqB;IAC3B,EAAE,EAAE,OAAO,CAAC;IACZ,KAAK,EAAE,UAAU,CAAC;IAClB,OAAO,EAAE,YAAY,CAAC;IACtB,QAAQ,EAAE,eAAe,GAAG,IAAI,CAAC;IACjC,QAAQ,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC;IAC3D,KAAK,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC;IACrD,UAAU,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,YAAY,CAAC,CAAC,CAAC;IAC/D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC7D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC,CAAC;IAC1E,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC;IAC1E,KAAK,EAAE,UAAU,CAAC;IAClB,YAAY,EAAE,YAAY,CAAC;IAC3B,MAAM,EAAE,UAAU,CAAC;IACnB,mDAAmD;IACnD,cAAc,EAAE,MAAM,GAAG,IAAI,CAAC;IAC9B,8EAA8E;IAC9E,aAAa,CAAC,EAAE,MAAM,IAAI,CAAC;IAC3B,4EAA4E;IAC5E,qBAAqB,CAAC,EAAE,CAAC,WAAW,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CAClE;AAED;;;GAGG;AACH,eAAO,MAAM,gBAAgB,sGAi+E5B,CAAC"}
@@ -46,8 +46,7 @@ import { capture } from '../../../analytics/index.js';
46
46
  * Smart container for managing overlays
47
47
  * Handles all modal interactions (selectors, autocomplete, approval)
48
48
  */
49
- export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input, session, approval, setInput, setUi, setSession, setMessages, setApproval, setApprovalQueue, agent, inputService, buffer, refreshStatic, onSubmitPromptCommand, }, ref) {
50
- const eventBus = agent.agentEventBus;
49
+ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input, session, approval, setInput, setUi, setSession, setMessages, setApproval, setApprovalQueue, agent, inputService, buffer, configFilePath, refreshStatic, onSubmitPromptCommand, }, ref) {
51
50
  // Refs to overlay components for input handling
52
51
  const approvalRef = useRef(null);
53
52
  const slashAutocompleteRef = useRef(null);
@@ -81,6 +80,21 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
81
80
  // State for selected plugin (for plugin-actions overlay)
82
81
  const [selectedPlugin, setSelectedPlugin] = useState(null);
83
82
  const marketplaceAddPromptRef = useRef(null);
83
+ const getConfigFilePathOrWarn = useCallback((action) => {
84
+ if (configFilePath) {
85
+ return configFilePath;
86
+ }
87
+ setMessages((prev) => [
88
+ ...prev,
89
+ {
90
+ id: generateMessageId('system'),
91
+ role: 'system',
92
+ content: `⚠️ Cannot ${action}: this agent is not file-backed (no config path).`,
93
+ timestamp: new Date(),
94
+ },
95
+ ]);
96
+ return null;
97
+ }, [configFilePath, setMessages]);
84
98
  // Expose handleInput method via ref - routes to appropriate overlay
85
99
  useImperativeHandle(ref, () => ({
86
100
  handleInput: (inputStr, key) => {
@@ -178,7 +192,7 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
178
192
  }, [setApproval, setApprovalQueue, setUi]);
179
193
  // Handle approval responses
180
194
  const handleApprove = useCallback((options) => {
181
- if (!approval || !eventBus)
195
+ if (!approval)
182
196
  return;
183
197
  // Enable "accept all edits" mode if requested
184
198
  if (options.enableAcceptEditsMode) {
@@ -187,18 +201,14 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
187
201
  // Auto-disable plan mode when plan_create or plan_review is approved
188
202
  // This signals the transition from planning phase to execution phase
189
203
  const toolName = approval.metadata.toolName;
190
- const isPlanTool = toolName === 'plan_create' ||
191
- toolName === 'plan_review' ||
192
- toolName === 'custom--plan_create' ||
193
- toolName === 'custom--plan_review';
194
- if (isPlanTool) {
204
+ if (toolName === 'plan_create' || toolName === 'plan_review') {
195
205
  setUi((prev) => ({
196
206
  ...prev,
197
207
  planModeActive: false,
198
208
  planModeInitialized: false,
199
209
  }));
200
210
  }
201
- eventBus.emit('approval:response', {
211
+ agent.emit('approval:response', {
202
212
  approvalId: approval.approvalId,
203
213
  status: ApprovalStatus.APPROVED,
204
214
  sessionId: approval.sessionId,
@@ -210,15 +220,15 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
210
220
  },
211
221
  });
212
222
  completeApproval();
213
- }, [approval, eventBus, completeApproval, setUi]);
223
+ }, [approval, agent, completeApproval, setUi]);
214
224
  const handleDeny = useCallback((feedback) => {
215
- if (!approval || !eventBus)
225
+ if (!approval)
216
226
  return;
217
227
  // Include user feedback in the denial message if provided
218
228
  const message = feedback
219
229
  ? `User requested changes: ${feedback}`
220
230
  : 'User denied the tool execution';
221
- eventBus.emit('approval:response', {
231
+ agent.emit('approval:response', {
222
232
  approvalId: approval.approvalId,
223
233
  status: ApprovalStatus.DENIED,
224
234
  sessionId: approval.sessionId,
@@ -226,11 +236,11 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
226
236
  message,
227
237
  });
228
238
  completeApproval();
229
- }, [approval, eventBus, completeApproval]);
239
+ }, [approval, agent, completeApproval]);
230
240
  const handleCancelApproval = useCallback(() => {
231
- if (!approval || !eventBus)
241
+ if (!approval)
232
242
  return;
233
- eventBus.emit('approval:response', {
243
+ agent.emit('approval:response', {
234
244
  approvalId: approval.approvalId,
235
245
  status: ApprovalStatus.CANCELLED,
236
246
  sessionId: approval.sessionId,
@@ -238,7 +248,7 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
238
248
  message: 'User cancelled the approval request',
239
249
  });
240
250
  completeApproval();
241
- }, [approval, eventBus, completeApproval]);
251
+ }, [approval, agent, completeApproval]);
242
252
  // Helper: Check if error is due to missing API key
243
253
  const isApiKeyMissingError = (error) => {
244
254
  if (error instanceof DextoValidationError) {
@@ -897,7 +907,7 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
897
907
  timestamp: new Date(),
898
908
  },
899
909
  ]);
900
- }, [setUi, setInput, setMessages, agent, buffer]);
910
+ }, [setUi, setInput, setMessages, agent, buffer, getConfigFilePathOrWarn]);
901
911
  // Handle stream mode selection
902
912
  const handleStreamSelect = useCallback((enabled) => {
903
913
  setUi((prev) => ({ ...prev, activeOverlay: 'none', mcpWizardServerType: null }));
@@ -1000,7 +1010,11 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1000
1010
  // Import persistence utilities
1001
1011
  const { updateMcpServerField } = await import('@dexto/agent-management');
1002
1012
  // Persist to config file AFTER successful enable/disable
1003
- await updateMcpServerField(agent.getAgentFilePath(), server.name, 'enabled', newEnabled);
1013
+ const agentPath = getConfigFilePathOrWarn('persist MCP server settings');
1014
+ if (!agentPath) {
1015
+ return;
1016
+ }
1017
+ await updateMcpServerField(agentPath, server.name, 'enabled', newEnabled);
1004
1018
  setMessages((prev) => [
1005
1019
  ...prev,
1006
1020
  {
@@ -1082,7 +1096,10 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1082
1096
  // Import persistence utilities
1083
1097
  const { removeMcpServerFromConfig } = await import('@dexto/agent-management');
1084
1098
  // Persist to config file using surgical removal
1085
- await removeMcpServerFromConfig(agent.getAgentFilePath(), server.name);
1099
+ const agentPath = getConfigFilePathOrWarn('persist MCP server deletion');
1100
+ if (agentPath) {
1101
+ await removeMcpServerFromConfig(agentPath, server.name);
1102
+ }
1086
1103
  // Also disconnect if connected
1087
1104
  try {
1088
1105
  await agent.removeMcpServer(server.name);
@@ -1325,8 +1342,12 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1325
1342
  ]);
1326
1343
  // Refresh prompts to remove uninstalled plugin skills
1327
1344
  try {
1328
- const newConfig = await reloadAgentConfigFromFile(agent.getAgentFilePath());
1329
- const enrichedConfig = enrichAgentConfig(newConfig, agent.getAgentFilePath());
1345
+ const agentPath = getConfigFilePathOrWarn('refresh prompts after plugin uninstall');
1346
+ if (!agentPath) {
1347
+ return;
1348
+ }
1349
+ const newConfig = await reloadAgentConfigFromFile(agentPath);
1350
+ const enrichedConfig = enrichAgentConfig(newConfig, agentPath);
1330
1351
  await agent.refreshPrompts(enrichedConfig.prompts);
1331
1352
  }
1332
1353
  catch {
@@ -1347,7 +1368,7 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1347
1368
  setSelectedPlugin(null);
1348
1369
  setUi((prev) => ({ ...prev, isProcessing: false }));
1349
1370
  }
1350
- }, [setUi, setMessages, agent]);
1371
+ }, [setUi, setMessages, agent, getConfigFilePathOrWarn]);
1351
1372
  // Handle marketplace browser actions
1352
1373
  const handleMarketplaceBrowserAction = useCallback(async (action) => {
1353
1374
  if (action.type === 'add-marketplace') {
@@ -1367,8 +1388,12 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1367
1388
  // Refresh prompts to include new plugin skills
1368
1389
  try {
1369
1390
  const { reloadAgentConfigFromFile, enrichAgentConfig } = await import('@dexto/agent-management');
1370
- const newConfig = await reloadAgentConfigFromFile(agent.getAgentFilePath());
1371
- const enrichedConfig = enrichAgentConfig(newConfig, agent.getAgentFilePath());
1391
+ const agentPath = getConfigFilePathOrWarn('refresh prompts after plugin install');
1392
+ if (!agentPath) {
1393
+ return;
1394
+ }
1395
+ const newConfig = await reloadAgentConfigFromFile(agentPath);
1396
+ const enrichedConfig = enrichAgentConfig(newConfig, agentPath);
1372
1397
  await agent.refreshPrompts(enrichedConfig.prompts);
1373
1398
  }
1374
1399
  catch (error) {
@@ -1376,7 +1401,7 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1376
1401
  // Log but don't show error to user
1377
1402
  }
1378
1403
  }
1379
- }, [setUi, setMessages, agent]);
1404
+ }, [setUi, setMessages, agent, getConfigFilePathOrWarn]);
1380
1405
  // Handle marketplace add completion
1381
1406
  const handleMarketplaceAddComplete = useCallback((name, pluginCount) => {
1382
1407
  setUi((prev) => ({ ...prev, activeOverlay: 'marketplace-browser' }));
@@ -1591,26 +1616,34 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1591
1616
  await writeFile(filePath, fileContent, 'utf-8');
1592
1617
  // Re-discover commands and refresh with enriched prompts
1593
1618
  const { reloadAgentConfigFromFile, enrichAgentConfig } = await import('@dexto/agent-management');
1594
- const newConfig = await reloadAgentConfigFromFile(agent.getAgentFilePath());
1595
- const enrichedConfig = enrichAgentConfig(newConfig, agent.getAgentFilePath());
1619
+ const agentPath = getConfigFilePathOrWarn('refresh prompts after creating shared prompt');
1620
+ if (!agentPath) {
1621
+ return;
1622
+ }
1623
+ const newConfig = await reloadAgentConfigFromFile(agentPath);
1624
+ const enrichedConfig = enrichAgentConfig(newConfig, agentPath);
1596
1625
  await agent.refreshPrompts(enrichedConfig.prompts);
1597
1626
  }
1598
1627
  else {
1599
1628
  // Create in agent's prompts directory
1600
- const agentDir = dirname(agent.getAgentFilePath());
1629
+ const agentPath = getConfigFilePathOrWarn('create prompt in agent prompts directory');
1630
+ if (!agentPath) {
1631
+ return;
1632
+ }
1633
+ const agentDir = dirname(agentPath);
1601
1634
  const promptsDir = join(agentDir, 'prompts');
1602
1635
  filePath = join(promptsDir, `${data.name}.md`);
1603
1636
  await mkdir(promptsDir, { recursive: true });
1604
1637
  await writeFile(filePath, fileContent, 'utf-8');
1605
1638
  // Add file reference to agent config using surgical helper
1606
1639
  const { addPromptToAgentConfig, reloadAgentConfigFromFile, enrichAgentConfig, } = await import('@dexto/agent-management');
1607
- await addPromptToAgentConfig(agent.getAgentFilePath(), {
1640
+ await addPromptToAgentConfig(agentPath, {
1608
1641
  type: 'file',
1609
1642
  file: `\${{dexto.agent_dir}}/prompts/${data.name}.md`,
1610
1643
  });
1611
1644
  // Reload config from disk, enrich to include discovered commands, then refresh
1612
- const newConfig = await reloadAgentConfigFromFile(agent.getAgentFilePath());
1613
- const enrichedConfig = enrichAgentConfig(newConfig, agent.getAgentFilePath());
1645
+ const newConfig = await reloadAgentConfigFromFile(agentPath);
1646
+ const enrichedConfig = enrichAgentConfig(newConfig, agentPath);
1614
1647
  await agent.refreshPrompts(enrichedConfig.prompts);
1615
1648
  }
1616
1649
  setMessages((prev) => [
@@ -1634,7 +1667,15 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1634
1667
  },
1635
1668
  ]);
1636
1669
  }
1637
- }, [ui.promptAddWizard?.scope, setUi, setInput, setMessages, buffer, agent]);
1670
+ }, [
1671
+ ui.promptAddWizard?.scope,
1672
+ setUi,
1673
+ setInput,
1674
+ setMessages,
1675
+ buffer,
1676
+ agent,
1677
+ getConfigFilePathOrWarn,
1678
+ ]);
1638
1679
  // Handle prompt delete
1639
1680
  const handlePromptDelete = useCallback(async (deletable) => {
1640
1681
  const displayName = deletable.prompt.displayName || deletable.prompt.name;
@@ -1649,10 +1690,14 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1649
1690
  ]);
1650
1691
  try {
1651
1692
  const { deletePromptByMetadata, reloadAgentConfigFromFile, enrichAgentConfig } = await import('@dexto/agent-management');
1693
+ const agentPath = getConfigFilePathOrWarn('delete prompt');
1694
+ if (!agentPath) {
1695
+ return;
1696
+ }
1652
1697
  // Use the higher-level delete function that handles file + config
1653
1698
  // Pass full metadata including originalId for inline prompt deletion
1654
1699
  const promptMetadata = deletable.prompt.metadata;
1655
- const result = await deletePromptByMetadata(agent.getAgentFilePath(), {
1700
+ const result = await deletePromptByMetadata(agentPath, {
1656
1701
  name: deletable.prompt.name,
1657
1702
  metadata: {
1658
1703
  filePath: deletable.filePath,
@@ -1663,8 +1708,8 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1663
1708
  throw new Error(result.error || 'Failed to delete prompt');
1664
1709
  }
1665
1710
  // Reload config from disk, enrich to include discovered commands, then refresh
1666
- const newConfig = await reloadAgentConfigFromFile(agent.getAgentFilePath());
1667
- const enrichedConfig = enrichAgentConfig(newConfig, agent.getAgentFilePath());
1711
+ const newConfig = await reloadAgentConfigFromFile(agentPath);
1712
+ const enrichedConfig = enrichAgentConfig(newConfig, agentPath);
1668
1713
  await agent.refreshPrompts(enrichedConfig.prompts);
1669
1714
  setMessages((prev) => [
1670
1715
  ...prev,
@@ -1698,7 +1743,7 @@ export const OverlayContainer = forwardRef(function OverlayContainer({ ui, input
1698
1743
  activeOverlay: 'prompt-list',
1699
1744
  }));
1700
1745
  }
1701
- }, [setUi, setMessages, agent]);
1746
+ }, [setUi, setMessages, agent, getConfigFilePathOrWarn]);
1702
1747
  // Handle prompt add wizard close
1703
1748
  const handlePromptAddWizardClose = useCallback(() => {
1704
1749
  setUi((prev) => ({
@@ -1 +1 @@
1
- {"version":3,"file":"useAgentEvents.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/hooks/useAgentEvents.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAG/B,OAAO,EAEH,KAAK,UAAU,EACf,KAAK,aAAa,EAErB,MAAM,aAAa,CAAC;AACrB,OAAO,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AACpF,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iCAAiC,CAAC;AAEvE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,qCAAqC,CAAC;AAEtE,UAAU,mBAAmB;IACzB,KAAK,EAAE,UAAU,CAAC;IAClB,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC7D,kBAAkB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IACpE,KAAK,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC;IACrD,UAAU,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,YAAY,CAAC,CAAC,CAAC;IAC/D,QAAQ,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC;IAC3D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC,CAAC;IAC1E,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC;IAC1E,iBAAiB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,aAAa,EAAE,CAAC,CAAC,CAAC;IACzE,8CAA8C;IAC9C,gBAAgB,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,iFAAiF;IACjF,MAAM,EAAE,UAAU,CAAC;CACtB;AAYD;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,EAC3B,KAAK,EACL,WAAW,EACX,kBAAkB,EAClB,KAAK,EACL,UAAU,EACV,QAAQ,EACR,WAAW,EACX,gBAAgB,EAChB,iBAAiB,EACjB,gBAAgB,EAChB,MAAM,GACT,EAAE,mBAAmB,GAAG,IAAI,CAid5B"}
1
+ {"version":3,"file":"useAgentEvents.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/hooks/useAgentEvents.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAG/B,OAAO,EAEH,KAAK,UAAU,EACf,KAAK,aAAa,EAErB,MAAM,aAAa,CAAC;AACrB,OAAO,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AACpF,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iCAAiC,CAAC;AAEvE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,qCAAqC,CAAC;AAEtE,UAAU,mBAAmB;IACzB,KAAK,EAAE,UAAU,CAAC;IAClB,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC7D,kBAAkB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IACpE,KAAK,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC;IACrD,UAAU,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,YAAY,CAAC,CAAC,CAAC;IAC/D,QAAQ,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC;IAC3D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC,CAAC;IAC1E,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC;IAC1E,iBAAiB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,aAAa,EAAE,CAAC,CAAC,CAAC;IACzE,8CAA8C;IAC9C,gBAAgB,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,iFAAiF;IACjF,MAAM,EAAE,UAAU,CAAC;CACtB;AAYD;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,EAC3B,KAAK,EACL,WAAW,EACX,kBAAkB,EAClB,KAAK,EACL,UAAU,EACV,QAAQ,EACR,WAAW,EACX,gBAAgB,EAChB,iBAAiB,EACjB,gBAAgB,EAChB,MAAM,GACT,EAAE,mBAAmB,GAAG,IAAI,CAgd5B"}
@@ -41,7 +41,6 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
41
41
  // Track if an external trigger is active (scheduler, A2A, etc.)
42
42
  const externalTriggerRef = useRef({ active: false, sessionId: null, messageId: null });
43
43
  useEffect(() => {
44
- const bus = agent.agentEventBus;
45
44
  const controller = new AbortController();
46
45
  const { signal } = controller;
47
46
  // Increase listener limit for safety (added more for external trigger events)
@@ -50,7 +49,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
50
49
  // event ordering. Direct bus subscription here caused a race condition where
51
50
  // approval UI showed before text messages were added.
52
51
  // Handle model switch
53
- bus.on('llm:switched', (payload) => {
52
+ agent.on('llm:switched', (payload) => {
54
53
  if (payload.newConfig?.model) {
55
54
  setSession((prev) => ({
56
55
  ...prev,
@@ -58,7 +57,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
58
57
  }));
59
58
  }
60
59
  }, { signal });
61
- bus.on('service:event', (payload) => {
60
+ agent.on('service:event', (payload) => {
62
61
  if (payload.service !== 'orchestration' || payload.event !== 'tasks-updated') {
63
62
  return;
64
63
  }
@@ -85,7 +84,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
85
84
  }));
86
85
  }
87
86
  }, { signal });
88
- bus.on('tool:background', (payload) => {
87
+ agent.on('tool:background', (payload) => {
89
88
  if (payload.sessionId !== currentSessionId) {
90
89
  return;
91
90
  }
@@ -102,7 +101,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
102
101
  };
103
102
  }));
104
103
  }, { signal });
105
- bus.on('tool:background-completed', (payload) => {
104
+ agent.on('tool:background-completed', (payload) => {
106
105
  if (payload.sessionId !== currentSessionId) {
107
106
  return;
108
107
  }
@@ -120,7 +119,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
120
119
  }));
121
120
  }, { signal });
122
121
  // Handle conversation reset
123
- bus.on('session:reset', () => {
122
+ agent.on('session:reset', () => {
124
123
  setMessages([]);
125
124
  setApproval(null);
126
125
  setApprovalQueue([]);
@@ -128,7 +127,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
128
127
  setUi((prev) => ({ ...prev, activeOverlay: 'none' }));
129
128
  }, { signal });
130
129
  // Handle session creation (e.g., from /new command)
131
- bus.on('session:created', (payload) => {
130
+ agent.on('session:created', (payload) => {
132
131
  if (payload.switchTo) {
133
132
  // Clear the terminal screen for a fresh start (only in TTY environments)
134
133
  // \x1B[2J clears visible screen, \x1B[3J clears scrollback, \x1B[H moves cursor to top
@@ -181,7 +180,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
181
180
  // Handle context cleared (from /clear command)
182
181
  // Keep messages visible for user reference - only context sent to LLM is cleared
183
182
  // Just clean up any pending approvals/overlays/queued messages
184
- bus.on('context:cleared', () => {
183
+ agent.on('context:cleared', () => {
185
184
  setApproval(null);
186
185
  setApprovalQueue([]);
187
186
  setQueuedMessages([]);
@@ -189,14 +188,14 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
189
188
  }, { signal });
190
189
  // Handle context compacting (from /compact command or auto-compaction)
191
190
  // Single source of truth - handles both manual /compact and auto-compaction during streaming
192
- bus.on('context:compacting', (payload) => {
191
+ agent.on('context:compacting', (payload) => {
193
192
  if (payload.sessionId !== currentSessionId)
194
193
  return;
195
194
  setUi((prev) => ({ ...prev, isCompacting: true }));
196
195
  }, { signal });
197
196
  // Handle context compacted
198
197
  // Single source of truth - shows notification for all compaction (manual and auto)
199
- bus.on('context:compacted', (payload) => {
198
+ agent.on('context:compacted', (payload) => {
200
199
  if (payload.sessionId !== currentSessionId)
201
200
  return;
202
201
  setUi((prev) => ({ ...prev, isCompacting: false }));
@@ -219,7 +218,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
219
218
  ]);
220
219
  }, { signal });
221
220
  // Handle message queued - fetch full queue state from agent
222
- bus.on('message:queued', (payload) => {
221
+ agent.on('message:queued', (payload) => {
223
222
  if (!payload.sessionId)
224
223
  return;
225
224
  // Fetch fresh queue state from agent to ensure consistency
@@ -233,7 +232,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
233
232
  });
234
233
  }, { signal });
235
234
  // Handle message removed from queue
236
- bus.on('message:removed', (payload) => {
235
+ agent.on('message:removed', (payload) => {
237
236
  setQueuedMessages((prev) => prev.filter((m) => m.id !== payload.id));
238
237
  }, { signal });
239
238
  // Note: message:dequeued is handled in processStream (via iterator) for proper synchronization
@@ -244,7 +243,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
244
243
  // through processStream (which only handles user-initiated streams).
245
244
  // ============================================================================
246
245
  // Handle external trigger invocation (scheduler, A2A, API)
247
- bus.on('run:invoke', (payload) => {
246
+ agent.on('run:invoke', (payload) => {
248
247
  // Only handle if this is for the current session
249
248
  if (payload.sessionId !== currentSessionId) {
250
249
  return;
@@ -299,7 +298,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
299
298
  ]);
300
299
  }, { signal });
301
300
  // Handle streaming chunks for external triggers
302
- bus.on('llm:chunk', (payload) => {
301
+ agent.on('llm:chunk', (payload) => {
303
302
  // Only handle if this is for an active external trigger
304
303
  if (!externalTriggerRef.current.active ||
305
304
  payload.sessionId !== externalTriggerRef.current.sessionId) {
@@ -317,7 +316,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
317
316
  setUi((prev) => (prev.isThinking ? { ...prev, isThinking: false } : prev));
318
317
  }, { signal });
319
318
  // Handle LLM thinking for external triggers
320
- bus.on('llm:thinking', (payload) => {
319
+ agent.on('llm:thinking', (payload) => {
321
320
  if (!externalTriggerRef.current.active ||
322
321
  payload.sessionId !== externalTriggerRef.current.sessionId) {
323
322
  return;
@@ -325,7 +324,7 @@ export function useAgentEvents({ agent, setMessages, setPendingMessages, setUi,
325
324
  setUi((prev) => ({ ...prev, isThinking: true }));
326
325
  }, { signal });
327
326
  // Handle run completion for external triggers
328
- bus.on('run:complete', (payload) => {
327
+ agent.on('run:complete', (payload) => {
329
328
  // Only handle if this is for an active external trigger
330
329
  if (!externalTriggerRef.current.active ||
331
330
  payload.sessionId !== externalTriggerRef.current.sessionId) {
@@ -1 +1 @@
1
- {"version":3,"file":"useTokenCounter.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/hooks/useTokenCounter.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAGH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAE9C,MAAM,WAAW,mBAAmB;IAChC,+CAA+C;IAC/C,KAAK,EAAE,UAAU,CAAC;IAClB,qEAAqE;IACrE,QAAQ,EAAE,OAAO,CAAC;CACrB;AAED,MAAM,WAAW,kBAAkB;IAC/B,yDAAyD;IACzD,iBAAiB,EAAE,MAAM,CAAC;IAC1B,qDAAqD;IACrD,sBAAsB,EAAE,MAAM,CAAC;IAC/B,yDAAyD;IACzD,YAAY,EAAE,MAAM,CAAC;IACrB,yDAAyD;IACzD,gBAAgB,EAAE,OAAO,CAAC;IAC1B,qEAAqE;IACrE,SAAS,EAAE,MAAM,CAAC;CACrB;AAsBD;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,EAAE,mBAAmB,GAAG,kBAAkB,CA0F5F"}
1
+ {"version":3,"file":"useTokenCounter.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/hooks/useTokenCounter.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAGH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAE9C,MAAM,WAAW,mBAAmB;IAChC,+CAA+C;IAC/C,KAAK,EAAE,UAAU,CAAC;IAClB,qEAAqE;IACrE,QAAQ,EAAE,OAAO,CAAC;CACrB;AAED,MAAM,WAAW,kBAAkB;IAC/B,yDAAyD;IACzD,iBAAiB,EAAE,MAAM,CAAC;IAC1B,qDAAqD;IACrD,sBAAsB,EAAE,MAAM,CAAC;IAC/B,yDAAyD;IACzD,YAAY,EAAE,MAAM,CAAC;IACrB,yDAAyD;IACzD,gBAAgB,EAAE,OAAO,CAAC;IAC1B,qEAAqE;IACrE,SAAS,EAAE,MAAM,CAAC;CACrB;AAsBD;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,EAAE,mBAAmB,GAAG,kBAAkB,CA6F5F"}
@@ -61,7 +61,6 @@ export function useTokenCounter({ agent, isActive }) {
61
61
  currentCharCountRef.current = 0;
62
62
  return;
63
63
  }
64
- const bus = agent.agentEventBus;
65
64
  const controller = new AbortController();
66
65
  const { signal } = controller;
67
66
  // Reset on new turn (isActive just became true)
@@ -70,14 +69,18 @@ export function useTokenCounter({ agent, isActive }) {
70
69
  setCumulativeOutputTokens(0);
71
70
  setCurrentSegmentEstimate(0);
72
71
  // Track streaming chunks - accumulate estimate for current segment
73
- bus.on('llm:chunk', (payload) => {
72
+ agent.on('llm:chunk', (payload) => {
74
73
  if (payload.chunkType === 'text') {
75
74
  currentCharCountRef.current += payload.content.length;
76
- setCurrentSegmentEstimate(estimateTokens(currentCharCountRef.current));
75
+ const estimate = estimateTokens(currentCharCountRef.current);
76
+ // Avoid frequent re-renders for short responses where we don't show tokens anyway.
77
+ if (estimate >= 1000) {
78
+ setCurrentSegmentEstimate(estimate);
79
+ }
77
80
  }
78
81
  }, { signal });
79
82
  // On response: update input (replace), accumulate output, reset estimate
80
- bus.on('llm:response', (payload) => {
83
+ agent.on('llm:response', (payload) => {
81
84
  const usage = payload.tokenUsage;
82
85
  if (usage) {
83
86
  // Replace input tokens (most recent call's context)
@@ -53,6 +53,6 @@ export declare class CommandService {
53
53
  /**
54
54
  * Executes a command and returns the result
55
55
  */
56
- executeCommand(command: string, args: string[], agent: DextoAgent, sessionId?: string): Promise<CommandExecutionResult>;
56
+ executeCommand(command: string, args: string[], agent: DextoAgent, sessionId?: string, configFilePath?: string | null): Promise<CommandExecutionResult>;
57
57
  }
58
58
  //# sourceMappingURL=CommandService.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"CommandService.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/services/CommandService.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAG9C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,uDAAuD,CAAC;AAC3F,OAAO,KAAK,EAAE,iBAAiB,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAEvE;;GAEG;AACH,MAAM,WAAW,YAAY;IACzB,UAAU,EAAE,iBAAiB,CAAC;IAC9B,UAAU,EAAE,UAAU,CAAC;IACvB,YAAY,EAAE,MAAM,CAAC;CACxB;AAED;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACnC,IAAI,EAAE,SAAS,GAAG,QAAQ,GAAG,QAAQ,GAAG,aAAa,CAAC;IACtD,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,+EAA+E;IAC/E,aAAa,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,OAAO,GAAG,MAAM,IAAI,YAAY,CAQtE;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAC9B,aAAa,EAAE,IAAI,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,wBAAgB,uBAAuB,CAAC,IAAI,EAAE,MAAM,GAAG,iBAAiB,CAEvE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,GAAG,MAAM,IAAI,iBAAiB,CAShF;AAED;;GAEG;AACH,qBAAa,cAAc;IACvB;;OAEG;IACH,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,aAAa;IAIxC;;OAEG;IACG,cAAc,CAChB,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,MAAM,EAAE,EACd,KAAK,EAAE,UAAU,EACjB,SAAS,CAAC,EAAE,MAAM,GACnB,OAAO,CAAC,sBAAsB,CAAC;CAqBrC"}
1
+ {"version":3,"file":"CommandService.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/services/CommandService.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAG9C,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,uDAAuD,CAAC;AAC3F,OAAO,KAAK,EAAE,iBAAiB,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAEvE;;GAEG;AACH,MAAM,WAAW,YAAY;IACzB,UAAU,EAAE,iBAAiB,CAAC;IAC9B,UAAU,EAAE,UAAU,CAAC;IACvB,YAAY,EAAE,MAAM,CAAC;CACxB;AAED;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACnC,IAAI,EAAE,SAAS,GAAG,QAAQ,GAAG,QAAQ,GAAG,aAAa,CAAC;IACtD,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,YAAY,CAAC;IACtB,+EAA+E;IAC/E,aAAa,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,MAAM,EAAE,OAAO,GAAG,MAAM,IAAI,YAAY,CAQtE;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAC9B,aAAa,EAAE,IAAI,CAAC;IACpB,IAAI,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,wBAAgB,uBAAuB,CAAC,IAAI,EAAE,MAAM,GAAG,iBAAiB,CAEvE;AAED;;GAEG;AACH,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,OAAO,GAAG,MAAM,IAAI,iBAAiB,CAShF;AAED;;GAEG;AACH,qBAAa,cAAc;IACvB;;OAEG;IACH,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,aAAa;IAIxC;;OAEG;IACG,cAAc,CAChB,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,MAAM,EAAE,EACd,KAAK,EAAE,UAAU,EACjB,SAAS,CAAC,EAAE,MAAM,EAClB,cAAc,CAAC,EAAE,MAAM,GAAG,IAAI,GAC/B,OAAO,CAAC,sBAAsB,CAAC;CAqBrC"}
@@ -44,8 +44,8 @@ export class CommandService {
44
44
  /**
45
45
  * Executes a command and returns the result
46
46
  */
47
- async executeCommand(command, args, agent, sessionId) {
48
- const result = await executeCommand(command, args, agent, sessionId);
47
+ async executeCommand(command, args, agent, sessionId, configFilePath) {
48
+ const result = await executeCommand(command, args, agent, sessionId, configFilePath);
49
49
  // If result is a send message marker, return the text to send through normal flow
50
50
  if (isSendMessageMarker(result)) {
51
51
  return { type: 'sendMessage', messageToSend: result.text };
@@ -53,8 +53,8 @@ export interface ProcessStreamOptions {
53
53
  autoApproveEditsRef: {
54
54
  current: boolean;
55
55
  };
56
- /** Event bus for emitting auto-approval responses */
57
- eventBus: import('@dexto/core').AgentEventBus;
56
+ /** Event emitter for emitting auto-approval responses */
57
+ eventBus: Pick<import('@dexto/core').AgentEventBus, 'emit'>;
58
58
  /** Sound notification service for playing sounds on events */
59
59
  soundService?: import('../utils/soundNotification.js').SoundNotificationService;
60
60
  /** Optional setter for todos (from service:event todo updates) */
@@ -1 +1 @@
1
- {"version":3,"file":"processStream.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/services/processStream.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAC/B,OAAO,KAAK,EAAE,cAAc,EAAuB,MAAM,aAAa,CAAC;AAGvE,OAAO,KAAK,EAAE,OAAO,EAAE,OAAO,EAAc,MAAM,mBAAmB,CAAC;AACtE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iCAAiC,CAAC;AAiCvE;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACjC,2DAA2D;IAC3D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC7D,oFAAoF;IACpF,kBAAkB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IACpE,iFAAiF;IACjF,iBAAiB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IACnE,KAAK,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC;IACrD,kEAAkE;IAClE,UAAU,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,mBAAmB,EAAE,YAAY,CAAC,CAAC,CAAC;IAC3F,yDAAyD;IACzD,iBAAiB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,aAAa,EAAE,aAAa,EAAE,CAAC,CAAC,CAAC;IAC/F,4DAA4D;IAC5D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC,CAAC;IAC1E,uDAAuD;IACvD,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC;CAC7E;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACjC,2FAA2F;IAC3F,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,2FAA2F;IAC3F,mBAAmB,EAAE;QAAE,OAAO,EAAE,OAAO,CAAA;KAAE,CAAC;IAC1C,qDAAqD;IACrD,QAAQ,EAAE,OAAO,aAAa,EAAE,aAAa,CAAC;IAC9C,8DAA8D;IAC9D,YAAY,CAAC,EAAE,OAAO,+BAA+B,EAAE,wBAAwB,CAAC;IAChF,kEAAkE;IAClE,QAAQ,CAAC,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,mBAAmB,EAAE,QAAQ,EAAE,CAAC,CAAC,CAAC;CAC3F;AA0BD;;;;;;;;;;GAUG;AACH,wBAAsB,aAAa,CAC/B,QAAQ,EAAE,qBAAqB,CAAC,cAAc,CAAC,EAC/C,OAAO,EAAE,oBAAoB,EAC7B,OAAO,EAAE,oBAAoB,GAC9B,OAAO,CAAC,IAAI,CAAC,CAsgCf"}
1
+ {"version":3,"file":"processStream.d.ts","sourceRoot":"","sources":["../../../../src/cli/ink-cli/services/processStream.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,OAAO,KAAK,KAAK,MAAM,OAAO,CAAC;AAC/B,OAAO,KAAK,EAAE,cAAc,EAAuB,MAAM,aAAa,CAAC;AAGvE,OAAO,KAAK,EAAE,OAAO,EAAE,OAAO,EAAc,MAAM,mBAAmB,CAAC;AACtE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iCAAiC,CAAC;AAwBvE;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACjC,2DAA2D;IAC3D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IAC7D,oFAAoF;IACpF,kBAAkB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IACpE,iFAAiF;IACjF,iBAAiB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC;IACnE,KAAK,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,CAAC,CAAC,CAAC;IACrD,kEAAkE;IAClE,UAAU,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,mBAAmB,EAAE,YAAY,CAAC,CAAC,CAAC;IAC3F,yDAAyD;IACzD,iBAAiB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,aAAa,EAAE,aAAa,EAAE,CAAC,CAAC,CAAC;IAC/F,4DAA4D;IAC5D,WAAW,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,GAAG,IAAI,CAAC,CAAC,CAAC;IAC1E,uDAAuD;IACvD,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,eAAe,EAAE,CAAC,CAAC,CAAC;CAC7E;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACjC,2FAA2F;IAC3F,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,2FAA2F;IAC3F,mBAAmB,EAAE;QAAE,OAAO,EAAE,OAAO,CAAA;KAAE,CAAC;IAC1C,yDAAyD;IACzD,QAAQ,EAAE,IAAI,CAAC,OAAO,aAAa,EAAE,aAAa,EAAE,MAAM,CAAC,CAAC;IAC5D,8DAA8D;IAC9D,YAAY,CAAC,EAAE,OAAO,+BAA+B,EAAE,wBAAwB,CAAC;IAChF,kEAAkE;IAClE,QAAQ,CAAC,EAAE,KAAK,CAAC,QAAQ,CAAC,KAAK,CAAC,cAAc,CAAC,OAAO,mBAAmB,EAAE,QAAQ,EAAE,CAAC,CAAC,CAAC;CAC3F;AA0BD;;;;;;;;;;GAUG;AACH,wBAAsB,aAAa,CAC/B,QAAQ,EAAE,qBAAqB,CAAC,cAAc,CAAC,EAC/C,OAAO,EAAE,oBAAoB,EAC7B,OAAO,EAAE,oBAAoB,GAC9B,OAAO,CAAC,IAAI,CAAC,CAygCf"}