autobyteus 1.2.1__py3-none-any.whl → 1.3.0__py3-none-any.whl

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 (472) hide show
  1. autobyteus/agent/agent.py +15 -5
  2. autobyteus/agent/bootstrap_steps/__init__.py +3 -3
  3. autobyteus/agent/bootstrap_steps/agent_bootstrapper.py +5 -59
  4. autobyteus/agent/bootstrap_steps/base_bootstrap_step.py +1 -4
  5. autobyteus/agent/bootstrap_steps/mcp_server_prewarming_step.py +1 -3
  6. autobyteus/agent/bootstrap_steps/system_prompt_processing_step.py +16 -13
  7. autobyteus/agent/bootstrap_steps/working_context_snapshot_restore_step.py +38 -0
  8. autobyteus/agent/bootstrap_steps/workspace_context_initialization_step.py +2 -4
  9. autobyteus/agent/context/agent_config.py +47 -20
  10. autobyteus/agent/context/agent_context.py +23 -18
  11. autobyteus/agent/context/agent_runtime_state.py +21 -19
  12. autobyteus/agent/events/__init__.py +16 -1
  13. autobyteus/agent/events/agent_events.py +43 -3
  14. autobyteus/agent/events/agent_input_event_queue_manager.py +79 -26
  15. autobyteus/agent/events/event_store.py +57 -0
  16. autobyteus/agent/events/notifiers.py +69 -59
  17. autobyteus/agent/events/worker_event_dispatcher.py +21 -64
  18. autobyteus/agent/factory/agent_factory.py +83 -6
  19. autobyteus/agent/handlers/__init__.py +2 -0
  20. autobyteus/agent/handlers/approved_tool_invocation_event_handler.py +51 -34
  21. autobyteus/agent/handlers/bootstrap_event_handler.py +155 -0
  22. autobyteus/agent/handlers/inter_agent_message_event_handler.py +10 -0
  23. autobyteus/agent/handlers/lifecycle_event_logger.py +19 -11
  24. autobyteus/agent/handlers/llm_complete_response_received_event_handler.py +10 -15
  25. autobyteus/agent/handlers/llm_user_message_ready_event_handler.py +188 -48
  26. autobyteus/agent/handlers/tool_execution_approval_event_handler.py +0 -10
  27. autobyteus/agent/handlers/tool_invocation_request_event_handler.py +53 -48
  28. autobyteus/agent/handlers/tool_result_event_handler.py +7 -8
  29. autobyteus/agent/handlers/user_input_message_event_handler.py +10 -3
  30. autobyteus/agent/input_processor/memory_ingest_input_processor.py +44 -0
  31. autobyteus/agent/lifecycle/__init__.py +12 -0
  32. autobyteus/agent/lifecycle/base_processor.py +109 -0
  33. autobyteus/agent/lifecycle/events.py +35 -0
  34. autobyteus/agent/lifecycle/processor_definition.py +36 -0
  35. autobyteus/agent/lifecycle/processor_registry.py +106 -0
  36. autobyteus/agent/llm_request_assembler.py +98 -0
  37. autobyteus/agent/llm_response_processor/__init__.py +1 -8
  38. autobyteus/agent/message/context_file_type.py +1 -1
  39. autobyteus/agent/runtime/agent_runtime.py +29 -21
  40. autobyteus/agent/runtime/agent_worker.py +98 -19
  41. autobyteus/agent/shutdown_steps/__init__.py +2 -0
  42. autobyteus/agent/shutdown_steps/agent_shutdown_orchestrator.py +2 -0
  43. autobyteus/agent/shutdown_steps/tool_cleanup_step.py +58 -0
  44. autobyteus/agent/status/__init__.py +14 -0
  45. autobyteus/agent/status/manager.py +93 -0
  46. autobyteus/agent/status/status_deriver.py +96 -0
  47. autobyteus/agent/{phases/phase_enum.py → status/status_enum.py} +16 -16
  48. autobyteus/agent/status/status_update_utils.py +73 -0
  49. autobyteus/agent/streaming/__init__.py +52 -5
  50. autobyteus/agent/streaming/adapters/__init__.py +18 -0
  51. autobyteus/agent/streaming/adapters/invocation_adapter.py +184 -0
  52. autobyteus/agent/streaming/adapters/tool_call_parsing.py +163 -0
  53. autobyteus/agent/streaming/adapters/tool_syntax_registry.py +67 -0
  54. autobyteus/agent/streaming/agent_event_stream.py +3 -183
  55. autobyteus/agent/streaming/api_tool_call/__init__.py +16 -0
  56. autobyteus/agent/streaming/api_tool_call/file_content_streamer.py +56 -0
  57. autobyteus/agent/streaming/api_tool_call/json_string_field_extractor.py +175 -0
  58. autobyteus/agent/streaming/api_tool_call_streaming_response_handler.py +4 -0
  59. autobyteus/agent/streaming/events/__init__.py +6 -0
  60. autobyteus/agent/streaming/events/stream_event_payloads.py +284 -0
  61. autobyteus/agent/streaming/events/stream_events.py +141 -0
  62. autobyteus/agent/streaming/handlers/__init__.py +15 -0
  63. autobyteus/agent/streaming/handlers/api_tool_call_streaming_response_handler.py +303 -0
  64. autobyteus/agent/streaming/handlers/parsing_streaming_response_handler.py +107 -0
  65. autobyteus/agent/streaming/handlers/pass_through_streaming_response_handler.py +107 -0
  66. autobyteus/agent/streaming/handlers/streaming_handler_factory.py +177 -0
  67. autobyteus/agent/streaming/handlers/streaming_response_handler.py +58 -0
  68. autobyteus/agent/streaming/parser/__init__.py +61 -0
  69. autobyteus/agent/streaming/parser/event_emitter.py +181 -0
  70. autobyteus/agent/streaming/parser/events.py +4 -0
  71. autobyteus/agent/streaming/parser/invocation_adapter.py +4 -0
  72. autobyteus/agent/streaming/parser/json_parsing_strategies/__init__.py +19 -0
  73. autobyteus/agent/streaming/parser/json_parsing_strategies/base.py +32 -0
  74. autobyteus/agent/streaming/parser/json_parsing_strategies/default.py +34 -0
  75. autobyteus/agent/streaming/parser/json_parsing_strategies/gemini.py +31 -0
  76. autobyteus/agent/streaming/parser/json_parsing_strategies/openai.py +64 -0
  77. autobyteus/agent/streaming/parser/json_parsing_strategies/registry.py +75 -0
  78. autobyteus/agent/streaming/parser/parser_context.py +227 -0
  79. autobyteus/agent/streaming/parser/parser_factory.py +132 -0
  80. autobyteus/agent/streaming/parser/sentinel_format.py +7 -0
  81. autobyteus/agent/streaming/parser/state_factory.py +62 -0
  82. autobyteus/agent/streaming/parser/states/__init__.py +1 -0
  83. autobyteus/agent/streaming/parser/states/base_state.py +60 -0
  84. autobyteus/agent/streaming/parser/states/custom_xml_tag_run_bash_parsing_state.py +38 -0
  85. autobyteus/agent/streaming/parser/states/custom_xml_tag_write_file_parsing_state.py +55 -0
  86. autobyteus/agent/streaming/parser/states/delimited_content_state.py +146 -0
  87. autobyteus/agent/streaming/parser/states/json_initialization_state.py +144 -0
  88. autobyteus/agent/streaming/parser/states/json_tool_parsing_state.py +137 -0
  89. autobyteus/agent/streaming/parser/states/sentinel_content_state.py +30 -0
  90. autobyteus/agent/streaming/parser/states/sentinel_initialization_state.py +117 -0
  91. autobyteus/agent/streaming/parser/states/text_state.py +78 -0
  92. autobyteus/agent/streaming/parser/states/xml_patch_file_tool_parsing_state.py +328 -0
  93. autobyteus/agent/streaming/parser/states/xml_run_bash_tool_parsing_state.py +129 -0
  94. autobyteus/agent/streaming/parser/states/xml_tag_initialization_state.py +151 -0
  95. autobyteus/agent/streaming/parser/states/xml_tool_parsing_state.py +63 -0
  96. autobyteus/agent/streaming/parser/states/xml_write_file_tool_parsing_state.py +343 -0
  97. autobyteus/agent/streaming/parser/strategies/__init__.py +17 -0
  98. autobyteus/agent/streaming/parser/strategies/base.py +24 -0
  99. autobyteus/agent/streaming/parser/strategies/json_tool_strategy.py +26 -0
  100. autobyteus/agent/streaming/parser/strategies/registry.py +28 -0
  101. autobyteus/agent/streaming/parser/strategies/sentinel_strategy.py +23 -0
  102. autobyteus/agent/streaming/parser/strategies/xml_tag_strategy.py +21 -0
  103. autobyteus/agent/streaming/parser/stream_scanner.py +167 -0
  104. autobyteus/agent/streaming/parser/streaming_parser.py +212 -0
  105. autobyteus/agent/streaming/parser/tool_call_parsing.py +4 -0
  106. autobyteus/agent/streaming/parser/tool_constants.py +7 -0
  107. autobyteus/agent/streaming/parser/tool_syntax_registry.py +4 -0
  108. autobyteus/agent/streaming/parser/xml_tool_parsing_state_registry.py +55 -0
  109. autobyteus/agent/streaming/parsing_streaming_response_handler.py +4 -0
  110. autobyteus/agent/streaming/pass_through_streaming_response_handler.py +4 -0
  111. autobyteus/agent/streaming/queue_streamer.py +3 -57
  112. autobyteus/agent/streaming/segments/__init__.py +5 -0
  113. autobyteus/agent/streaming/segments/segment_events.py +82 -0
  114. autobyteus/agent/streaming/stream_event_payloads.py +2 -223
  115. autobyteus/agent/streaming/stream_events.py +3 -140
  116. autobyteus/agent/streaming/streaming_handler_factory.py +4 -0
  117. autobyteus/agent/streaming/streaming_response_handler.py +4 -0
  118. autobyteus/agent/streaming/streams/__init__.py +5 -0
  119. autobyteus/agent/streaming/streams/agent_event_stream.py +197 -0
  120. autobyteus/agent/streaming/utils/__init__.py +5 -0
  121. autobyteus/agent/streaming/utils/queue_streamer.py +59 -0
  122. autobyteus/agent/system_prompt_processor/__init__.py +2 -0
  123. autobyteus/agent/system_prompt_processor/available_skills_processor.py +96 -0
  124. autobyteus/agent/system_prompt_processor/base_processor.py +1 -1
  125. autobyteus/agent/system_prompt_processor/processor_meta.py +15 -2
  126. autobyteus/agent/system_prompt_processor/tool_manifest_injector_processor.py +39 -58
  127. autobyteus/agent/token_budget.py +56 -0
  128. autobyteus/agent/tool_execution_result_processor/memory_ingest_tool_result_processor.py +29 -0
  129. autobyteus/agent/tool_invocation.py +16 -40
  130. autobyteus/agent/tool_invocation_preprocessor/__init__.py +9 -0
  131. autobyteus/agent/tool_invocation_preprocessor/base_preprocessor.py +45 -0
  132. autobyteus/agent/tool_invocation_preprocessor/processor_definition.py +15 -0
  133. autobyteus/agent/tool_invocation_preprocessor/processor_meta.py +33 -0
  134. autobyteus/agent/tool_invocation_preprocessor/processor_registry.py +60 -0
  135. autobyteus/agent/utils/wait_for_idle.py +12 -14
  136. autobyteus/agent/workspace/base_workspace.py +6 -27
  137. autobyteus/agent_team/agent_team.py +3 -3
  138. autobyteus/agent_team/agent_team_builder.py +1 -41
  139. autobyteus/agent_team/bootstrap_steps/__init__.py +0 -4
  140. autobyteus/agent_team/bootstrap_steps/agent_configuration_preparation_step.py +8 -18
  141. autobyteus/agent_team/bootstrap_steps/agent_team_bootstrapper.py +4 -16
  142. autobyteus/agent_team/bootstrap_steps/base_agent_team_bootstrap_step.py +1 -2
  143. autobyteus/agent_team/bootstrap_steps/coordinator_initialization_step.py +1 -2
  144. autobyteus/agent_team/bootstrap_steps/task_notifier_initialization_step.py +1 -2
  145. autobyteus/agent_team/bootstrap_steps/team_context_initialization_step.py +4 -4
  146. autobyteus/agent_team/context/agent_team_config.py +6 -3
  147. autobyteus/agent_team/context/agent_team_context.py +25 -3
  148. autobyteus/agent_team/context/agent_team_runtime_state.py +9 -6
  149. autobyteus/agent_team/events/__init__.py +11 -0
  150. autobyteus/agent_team/events/agent_team_event_dispatcher.py +22 -9
  151. autobyteus/agent_team/events/agent_team_events.py +16 -0
  152. autobyteus/agent_team/events/event_store.py +57 -0
  153. autobyteus/agent_team/factory/agent_team_factory.py +8 -0
  154. autobyteus/agent_team/handlers/inter_agent_message_request_event_handler.py +18 -2
  155. autobyteus/agent_team/handlers/lifecycle_agent_team_event_handler.py +21 -5
  156. autobyteus/agent_team/handlers/process_user_message_event_handler.py +17 -8
  157. autobyteus/agent_team/handlers/tool_approval_team_event_handler.py +19 -4
  158. autobyteus/agent_team/runtime/agent_team_runtime.py +41 -10
  159. autobyteus/agent_team/runtime/agent_team_worker.py +69 -5
  160. autobyteus/agent_team/status/__init__.py +14 -0
  161. autobyteus/agent_team/status/agent_team_status.py +18 -0
  162. autobyteus/agent_team/status/agent_team_status_manager.py +33 -0
  163. autobyteus/agent_team/status/status_deriver.py +62 -0
  164. autobyteus/agent_team/status/status_update_utils.py +42 -0
  165. autobyteus/agent_team/streaming/__init__.py +2 -2
  166. autobyteus/agent_team/streaming/agent_team_event_notifier.py +6 -6
  167. autobyteus/agent_team/streaming/agent_team_stream_event_payloads.py +4 -4
  168. autobyteus/agent_team/streaming/agent_team_stream_events.py +3 -3
  169. autobyteus/agent_team/system_prompt_processor/__init__.py +6 -0
  170. autobyteus/agent_team/system_prompt_processor/team_manifest_injector_processor.py +76 -0
  171. autobyteus/agent_team/task_notification/task_notification_mode.py +19 -0
  172. autobyteus/agent_team/utils/wait_for_idle.py +4 -4
  173. autobyteus/cli/agent_cli.py +18 -10
  174. autobyteus/cli/agent_team_tui/app.py +14 -11
  175. autobyteus/cli/agent_team_tui/state.py +13 -15
  176. autobyteus/cli/agent_team_tui/widgets/agent_list_sidebar.py +15 -15
  177. autobyteus/cli/agent_team_tui/widgets/focus_pane.py +143 -36
  178. autobyteus/cli/agent_team_tui/widgets/renderables.py +1 -1
  179. autobyteus/cli/agent_team_tui/widgets/shared.py +25 -25
  180. autobyteus/cli/cli_display.py +193 -44
  181. autobyteus/cli/workflow_tui/app.py +9 -10
  182. autobyteus/cli/workflow_tui/state.py +14 -16
  183. autobyteus/cli/workflow_tui/widgets/agent_list_sidebar.py +15 -15
  184. autobyteus/cli/workflow_tui/widgets/focus_pane.py +137 -35
  185. autobyteus/cli/workflow_tui/widgets/renderables.py +1 -1
  186. autobyteus/cli/workflow_tui/widgets/shared.py +25 -25
  187. autobyteus/clients/autobyteus_client.py +94 -1
  188. autobyteus/events/event_types.py +11 -18
  189. autobyteus/llm/api/autobyteus_llm.py +33 -29
  190. autobyteus/llm/api/claude_llm.py +142 -36
  191. autobyteus/llm/api/gemini_llm.py +163 -59
  192. autobyteus/llm/api/grok_llm.py +1 -1
  193. autobyteus/llm/api/minimax_llm.py +26 -0
  194. autobyteus/llm/api/mistral_llm.py +113 -87
  195. autobyteus/llm/api/ollama_llm.py +9 -42
  196. autobyteus/llm/api/openai_compatible_llm.py +127 -91
  197. autobyteus/llm/api/openai_llm.py +3 -3
  198. autobyteus/llm/api/openai_responses_llm.py +324 -0
  199. autobyteus/llm/api/zhipu_llm.py +21 -2
  200. autobyteus/llm/autobyteus_provider.py +70 -60
  201. autobyteus/llm/base_llm.py +85 -81
  202. autobyteus/llm/converters/__init__.py +14 -0
  203. autobyteus/llm/converters/anthropic_tool_call_converter.py +37 -0
  204. autobyteus/llm/converters/gemini_tool_call_converter.py +57 -0
  205. autobyteus/llm/converters/mistral_tool_call_converter.py +37 -0
  206. autobyteus/llm/converters/openai_tool_call_converter.py +38 -0
  207. autobyteus/llm/extensions/base_extension.py +6 -12
  208. autobyteus/llm/extensions/token_usage_tracking_extension.py +45 -18
  209. autobyteus/llm/llm_factory.py +282 -204
  210. autobyteus/llm/lmstudio_provider.py +60 -49
  211. autobyteus/llm/models.py +35 -2
  212. autobyteus/llm/ollama_provider.py +60 -49
  213. autobyteus/llm/ollama_provider_resolver.py +0 -1
  214. autobyteus/llm/prompt_renderers/__init__.py +19 -0
  215. autobyteus/llm/prompt_renderers/anthropic_prompt_renderer.py +104 -0
  216. autobyteus/llm/prompt_renderers/autobyteus_prompt_renderer.py +19 -0
  217. autobyteus/llm/prompt_renderers/base_prompt_renderer.py +10 -0
  218. autobyteus/llm/prompt_renderers/gemini_prompt_renderer.py +63 -0
  219. autobyteus/llm/prompt_renderers/mistral_prompt_renderer.py +87 -0
  220. autobyteus/llm/prompt_renderers/ollama_prompt_renderer.py +51 -0
  221. autobyteus/llm/prompt_renderers/openai_chat_renderer.py +97 -0
  222. autobyteus/llm/prompt_renderers/openai_responses_renderer.py +101 -0
  223. autobyteus/llm/providers.py +1 -3
  224. autobyteus/llm/token_counter/claude_token_counter.py +56 -25
  225. autobyteus/llm/token_counter/mistral_token_counter.py +12 -8
  226. autobyteus/llm/token_counter/openai_token_counter.py +24 -5
  227. autobyteus/llm/token_counter/token_counter_factory.py +12 -5
  228. autobyteus/llm/utils/llm_config.py +6 -12
  229. autobyteus/llm/utils/media_payload_formatter.py +27 -20
  230. autobyteus/llm/utils/messages.py +55 -3
  231. autobyteus/llm/utils/response_types.py +3 -0
  232. autobyteus/llm/utils/tool_call_delta.py +31 -0
  233. autobyteus/memory/__init__.py +35 -0
  234. autobyteus/memory/compaction/__init__.py +9 -0
  235. autobyteus/memory/compaction/compaction_result.py +8 -0
  236. autobyteus/memory/compaction/compactor.py +89 -0
  237. autobyteus/memory/compaction/summarizer.py +11 -0
  238. autobyteus/memory/compaction_snapshot_builder.py +84 -0
  239. autobyteus/memory/memory_manager.py +205 -0
  240. autobyteus/memory/models/__init__.py +14 -0
  241. autobyteus/memory/models/episodic_item.py +41 -0
  242. autobyteus/memory/models/memory_types.py +7 -0
  243. autobyteus/memory/models/raw_trace_item.py +79 -0
  244. autobyteus/memory/models/semantic_item.py +41 -0
  245. autobyteus/memory/models/tool_interaction.py +20 -0
  246. autobyteus/memory/path_resolver.py +27 -0
  247. autobyteus/memory/policies/__init__.py +5 -0
  248. autobyteus/memory/policies/compaction_policy.py +16 -0
  249. autobyteus/memory/restore/__init__.py +1 -0
  250. autobyteus/memory/restore/working_context_snapshot_bootstrapper.py +61 -0
  251. autobyteus/memory/retrieval/__init__.py +7 -0
  252. autobyteus/memory/retrieval/memory_bundle.py +11 -0
  253. autobyteus/memory/retrieval/retriever.py +13 -0
  254. autobyteus/memory/store/__init__.py +9 -0
  255. autobyteus/memory/store/base_store.py +14 -0
  256. autobyteus/memory/store/file_store.py +98 -0
  257. autobyteus/memory/store/working_context_snapshot_store.py +28 -0
  258. autobyteus/memory/tool_interaction_builder.py +46 -0
  259. autobyteus/memory/turn_tracker.py +9 -0
  260. autobyteus/memory/working_context_snapshot.py +69 -0
  261. autobyteus/memory/working_context_snapshot_serializer.py +135 -0
  262. autobyteus/multimedia/audio/api/autobyteus_audio_client.py +19 -5
  263. autobyteus/multimedia/audio/api/gemini_audio_client.py +109 -16
  264. autobyteus/multimedia/audio/audio_client_factory.py +47 -9
  265. autobyteus/multimedia/audio/audio_model.py +2 -1
  266. autobyteus/multimedia/image/api/autobyteus_image_client.py +19 -5
  267. autobyteus/multimedia/image/api/gemini_image_client.py +39 -17
  268. autobyteus/multimedia/image/api/openai_image_client.py +125 -43
  269. autobyteus/multimedia/image/autobyteus_image_provider.py +2 -1
  270. autobyteus/multimedia/image/image_client_factory.py +47 -15
  271. autobyteus/multimedia/image/image_model.py +5 -2
  272. autobyteus/multimedia/providers.py +3 -2
  273. autobyteus/skills/loader.py +71 -0
  274. autobyteus/skills/model.py +11 -0
  275. autobyteus/skills/registry.py +70 -0
  276. autobyteus/task_management/tools/todo_tools/add_todo.py +2 -2
  277. autobyteus/task_management/tools/todo_tools/create_todo_list.py +2 -2
  278. autobyteus/task_management/tools/todo_tools/update_todo_status.py +2 -2
  279. autobyteus/tools/__init__.py +34 -47
  280. autobyteus/tools/base_tool.py +7 -0
  281. autobyteus/tools/file/__init__.py +2 -6
  282. autobyteus/tools/file/patch_file.py +149 -0
  283. autobyteus/tools/file/read_file.py +36 -5
  284. autobyteus/tools/file/write_file.py +4 -1
  285. autobyteus/tools/functional_tool.py +43 -6
  286. autobyteus/tools/mcp/__init__.py +2 -0
  287. autobyteus/tools/mcp/config_service.py +5 -1
  288. autobyteus/tools/mcp/server/__init__.py +2 -0
  289. autobyteus/tools/mcp/server/http_managed_mcp_server.py +1 -1
  290. autobyteus/tools/mcp/server/websocket_managed_mcp_server.py +141 -0
  291. autobyteus/tools/mcp/server_instance_manager.py +8 -1
  292. autobyteus/tools/mcp/types.py +61 -0
  293. autobyteus/tools/multimedia/audio_tools.py +70 -17
  294. autobyteus/tools/multimedia/download_media_tool.py +18 -4
  295. autobyteus/tools/multimedia/image_tools.py +246 -62
  296. autobyteus/tools/operation_executor/journal_manager.py +107 -0
  297. autobyteus/tools/operation_executor/operation_event_buffer.py +57 -0
  298. autobyteus/tools/operation_executor/operation_event_producer.py +29 -0
  299. autobyteus/tools/operation_executor/operation_executor.py +58 -0
  300. autobyteus/tools/registry/tool_definition.py +43 -2
  301. autobyteus/tools/skill/load_skill.py +50 -0
  302. autobyteus/tools/terminal/__init__.py +45 -0
  303. autobyteus/tools/terminal/ansi_utils.py +32 -0
  304. autobyteus/tools/terminal/background_process_manager.py +233 -0
  305. autobyteus/tools/terminal/output_buffer.py +105 -0
  306. autobyteus/tools/terminal/prompt_detector.py +63 -0
  307. autobyteus/tools/terminal/pty_session.py +241 -0
  308. autobyteus/tools/terminal/session_factory.py +20 -0
  309. autobyteus/tools/terminal/terminal_session_manager.py +226 -0
  310. autobyteus/tools/terminal/tools/__init__.py +13 -0
  311. autobyteus/tools/terminal/tools/get_process_output.py +81 -0
  312. autobyteus/tools/terminal/tools/run_bash.py +109 -0
  313. autobyteus/tools/terminal/tools/start_background_process.py +104 -0
  314. autobyteus/tools/terminal/tools/stop_background_process.py +67 -0
  315. autobyteus/tools/terminal/types.py +54 -0
  316. autobyteus/tools/terminal/wsl_tmux_session.py +221 -0
  317. autobyteus/tools/terminal/wsl_utils.py +156 -0
  318. autobyteus/tools/transaction_management/backup_handler.py +48 -0
  319. autobyteus/tools/transaction_management/operation_lifecycle_manager.py +62 -0
  320. autobyteus/tools/usage/__init__.py +1 -2
  321. autobyteus/tools/usage/formatters/__init__.py +17 -1
  322. autobyteus/tools/usage/formatters/base_formatter.py +8 -0
  323. autobyteus/tools/usage/formatters/default_xml_schema_formatter.py +2 -2
  324. autobyteus/tools/usage/formatters/mistral_json_schema_formatter.py +18 -0
  325. autobyteus/tools/usage/formatters/patch_file_xml_example_formatter.py +64 -0
  326. autobyteus/tools/usage/formatters/patch_file_xml_schema_formatter.py +31 -0
  327. autobyteus/tools/usage/formatters/run_bash_xml_example_formatter.py +32 -0
  328. autobyteus/tools/usage/formatters/run_bash_xml_schema_formatter.py +36 -0
  329. autobyteus/tools/usage/formatters/write_file_xml_example_formatter.py +53 -0
  330. autobyteus/tools/usage/formatters/write_file_xml_schema_formatter.py +31 -0
  331. autobyteus/tools/usage/providers/tool_manifest_provider.py +10 -10
  332. autobyteus/tools/usage/registries/__init__.py +1 -3
  333. autobyteus/tools/usage/registries/tool_formatting_registry.py +115 -8
  334. autobyteus/tools/usage/tool_schema_provider.py +51 -0
  335. autobyteus/tools/web/__init__.py +4 -0
  336. autobyteus/tools/web/read_url_tool.py +80 -0
  337. autobyteus/utils/diff_utils.py +271 -0
  338. autobyteus/utils/download_utils.py +109 -0
  339. autobyteus/utils/file_utils.py +57 -2
  340. autobyteus/utils/gemini_helper.py +64 -0
  341. autobyteus/utils/gemini_model_mapping.py +71 -0
  342. autobyteus/utils/llm_output_formatter.py +75 -0
  343. autobyteus/utils/tool_call_format.py +36 -0
  344. autobyteus/workflow/agentic_workflow.py +3 -3
  345. autobyteus/workflow/bootstrap_steps/agent_tool_injection_step.py +2 -2
  346. autobyteus/workflow/bootstrap_steps/base_workflow_bootstrap_step.py +2 -2
  347. autobyteus/workflow/bootstrap_steps/coordinator_initialization_step.py +2 -2
  348. autobyteus/workflow/bootstrap_steps/coordinator_prompt_preparation_step.py +3 -9
  349. autobyteus/workflow/bootstrap_steps/workflow_bootstrapper.py +6 -6
  350. autobyteus/workflow/bootstrap_steps/workflow_runtime_queue_initialization_step.py +2 -2
  351. autobyteus/workflow/context/workflow_context.py +3 -3
  352. autobyteus/workflow/context/workflow_runtime_state.py +5 -5
  353. autobyteus/workflow/events/workflow_event_dispatcher.py +5 -5
  354. autobyteus/workflow/handlers/lifecycle_workflow_event_handler.py +3 -3
  355. autobyteus/workflow/handlers/process_user_message_event_handler.py +5 -5
  356. autobyteus/workflow/handlers/tool_approval_workflow_event_handler.py +2 -2
  357. autobyteus/workflow/runtime/workflow_runtime.py +8 -8
  358. autobyteus/workflow/runtime/workflow_worker.py +3 -3
  359. autobyteus/workflow/status/__init__.py +11 -0
  360. autobyteus/workflow/status/workflow_status.py +19 -0
  361. autobyteus/workflow/status/workflow_status_manager.py +48 -0
  362. autobyteus/workflow/streaming/__init__.py +2 -2
  363. autobyteus/workflow/streaming/workflow_event_notifier.py +7 -7
  364. autobyteus/workflow/streaming/workflow_stream_event_payloads.py +4 -4
  365. autobyteus/workflow/streaming/workflow_stream_events.py +3 -3
  366. autobyteus/workflow/utils/wait_for_idle.py +4 -4
  367. autobyteus-1.3.0.dist-info/METADATA +293 -0
  368. autobyteus-1.3.0.dist-info/RECORD +606 -0
  369. {autobyteus-1.2.1.dist-info → autobyteus-1.3.0.dist-info}/WHEEL +1 -1
  370. {autobyteus-1.2.1.dist-info → autobyteus-1.3.0.dist-info}/top_level.txt +0 -1
  371. autobyteus/agent/bootstrap_steps/agent_runtime_queue_initialization_step.py +0 -57
  372. autobyteus/agent/hooks/__init__.py +0 -16
  373. autobyteus/agent/hooks/base_phase_hook.py +0 -78
  374. autobyteus/agent/hooks/hook_definition.py +0 -36
  375. autobyteus/agent/hooks/hook_meta.py +0 -37
  376. autobyteus/agent/hooks/hook_registry.py +0 -106
  377. autobyteus/agent/llm_response_processor/provider_aware_tool_usage_processor.py +0 -103
  378. autobyteus/agent/phases/__init__.py +0 -18
  379. autobyteus/agent/phases/discover.py +0 -53
  380. autobyteus/agent/phases/manager.py +0 -265
  381. autobyteus/agent/phases/transition_decorator.py +0 -40
  382. autobyteus/agent/phases/transition_info.py +0 -33
  383. autobyteus/agent/remote_agent.py +0 -244
  384. autobyteus/agent/workspace/workspace_definition.py +0 -36
  385. autobyteus/agent/workspace/workspace_meta.py +0 -37
  386. autobyteus/agent/workspace/workspace_registry.py +0 -72
  387. autobyteus/agent_team/bootstrap_steps/agent_team_runtime_queue_initialization_step.py +0 -25
  388. autobyteus/agent_team/bootstrap_steps/coordinator_prompt_preparation_step.py +0 -85
  389. autobyteus/agent_team/phases/__init__.py +0 -11
  390. autobyteus/agent_team/phases/agent_team_operational_phase.py +0 -19
  391. autobyteus/agent_team/phases/agent_team_phase_manager.py +0 -48
  392. autobyteus/llm/api/bedrock_llm.py +0 -92
  393. autobyteus/llm/api/groq_llm.py +0 -94
  394. autobyteus/llm/api/nvidia_llm.py +0 -108
  395. autobyteus/llm/utils/token_pricing_config.py +0 -87
  396. autobyteus/rpc/__init__.py +0 -73
  397. autobyteus/rpc/client/__init__.py +0 -17
  398. autobyteus/rpc/client/abstract_client_connection.py +0 -124
  399. autobyteus/rpc/client/client_connection_manager.py +0 -153
  400. autobyteus/rpc/client/sse_client_connection.py +0 -306
  401. autobyteus/rpc/client/stdio_client_connection.py +0 -280
  402. autobyteus/rpc/config/__init__.py +0 -13
  403. autobyteus/rpc/config/agent_server_config.py +0 -153
  404. autobyteus/rpc/config/agent_server_registry.py +0 -152
  405. autobyteus/rpc/hosting.py +0 -244
  406. autobyteus/rpc/protocol.py +0 -244
  407. autobyteus/rpc/server/__init__.py +0 -20
  408. autobyteus/rpc/server/agent_server_endpoint.py +0 -181
  409. autobyteus/rpc/server/base_method_handler.py +0 -40
  410. autobyteus/rpc/server/method_handlers.py +0 -259
  411. autobyteus/rpc/server/sse_server_handler.py +0 -182
  412. autobyteus/rpc/server/stdio_server_handler.py +0 -151
  413. autobyteus/rpc/server_main.py +0 -198
  414. autobyteus/rpc/transport_type.py +0 -13
  415. autobyteus/tools/bash/__init__.py +0 -2
  416. autobyteus/tools/bash/bash_executor.py +0 -100
  417. autobyteus/tools/browser/__init__.py +0 -2
  418. autobyteus/tools/browser/session_aware/browser_session_aware_navigate_to.py +0 -75
  419. autobyteus/tools/browser/session_aware/browser_session_aware_tool.py +0 -30
  420. autobyteus/tools/browser/session_aware/browser_session_aware_web_element_trigger.py +0 -154
  421. autobyteus/tools/browser/session_aware/browser_session_aware_webpage_reader.py +0 -89
  422. autobyteus/tools/browser/session_aware/browser_session_aware_webpage_screenshot_taker.py +0 -107
  423. autobyteus/tools/browser/session_aware/factory/browser_session_aware_web_element_trigger_factory.py +0 -14
  424. autobyteus/tools/browser/session_aware/factory/browser_session_aware_webpage_reader_factory.py +0 -26
  425. autobyteus/tools/browser/session_aware/factory/browser_session_aware_webpage_screenshot_taker_factory.py +0 -14
  426. autobyteus/tools/browser/session_aware/shared_browser_session.py +0 -11
  427. autobyteus/tools/browser/session_aware/shared_browser_session_manager.py +0 -25
  428. autobyteus/tools/browser/session_aware/web_element_action.py +0 -20
  429. autobyteus/tools/browser/standalone/__init__.py +0 -6
  430. autobyteus/tools/browser/standalone/factory/__init__.py +0 -0
  431. autobyteus/tools/browser/standalone/factory/webpage_reader_factory.py +0 -25
  432. autobyteus/tools/browser/standalone/factory/webpage_screenshot_taker_factory.py +0 -14
  433. autobyteus/tools/browser/standalone/navigate_to.py +0 -84
  434. autobyteus/tools/browser/standalone/web_page_pdf_generator.py +0 -101
  435. autobyteus/tools/browser/standalone/webpage_image_downloader.py +0 -169
  436. autobyteus/tools/browser/standalone/webpage_reader.py +0 -105
  437. autobyteus/tools/browser/standalone/webpage_screenshot_taker.py +0 -105
  438. autobyteus/tools/file/edit_file.py +0 -200
  439. autobyteus/tools/file/list_directory.py +0 -168
  440. autobyteus/tools/file/search_files.py +0 -188
  441. autobyteus/tools/timer.py +0 -175
  442. autobyteus/tools/usage/parsers/__init__.py +0 -22
  443. autobyteus/tools/usage/parsers/_json_extractor.py +0 -99
  444. autobyteus/tools/usage/parsers/_string_decoders.py +0 -18
  445. autobyteus/tools/usage/parsers/anthropic_xml_tool_usage_parser.py +0 -10
  446. autobyteus/tools/usage/parsers/base_parser.py +0 -41
  447. autobyteus/tools/usage/parsers/default_json_tool_usage_parser.py +0 -83
  448. autobyteus/tools/usage/parsers/default_xml_tool_usage_parser.py +0 -316
  449. autobyteus/tools/usage/parsers/exceptions.py +0 -13
  450. autobyteus/tools/usage/parsers/gemini_json_tool_usage_parser.py +0 -77
  451. autobyteus/tools/usage/parsers/openai_json_tool_usage_parser.py +0 -149
  452. autobyteus/tools/usage/parsers/provider_aware_tool_usage_parser.py +0 -59
  453. autobyteus/tools/usage/registries/tool_usage_parser_registry.py +0 -62
  454. autobyteus/workflow/phases/__init__.py +0 -11
  455. autobyteus/workflow/phases/workflow_operational_phase.py +0 -19
  456. autobyteus/workflow/phases/workflow_phase_manager.py +0 -48
  457. autobyteus-1.2.1.dist-info/METADATA +0 -205
  458. autobyteus-1.2.1.dist-info/RECORD +0 -511
  459. examples/__init__.py +0 -1
  460. examples/agent_team/__init__.py +0 -1
  461. examples/discover_phase_transitions.py +0 -104
  462. examples/run_agentic_software_engineer.py +0 -239
  463. examples/run_browser_agent.py +0 -262
  464. examples/run_google_slides_agent.py +0 -287
  465. examples/run_mcp_browser_client.py +0 -174
  466. examples/run_mcp_google_slides_client.py +0 -270
  467. examples/run_mcp_list_tools.py +0 -189
  468. examples/run_poem_writer.py +0 -284
  469. examples/run_sqlite_agent.py +0 -295
  470. /autobyteus/{tools/browser/session_aware → skills}/__init__.py +0 -0
  471. /autobyteus/tools/{browser/session_aware/factory → skill}/__init__.py +0 -0
  472. {autobyteus-1.2.1.dist-info → autobyteus-1.3.0.dist-info}/licenses/LICENSE +0 -0
@@ -1,117 +1,74 @@
1
1
  # file: autobyteus/autobyteus/agent/events/worker_event_dispatcher.py
2
- import asyncio
3
2
  import logging
4
3
  import traceback
5
- from typing import TYPE_CHECKING, Optional
4
+ from typing import TYPE_CHECKING
6
5
 
7
- from autobyteus.agent.phases import AgentOperationalPhase
6
+ from autobyteus.agent.status.status_enum import AgentStatus
7
+ from autobyteus.agent.status.status_update_utils import apply_event_and_derive_status
8
8
  from autobyteus.agent.events.agent_events import ( # Updated relative import path if needed, but BaseEvent is fine
9
9
  BaseEvent,
10
- AgentReadyEvent,
11
10
  AgentErrorEvent,
12
- LLMUserMessageReadyEvent,
13
- PendingToolInvocationEvent,
14
- ToolExecutionApprovalEvent,
15
- ToolResultEvent,
11
+ AgentIdleEvent,
16
12
  LLMCompleteResponseReceivedEvent,
17
- UserMessageReceivedEvent,
18
- InterAgentMessageReceivedEvent,
19
13
  )
20
14
 
21
15
  if TYPE_CHECKING:
22
16
  from autobyteus.agent.context import AgentContext
23
17
  from autobyteus.agent.handlers import EventHandlerRegistry
24
- from autobyteus.agent.phases import AgentPhaseManager
25
18
  logger = logging.getLogger(__name__)
26
19
 
27
20
  class WorkerEventDispatcher:
28
21
  """
29
22
  Responsible for dispatching events to their appropriate handlers within an AgentWorker.
30
- It also manages related phase transitions that occur immediately before or after
23
+ It also manages related status updates that occur immediately before or after
31
24
  an event is handled. This component is part of the agent's event system.
32
25
  """
33
26
 
34
27
  def __init__(self,
35
- event_handler_registry: 'EventHandlerRegistry',
36
- phase_manager: 'AgentPhaseManager'):
28
+ event_handler_registry: 'EventHandlerRegistry'):
37
29
  """
38
30
  Initializes the WorkerEventDispatcher.
39
31
 
40
32
  Args:
41
33
  event_handler_registry: The registry for event handlers.
42
- phase_manager: The agent's phase manager.
43
34
  """
44
35
  self.event_handler_registry: 'EventHandlerRegistry' = event_handler_registry
45
- self.phase_manager: 'AgentPhaseManager' = phase_manager
46
36
  logger.debug("WorkerEventDispatcher initialized.")
47
37
 
48
38
  async def dispatch(self, event: BaseEvent, context: 'AgentContext') -> None: # pragma: no cover
49
39
  """
50
- Dispatches an event to its registered handler and manages phase transitions.
40
+ Dispatches an event to its registered handler and manages status updates.
51
41
  """
52
42
  event_class = type(event)
53
43
  handler = self.event_handler_registry.get_handler(event_class)
54
44
  agent_id = context.agent_id
55
45
 
46
+ try:
47
+ await apply_event_and_derive_status(event, context)
48
+ except Exception as e: # pragma: no cover
49
+ logger.error(f"WorkerEventDispatcher '{agent_id}': Status projection failed: {e}", exc_info=True)
50
+
56
51
  if handler:
57
52
  event_class_name = event_class.__name__
58
53
  handler_class_name = type(handler).__name__
59
54
 
60
- current_phase_before_dispatch = context.current_phase
61
-
62
- if current_phase_before_dispatch == AgentOperationalPhase.IDLE:
63
- if isinstance(event, (UserMessageReceivedEvent, InterAgentMessageReceivedEvent)):
64
- await self.phase_manager.notify_processing_input_started(trigger_info=type(event).__name__)
65
-
66
- if isinstance(event, LLMUserMessageReadyEvent):
67
- if current_phase_before_dispatch not in [AgentOperationalPhase.AWAITING_LLM_RESPONSE, AgentOperationalPhase.ERROR]:
68
- await self.phase_manager.notify_awaiting_llm_response()
69
- elif isinstance(event, PendingToolInvocationEvent):
70
- if not context.auto_execute_tools:
71
- await self.phase_manager.notify_tool_execution_pending_approval(event.tool_invocation)
72
- else:
73
- await self.phase_manager.notify_tool_execution_started(event.tool_invocation.name)
74
- elif isinstance(event, ToolExecutionApprovalEvent):
75
- tool_name_for_approval: Optional[str] = None
76
- pending_invocation = context.state.pending_tool_approvals.get(event.tool_invocation_id)
77
- if pending_invocation:
78
- tool_name_for_approval = pending_invocation.name
79
- else:
80
- logger.warning(f"WorkerEventDispatcher '{agent_id}': Could not find pending invocation for ID '{event.tool_invocation_id}' to get tool name for phase notification.")
81
- tool_name_for_approval = "unknown_tool"
82
-
83
- await self.phase_manager.notify_tool_execution_resumed_after_approval(
84
- approved=event.is_approved,
85
- tool_name=tool_name_for_approval
86
- )
87
- elif isinstance(event, ToolResultEvent):
88
- if context.current_phase == AgentOperationalPhase.EXECUTING_TOOL:
89
- await self.phase_manager.notify_processing_tool_result(event.tool_name)
90
- elif isinstance(event, LLMCompleteResponseReceivedEvent):
91
- if context.current_phase == AgentOperationalPhase.AWAITING_LLM_RESPONSE:
92
- await self.phase_manager.notify_analyzing_llm_response()
93
-
94
55
  try:
95
- logger.debug(f"WorkerEventDispatcher '{agent_id}' (Phase: {context.current_phase.value}) dispatching '{event_class_name}' to {handler_class_name}.")
56
+ logger.debug(f"WorkerEventDispatcher '{agent_id}' (Status: {context.current_status.value}) dispatching '{event_class_name}' to {handler_class_name}.")
96
57
  await handler.handle(event, context)
97
- logger.debug(f"WorkerEventDispatcher '{agent_id}' (Phase: {context.current_phase.value}) event '{event_class_name}' handled by {handler_class_name}.")
98
-
99
- if isinstance(event, AgentReadyEvent):
100
- await self.phase_manager.notify_initialization_complete()
101
-
102
- if isinstance(event, LLMCompleteResponseReceivedEvent):
103
- if context.current_phase == AgentOperationalPhase.ANALYZING_LLM_RESPONSE and \
104
- not context.state.pending_tool_approvals and \
105
- context.input_event_queues.tool_invocation_request_queue.empty():
106
- await self.phase_manager.notify_processing_complete_and_idle()
58
+ logger.debug(f"WorkerEventDispatcher '{agent_id}' (Status: {context.current_status.value}) event '{event_class_name}' handled by {handler_class_name}.")
107
59
 
108
60
  except Exception as e:
109
61
  error_details = traceback.format_exc()
110
62
  error_msg = f"WorkerEventDispatcher '{agent_id}' error handling '{event_class_name}' with {handler_class_name}: {e}"
111
63
  logger.error(error_msg, exc_info=True)
112
- await self.phase_manager.notify_error_occurred(error_msg, error_details)
113
64
  await context.input_event_queues.enqueue_internal_system_event(
114
65
  AgentErrorEvent(error_message=error_msg, exception_details=error_details)
115
66
  )
67
+ else:
68
+ if isinstance(event, LLMCompleteResponseReceivedEvent):
69
+ if context.current_status == AgentStatus.ANALYZING_LLM_RESPONSE and \
70
+ not context.state.pending_tool_approvals and \
71
+ context.input_event_queues.tool_invocation_request_queue.empty():
72
+ await context.input_event_queues.enqueue_internal_system_event(AgentIdleEvent())
116
73
  else:
117
- logger.warning(f"WorkerEventDispatcher '{agent_id}' (Phase: {context.current_phase.value}) No handler for '{event_class.__name__}'. Event: {event}")
74
+ logger.warning(f"WorkerEventDispatcher '{agent_id}' (Status: {context.current_status.value}) No handler for '{event_class.__name__}'. Event: {event}")
@@ -13,6 +13,13 @@ from autobyteus.agent.workspace.base_workspace import BaseAgentWorkspace
13
13
  from autobyteus.agent.handlers import *
14
14
  from autobyteus.utils.singleton import SingletonMeta
15
15
  from autobyteus.tools.base_tool import BaseTool
16
+ from autobyteus.memory import FileMemoryStore, MemoryManager, resolve_memory_base_dir
17
+ from autobyteus.memory.store.working_context_snapshot_store import WorkingContextSnapshotStore
18
+ from autobyteus.memory.restore.working_context_snapshot_bootstrapper import WorkingContextSnapshotBootstrapOptions
19
+ from autobyteus.agent.input_processor.memory_ingest_input_processor import MemoryIngestInputProcessor
20
+ from autobyteus.agent.tool_execution_result_processor.memory_ingest_tool_result_processor import (
21
+ MemoryIngestToolResultProcessor,
22
+ )
16
23
 
17
24
  if TYPE_CHECKING:
18
25
  from autobyteus.agent.runtime.agent_runtime import AgentRuntime
@@ -41,9 +48,16 @@ class AgentFactory(metaclass=SingletonMeta):
41
48
  registry.register(ToolExecutionApprovalEvent, ToolExecutionApprovalEventHandler())
42
49
  registry.register(LLMUserMessageReadyEvent, LLMUserMessageReadyEventHandler())
43
50
  registry.register(ApprovedToolInvocationEvent, ApprovedToolInvocationEventHandler())
51
+ bootstrap_handler = BootstrapEventHandler()
52
+ registry.register(BootstrapStartedEvent, bootstrap_handler)
53
+ registry.register(BootstrapStepRequestedEvent, bootstrap_handler)
54
+ registry.register(BootstrapStepCompletedEvent, bootstrap_handler)
55
+ registry.register(BootstrapCompletedEvent, bootstrap_handler)
44
56
  lifecycle_logger_instance = LifecycleEventLogger()
45
57
  registry.register(AgentReadyEvent, lifecycle_logger_instance)
46
58
  registry.register(AgentStoppedEvent, lifecycle_logger_instance)
59
+ registry.register(AgentIdleEvent, lifecycle_logger_instance)
60
+ registry.register(ShutdownRequestedEvent, lifecycle_logger_instance)
47
61
  registry.register(AgentErrorEvent, lifecycle_logger_instance)
48
62
  return registry
49
63
 
@@ -69,18 +83,58 @@ class AgentFactory(metaclass=SingletonMeta):
69
83
 
70
84
  return tool_instances_dict
71
85
 
72
- def _create_runtime(self,
73
- agent_id: str,
74
- config: AgentConfig
75
- ) -> 'AgentRuntime':
86
+ def _prepare_skills(self, agent_id: str, config: AgentConfig):
87
+ """
88
+ Registers skills from paths and ensures all skill names are valid.
89
+ """
90
+ from autobyteus.skills.registry import SkillRegistry
91
+ import os
92
+
93
+ registry = SkillRegistry()
94
+ updated_skills = []
95
+ for skill_item in config.skills:
96
+ # Check if it's a path (absolute or relative to current working directory)
97
+ if os.path.isabs(skill_item) or os.path.exists(skill_item):
98
+ try:
99
+ skill = registry.register_skill_from_path(skill_item)
100
+ updated_skills.append(skill.name)
101
+ except Exception as e:
102
+ logger.error(f"Agent '{agent_id}': Failed to register skill from path '{skill_item}': {e}")
103
+ else:
104
+ updated_skills.append(skill_item)
105
+
106
+ config.skills = updated_skills
107
+
108
+ def _create_runtime_with_id(self,
109
+ agent_id: str,
110
+ config: AgentConfig,
111
+ memory_dir_override: Optional[str] = None,
112
+ restore_options: Optional[WorkingContextSnapshotBootstrapOptions] = None
113
+ ) -> 'AgentRuntime':
76
114
  from autobyteus.agent.runtime.agent_runtime import AgentRuntime
77
115
 
116
+ # Prepare skills (resolve paths to names and register them)
117
+ self._prepare_skills(agent_id, config)
118
+
78
119
  # The workspace and initial custom data are now passed directly from the config to the state.
79
120
  runtime_state = AgentRuntimeState(
80
121
  agent_id=agent_id,
81
122
  workspace=config.workspace,
82
123
  custom_data=config.initial_custom_data
83
124
  )
125
+
126
+ # Memory manager (file-backed) initialization
127
+ memory_dir = resolve_memory_base_dir(override_dir=memory_dir_override or config.memory_dir)
128
+ memory_store = FileMemoryStore(base_dir=memory_dir, agent_id=agent_id)
129
+ working_context_snapshot_store = WorkingContextSnapshotStore(base_dir=memory_dir, agent_id=agent_id)
130
+ runtime_state.memory_manager = MemoryManager(store=memory_store, working_context_snapshot_store=working_context_snapshot_store)
131
+ runtime_state.restore_options = restore_options
132
+
133
+ # Ensure memory ingest processors are present
134
+ if not any(isinstance(p, MemoryIngestInputProcessor) for p in config.input_processors):
135
+ config.input_processors.append(MemoryIngestInputProcessor())
136
+ if not any(isinstance(p, MemoryIngestToolResultProcessor) for p in config.tool_execution_result_processors):
137
+ config.tool_execution_result_processors.append(MemoryIngestToolResultProcessor())
84
138
 
85
139
  # --- Set pre-initialized instances on the state ---
86
140
  runtime_state.llm_instance = config.llm_instance
@@ -94,7 +148,7 @@ class AgentFactory(metaclass=SingletonMeta):
94
148
  logger.info(f"Instantiating AgentRuntime for agent_id: '{agent_id}' with config: '{config.name}'.")
95
149
 
96
150
  return AgentRuntime(
97
- context=context,
151
+ context=context,
98
152
  event_handler_registry=event_handler_registry
99
153
  )
100
154
 
@@ -114,7 +168,7 @@ class AgentFactory(metaclass=SingletonMeta):
114
168
  while agent_id in self._active_agents:
115
169
  agent_id = f"{config.name}_{config.role}_{random.randint(1000, 9999)}"
116
170
 
117
- runtime = self._create_runtime(
171
+ runtime = self._create_runtime_with_id(
118
172
  agent_id=agent_id,
119
173
  config=config,
120
174
  )
@@ -124,6 +178,29 @@ class AgentFactory(metaclass=SingletonMeta):
124
178
  logger.info(f"Agent '{agent_id}' created and stored successfully.")
125
179
  return agent
126
180
 
181
+ def restore_agent(
182
+ self,
183
+ agent_id: str,
184
+ config: AgentConfig,
185
+ memory_dir: Optional[str] = None,
186
+ ) -> Agent:
187
+ if not agent_id or not isinstance(agent_id, str):
188
+ raise ValueError("restore_agent requires a non-empty string agent_id.")
189
+ if agent_id in self._active_agents:
190
+ raise ValueError(f"Agent '{agent_id}' is already active.")
191
+
192
+ restore_options = WorkingContextSnapshotBootstrapOptions()
193
+ runtime = self._create_runtime_with_id(
194
+ agent_id=agent_id,
195
+ config=config,
196
+ memory_dir_override=memory_dir,
197
+ restore_options=restore_options,
198
+ )
199
+ agent = Agent(runtime=runtime)
200
+ self._active_agents[agent_id] = agent
201
+ logger.info(f"Agent '{agent_id}' restored and stored successfully.")
202
+ return agent
203
+
127
204
  def get_agent(self, agent_id: str) -> Optional[Agent]:
128
205
  """Retrieves an active agent instance by its ID."""
129
206
  return self._active_agents.get(agent_id)
@@ -14,6 +14,7 @@ from .tool_invocation_request_event_handler import ToolInvocationRequestEventHan
14
14
  from .tool_result_event_handler import ToolResultEventHandler
15
15
  from .approved_tool_invocation_event_handler import ApprovedToolInvocationEventHandler
16
16
  from .tool_execution_approval_event_handler import ToolExecutionApprovalEventHandler
17
+ from .bootstrap_event_handler import BootstrapEventHandler
17
18
 
18
19
  # General Purpose and Lifecycle Handlers
19
20
  from .generic_event_handler import GenericEventHandler
@@ -31,6 +32,7 @@ __all__ = [
31
32
  "ToolResultEventHandler",
32
33
  "ApprovedToolInvocationEventHandler",
33
34
  "ToolExecutionApprovalEventHandler",
35
+ "BootstrapEventHandler",
34
36
  "GenericEventHandler",
35
37
  "LifecycleEventLogger",
36
38
  ]
@@ -1,12 +1,13 @@
1
1
  # file: autobyteus/autobyteus/agent/handlers/approved_tool_invocation_event_handler.py
2
2
  import logging
3
- import json
3
+
4
4
  import traceback
5
5
  from typing import TYPE_CHECKING, Optional
6
6
 
7
7
  from autobyteus.agent.handlers.base_event_handler import AgentEventHandler
8
8
  from autobyteus.agent.events import ApprovedToolInvocationEvent, ToolResultEvent
9
9
  from autobyteus.agent.tool_invocation import ToolInvocation
10
+ from autobyteus.utils.llm_output_formatter import format_to_clean_string
10
11
 
11
12
  if TYPE_CHECKING:
12
13
  from autobyteus.agent.context import AgentContext
@@ -38,18 +39,38 @@ class ApprovedToolInvocationEventHandler(AgentEventHandler):
38
39
  agent_id = context.agent_id
39
40
 
40
41
  notifier: Optional['AgentExternalEventNotifier'] = None
41
- if context.phase_manager:
42
- notifier = context.phase_manager.notifier
42
+ if context.status_manager:
43
+ notifier = context.status_manager.notifier
43
44
 
44
45
  if not notifier: # pragma: no cover
45
46
  logger.error(f"Agent '{agent_id}': Notifier not available in ApprovedToolInvocationEventHandler. Tool interaction logs will not be emitted.")
46
47
 
47
48
  logger.info(f"Agent '{agent_id}' handling ApprovedToolInvocationEvent for tool: '{tool_name}' (ID: {invocation_id}) with args: {arguments}")
48
49
 
49
- try:
50
- args_str = json.dumps(arguments)
51
- except TypeError: # pragma: no cover
52
- args_str = str(arguments)
50
+ # Run tool invocation preprocessors before execution
51
+ processors = context.config.tool_invocation_preprocessors
52
+ if processors:
53
+ sorted_processors = sorted(processors, key=lambda p: p.get_order())
54
+ for processor in sorted_processors:
55
+ try:
56
+ tool_invocation = await processor.process(tool_invocation, context)
57
+ tool_name = tool_invocation.name
58
+ arguments = tool_invocation.arguments
59
+ invocation_id = tool_invocation.id
60
+ except Exception as e:
61
+ error_message = f"Error in tool invocation preprocessor '{processor.get_name()}' for tool '{tool_name}': {e}"
62
+ logger.error(f"Agent '{agent_id}': {error_message}", exc_info=True)
63
+ result_event = ToolResultEvent(
64
+ tool_name=tool_name,
65
+ result=None,
66
+ error=error_message,
67
+ tool_invocation_id=invocation_id,
68
+ turn_id=tool_invocation.turn_id,
69
+ )
70
+ await context.input_event_queues.enqueue_tool_result(result_event)
71
+ return
72
+
73
+ args_str = format_to_clean_string(arguments)
53
74
  log_msg_call = f"[APPROVED_TOOL_CALL] Agent_ID: {agent_id}, Tool: {tool_name}, Invocation_ID: {invocation_id}, Arguments: {args_str}"
54
75
 
55
76
  if notifier:
@@ -69,13 +90,13 @@ class ApprovedToolInvocationEventHandler(AgentEventHandler):
69
90
  if not tool_instance:
70
91
  error_message = f"Tool '{tool_name}' not found or configured for agent '{agent_id}'."
71
92
  logger.error(error_message)
72
- result_event = ToolResultEvent(tool_name=tool_name, result=None, error=error_message, tool_invocation_id=invocation_id)
73
- context.add_message_to_history({
74
- "role": "tool",
75
- "tool_call_id": invocation_id,
76
- "name": tool_name,
77
- "content": f"Error: Approved tool '{tool_name}' execution failed. Reason: {error_message}",
78
- })
93
+ result_event = ToolResultEvent(
94
+ tool_name=tool_name,
95
+ result=None,
96
+ error=error_message,
97
+ tool_invocation_id=invocation_id,
98
+ turn_id=tool_invocation.turn_id,
99
+ )
79
100
  log_msg_error = f"[APPROVED_TOOL_ERROR] {error_message}"
80
101
  if notifier:
81
102
  try:
@@ -94,21 +115,17 @@ class ApprovedToolInvocationEventHandler(AgentEventHandler):
94
115
  logger.debug(f"Executing approved tool '{tool_name}' for agent '{agent_id}'. Invocation ID: {invocation_id}")
95
116
  execution_result = await tool_instance.execute(context=context, **arguments)
96
117
 
97
- try:
98
- result_json_for_log = json.dumps(execution_result)
99
- except (TypeError, ValueError):
100
- result_json_for_log = json.dumps(str(execution_result))
118
+ result_json_for_log = format_to_clean_string(execution_result)
101
119
 
102
120
  logger.info(f"Approved tool '{tool_name}' (ID: {invocation_id}) executed successfully by agent '{agent_id}'.")
103
- result_event = ToolResultEvent(tool_name=tool_name, result=execution_result, error=None, tool_invocation_id=invocation_id)
104
-
105
- history_content = str(execution_result)
106
- context.add_message_to_history({
107
- "role": "tool",
108
- "tool_call_id": invocation_id,
109
- "name": tool_name,
110
- "content": history_content,
111
- })
121
+ result_event = ToolResultEvent(
122
+ tool_name=tool_name,
123
+ result=execution_result,
124
+ error=None,
125
+ tool_invocation_id=invocation_id,
126
+ tool_args=arguments,
127
+ turn_id=tool_invocation.turn_id,
128
+ )
112
129
  log_msg_result = f"[APPROVED_TOOL_RESULT] {result_json_for_log}"
113
130
  if notifier:
114
131
  try:
@@ -122,13 +139,13 @@ class ApprovedToolInvocationEventHandler(AgentEventHandler):
122
139
  error_message = f"Error executing approved tool '{tool_name}' (ID: {invocation_id}): {str(e)}"
123
140
  error_details = traceback.format_exc()
124
141
  logger.error(f"Agent '{agent_id}' {error_message}", exc_info=True)
125
- result_event = ToolResultEvent(tool_name=tool_name, result=None, error=error_message, tool_invocation_id=invocation_id)
126
- context.add_message_to_history({
127
- "role": "tool",
128
- "tool_call_id": invocation_id,
129
- "name": tool_name,
130
- "content": f"Error: Approved tool '{tool_name}' execution failed. Reason: {error_message}",
131
- })
142
+ result_event = ToolResultEvent(
143
+ tool_name=tool_name,
144
+ result=None,
145
+ error=error_message,
146
+ tool_invocation_id=invocation_id,
147
+ turn_id=tool_invocation.turn_id,
148
+ )
132
149
  log_msg_exception = f"[APPROVED_TOOL_EXCEPTION] {error_message}\nDetails:\n{error_details}"
133
150
  if notifier:
134
151
  try:
@@ -0,0 +1,155 @@
1
+ # file: autobyteus/autobyteus/agent/handlers/bootstrap_event_handler.py
2
+ import logging
3
+ from typing import List, Optional, TYPE_CHECKING
4
+
5
+ from autobyteus.agent.bootstrap_steps.agent_bootstrapper import AgentBootstrapper
6
+ from autobyteus.agent.bootstrap_steps.base_bootstrap_step import BaseBootstrapStep
7
+ from autobyteus.agent.events import (
8
+ AgentErrorEvent,
9
+ AgentReadyEvent,
10
+ BootstrapStartedEvent,
11
+ BootstrapStepRequestedEvent,
12
+ BootstrapStepCompletedEvent,
13
+ BootstrapCompletedEvent,
14
+ )
15
+ from autobyteus.agent.handlers.base_event_handler import AgentEventHandler
16
+
17
+ if TYPE_CHECKING:
18
+ from autobyteus.agent.context import AgentContext
19
+
20
+ logger = logging.getLogger(__name__)
21
+
22
+ _BOOTSTRAP_STEPS_KEY = "_bootstrap_steps"
23
+
24
+
25
+ class BootstrapEventHandler(AgentEventHandler):
26
+ """
27
+ Orchestrates the agent bootstrap sequence using internal lifecycle events.
28
+ """
29
+
30
+ def __init__(self, steps: Optional[List[BaseBootstrapStep]] = None) -> None:
31
+ self._bootstrapper = AgentBootstrapper(steps=steps)
32
+
33
+ async def handle(self, event: object, context: 'AgentContext') -> None:
34
+ if isinstance(event, BootstrapStartedEvent):
35
+ await self._handle_bootstrap_started(context)
36
+ return
37
+
38
+ if isinstance(event, BootstrapStepRequestedEvent):
39
+ await self._handle_bootstrap_step_requested(event, context)
40
+ return
41
+
42
+ if isinstance(event, BootstrapStepCompletedEvent):
43
+ await self._handle_bootstrap_step_completed(event, context)
44
+ return
45
+
46
+ if isinstance(event, BootstrapCompletedEvent):
47
+ await self._handle_bootstrap_completed(event, context)
48
+ return
49
+
50
+ logger.warning(f"BootstrapEventHandler received unexpected event type: {type(event).__name__}")
51
+
52
+ async def _handle_bootstrap_started(self, context: 'AgentContext') -> None:
53
+ steps = list(self._bootstrapper.bootstrap_steps)
54
+ context.state.custom_data[_BOOTSTRAP_STEPS_KEY] = steps
55
+
56
+ if not steps:
57
+ logger.info(f"Agent '{context.agent_id}': No bootstrap steps configured. Marking bootstrap complete.")
58
+ await context.input_event_queues.enqueue_internal_system_event(
59
+ BootstrapCompletedEvent(success=True)
60
+ )
61
+ return
62
+
63
+ logger.info(f"Agent '{context.agent_id}': Bootstrap started with {len(steps)} steps.")
64
+ await context.input_event_queues.enqueue_internal_system_event(
65
+ BootstrapStepRequestedEvent(step_index=0)
66
+ )
67
+
68
+ async def _handle_bootstrap_step_requested(self, event: BootstrapStepRequestedEvent, context: 'AgentContext') -> None:
69
+ steps: Optional[List[BaseBootstrapStep]] = context.state.custom_data.get(_BOOTSTRAP_STEPS_KEY)
70
+ if not steps:
71
+ error_message = "Bootstrap steps list missing from context during step request."
72
+ logger.error(f"Agent '{context.agent_id}': {error_message}")
73
+ await self._notify_bootstrap_error(context, error_message)
74
+ await context.input_event_queues.enqueue_internal_system_event(
75
+ BootstrapCompletedEvent(success=False, error_message=error_message)
76
+ )
77
+ return
78
+
79
+ step_index = event.step_index
80
+ if step_index < 0 or step_index >= len(steps):
81
+ error_message = f"Invalid bootstrap step index {step_index}."
82
+ logger.error(f"Agent '{context.agent_id}': {error_message}")
83
+ await self._notify_bootstrap_error(context, error_message)
84
+ await context.input_event_queues.enqueue_internal_system_event(
85
+ BootstrapCompletedEvent(success=False, error_message=error_message)
86
+ )
87
+ return
88
+
89
+ step = steps[step_index]
90
+ step_name = step.__class__.__name__
91
+ logger.debug(f"Agent '{context.agent_id}': Executing bootstrap step {step_index + 1}/{len(steps)}: {step_name}")
92
+
93
+ try:
94
+ success = await step.execute(context)
95
+ except Exception as e: # pragma: no cover
96
+ error_message = f"Exception during bootstrap step '{step_name}': {e}"
97
+ logger.error(f"Agent '{context.agent_id}': {error_message}", exc_info=True)
98
+ success = False
99
+ if not success:
100
+ error_message = f"Bootstrap step '{step_name}' failed."
101
+ await self._notify_bootstrap_error(context, error_message)
102
+
103
+ await context.input_event_queues.enqueue_internal_system_event(
104
+ BootstrapStepCompletedEvent(
105
+ step_index=step_index,
106
+ step_name=step_name,
107
+ success=success,
108
+ error_message=None if success else f"Step '{step_name}' failed",
109
+ )
110
+ )
111
+
112
+ async def _handle_bootstrap_step_completed(self, event: BootstrapStepCompletedEvent, context: 'AgentContext') -> None:
113
+ if not event.success:
114
+ await context.input_event_queues.enqueue_internal_system_event(
115
+ BootstrapCompletedEvent(success=False, error_message=event.error_message)
116
+ )
117
+ return
118
+
119
+ steps: Optional[List[BaseBootstrapStep]] = context.state.custom_data.get(_BOOTSTRAP_STEPS_KEY)
120
+ if not steps:
121
+ error_message = "Bootstrap steps list missing during step completion."
122
+ logger.error(f"Agent '{context.agent_id}': {error_message}")
123
+ await self._notify_bootstrap_error(context, error_message)
124
+ await context.input_event_queues.enqueue_internal_system_event(
125
+ BootstrapCompletedEvent(success=False, error_message=error_message)
126
+ )
127
+ return
128
+
129
+ next_index = event.step_index + 1
130
+ if next_index < len(steps):
131
+ await context.input_event_queues.enqueue_internal_system_event(
132
+ BootstrapStepRequestedEvent(step_index=next_index)
133
+ )
134
+ return
135
+
136
+ await context.input_event_queues.enqueue_internal_system_event(
137
+ BootstrapCompletedEvent(success=True)
138
+ )
139
+
140
+ async def _handle_bootstrap_completed(self, event: BootstrapCompletedEvent, context: 'AgentContext') -> None:
141
+ if not event.success:
142
+ logger.error(
143
+ f"Agent '{context.agent_id}': Bootstrap completed with failure. "
144
+ f"Error: {event.error_message}"
145
+ )
146
+ await self._notify_bootstrap_error(context, event.error_message or "Bootstrap failed.")
147
+ return
148
+
149
+ logger.info(f"Agent '{context.agent_id}': Bootstrap completed successfully. Emitting AgentReadyEvent.")
150
+ await context.input_event_queues.enqueue_internal_system_event(AgentReadyEvent())
151
+
152
+ async def _notify_bootstrap_error(self, context: 'AgentContext', error_message: str) -> None:
153
+ await context.input_event_queues.enqueue_internal_system_event(
154
+ AgentErrorEvent(error_message=error_message, exception_details=error_message)
155
+ )
@@ -48,6 +48,16 @@ class InterAgentMessageReceivedEventHandler(AgentEventHandler):
48
48
  f"'{inter_agent_msg.sender_agent_id}', type '{inter_agent_msg.message_type.value}'. "
49
49
  f"Content: '{inter_agent_msg.content}'"
50
50
  )
51
+
52
+ # Surface this inter-agent message to external subscribers (UI, etc.)
53
+ if context.status_manager and context.status_manager.notifier:
54
+ notifier: 'AgentExternalEventNotifier' = context.status_manager.notifier
55
+ notifier.notify_agent_data_inter_agent_message_received({
56
+ "sender_agent_id": inter_agent_msg.sender_agent_id,
57
+ "recipient_role_name": inter_agent_msg.recipient_role_name,
58
+ "content": inter_agent_msg.content,
59
+ "message_type": inter_agent_msg.message_type.value,
60
+ })
51
61
 
52
62
  content_for_llm = (
53
63
  f"You have received a message from another agent.\n"