autobyteus 1.0.4__tar.gz → 1.0.6__tar.gz

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 (165) hide show
  1. {autobyteus-1.0.4 → autobyteus-1.0.6}/PKG-INFO +2 -2
  2. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/agent.py +1 -1
  3. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/message/send_message_to.py +0 -3
  4. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/autobyteus_provider.py +2 -1
  5. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/llm_factory.py +33 -13
  6. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/models.py +12 -0
  7. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/ollama_provider.py +1 -0
  8. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/ask_user_input.py +8 -19
  9. autobyteus-1.0.6/autobyteus/tools/base_tool.py +77 -0
  10. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/bash/bash_executor.py +3 -15
  11. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/browser_session_aware_navigate_to.py +8 -4
  12. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/browser_session_aware_web_element_trigger.py +12 -55
  13. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/browser_session_aware_webpage_reader.py +9 -5
  14. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/browser_session_aware_webpage_screenshot_taker.py +8 -4
  15. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/google_search_ui.py +6 -32
  16. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/navigate_to.py +8 -16
  17. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/webpage_image_downloader.py +9 -60
  18. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/webpage_reader.py +8 -6
  19. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/webpage_screenshot_taker.py +9 -6
  20. autobyteus-1.0.6/autobyteus/tools/factory/tool_factory.py +10 -0
  21. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/file/file_reader.py +6 -8
  22. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/file/file_writer.py +6 -9
  23. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/image_downloader.py +18 -41
  24. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/pdf_downloader.py +8 -13
  25. autobyteus-1.0.6/autobyteus/tools/registry/__init__.py +11 -0
  26. autobyteus-1.0.6/autobyteus/tools/registry/tool_definition.py +60 -0
  27. autobyteus-1.0.6/autobyteus/tools/registry/tool_registry.py +106 -0
  28. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/timer.py +16 -18
  29. autobyteus-1.0.6/autobyteus/tools/tool_meta.py +52 -0
  30. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/utils.py +1 -1
  31. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/web_page_pdf_generator.py +8 -4
  32. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus.egg-info/PKG-INFO +2 -2
  33. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus.egg-info/SOURCES.txt +4 -0
  34. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus.egg-info/requires.txt +1 -1
  35. {autobyteus-1.0.4 → autobyteus-1.0.6}/setup.py +2 -2
  36. autobyteus-1.0.4/autobyteus/tools/base_tool.py +0 -49
  37. autobyteus-1.0.4/autobyteus/tools/factory/tool_factory.py +0 -8
  38. {autobyteus-1.0.4 → autobyteus-1.0.6}/LICENSE +0 -0
  39. {autobyteus-1.0.4 → autobyteus-1.0.6}/README.md +0 -0
  40. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/__init__.py +0 -0
  41. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/__init__.py +0 -0
  42. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/async_agent.py +0 -0
  43. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/async_group_aware_agent.py +0 -0
  44. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/exceptions.py +0 -0
  45. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/factory/__init__.py +0 -0
  46. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/group/__init__.py +0 -0
  47. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/group/async_group_aware_agent.py +0 -0
  48. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/group/coordinator_agent.py +0 -0
  49. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/group/group_aware_agent.py +0 -0
  50. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/message/__init__.py +0 -0
  51. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/message/message.py +0 -0
  52. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/message/message_types.py +0 -0
  53. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/orchestrator/__init__.py +0 -0
  54. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/orchestrator/base_agent_orchestrator.py +0 -0
  55. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/orchestrator/multi_replica_agent_orchestrator.py +0 -0
  56. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/orchestrator/single_replica_agent_orchestrator.py +0 -0
  57. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/response_parser/__init__.py +0 -0
  58. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/response_parser/tool_usage_command_parser.py +0 -0
  59. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/status.py +0 -0
  60. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/agent/tool_invocation.py +0 -0
  61. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/check_requirements.py +0 -0
  62. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/conversation/__init__.py +0 -0
  63. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/conversation/conversation.py +0 -0
  64. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/conversation/user_message.py +0 -0
  65. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/events/__init__.py +0 -0
  66. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/events/decorators.py +0 -0
  67. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/events/event_emitter.py +0 -0
  68. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/events/event_manager.py +0 -0
  69. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/events/event_types.py +0 -0
  70. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/__init__.py +0 -0
  71. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/__init__.py +0 -0
  72. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/autobyteus_llm.py +0 -0
  73. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/bedrock_llm.py +0 -0
  74. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/claude_llm.py +0 -0
  75. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/deepseek_llm.py +0 -0
  76. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/gemini_llm.py +0 -0
  77. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/grok_llm.py +0 -0
  78. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/groq_llm.py +0 -0
  79. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/mistral_llm.py +0 -0
  80. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/nvidia_llm.py +0 -0
  81. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/ollama_llm.py +0 -0
  82. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/api/openai_llm.py +0 -0
  83. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/base_llm.py +0 -0
  84. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/extensions/__init__.py +0 -0
  85. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/extensions/base_extension.py +0 -0
  86. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/extensions/extension_registry.py +0 -0
  87. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/extensions/token_usage_tracking_extension.py +0 -0
  88. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/providers.py +0 -0
  89. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/__init__.py +0 -0
  90. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/base_token_counter.py +0 -0
  91. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/claude_token_counter.py +0 -0
  92. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/deepseek_token_counter.py +0 -0
  93. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/mistral_token_counter.py +0 -0
  94. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/openai_token_counter.py +0 -0
  95. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/token_counter/token_counter_factory.py +0 -0
  96. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/__init__.py +0 -0
  97. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/image_payload_formatter.py +0 -0
  98. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/llm_config.py +0 -0
  99. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/messages.py +0 -0
  100. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/rate_limiter.py +0 -0
  101. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/response_types.py +0 -0
  102. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/token_pricing_config.py +0 -0
  103. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/token_usage.py +0 -0
  104. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/llm/utils/token_usage_tracker.py +0 -0
  105. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/person/__init__.py +0 -0
  106. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/person/examples/__init__.py +0 -0
  107. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/person/examples/sample_persons.py +0 -0
  108. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/person/examples/sample_roles.py +0 -0
  109. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/person/person.py +0 -0
  110. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/person/role.py +0 -0
  111. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/__init__.py +0 -0
  112. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/prompt_builder.py +0 -0
  113. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/prompt_template.py +0 -0
  114. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/prompt_version_manager.py +0 -0
  115. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/storage/__init__.py +0 -0
  116. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/storage/prompt_version_model.py +0 -0
  117. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/prompt/storage/prompt_version_repository.py +0 -0
  118. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/__init__.py +0 -0
  119. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/bash/__init__.py +0 -0
  120. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/bash/factory/__init__.py +0 -0
  121. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/bash/factory/bash_executor_factory.py +0 -0
  122. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/__init__.py +0 -0
  123. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/__init__.py +0 -0
  124. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/browser_session_aware_tool.py +0 -0
  125. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/factory/__init__.py +0 -0
  126. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/factory/browser_session_aware_web_element_trigger_factory.py +0 -0
  127. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/factory/browser_session_aware_webpage_reader_factory.py +0 -0
  128. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/factory/browser_session_aware_webpage_screenshot_taker_factory.py +0 -0
  129. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/shared_browser_session.py +0 -0
  130. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/shared_browser_session_manager.py +0 -0
  131. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/session_aware/web_element_action.py +0 -0
  132. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/__init__.py +0 -0
  133. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/factory/__init__.py +0 -0
  134. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/factory/google_search_factory.py +0 -0
  135. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/factory/webpage_reader_factory.py +0 -0
  136. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/browser/standalone/factory/webpage_screenshot_taker_factory.py +0 -0
  137. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/factory/__init__.py +0 -0
  138. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/factory/ask_user_input_factory.py +0 -0
  139. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/factory/image_downloader_factory.py +0 -0
  140. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/factory/pdf_downloader_factory.py +0 -0
  141. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/factory/webpage_image_downloader_factory.py +0 -0
  142. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/file/__init__.py +0 -0
  143. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/file/factory/__init__.py +0 -0
  144. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/file/factory/file_reader_factory.py +0 -0
  145. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/file/factory/file_writer_factory.py +0 -0
  146. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/handlers/__init__.py +0 -0
  147. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/handlers/shell_handler.py +0 -0
  148. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/operation/__init__.py +0 -0
  149. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/operation/file_operation.py +0 -0
  150. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/operation/file_rename_operation.py +0 -0
  151. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/operation/operation.py +0 -0
  152. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/tools/operation/shell_operation.py +0 -0
  153. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/utils/__init__.py +0 -0
  154. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/utils/dynamic_enum.py +0 -0
  155. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/utils/file_utils.py +0 -0
  156. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/utils/html_cleaner.py +0 -0
  157. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/utils/singleton.py +0 -0
  158. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/workflow/__init__.py +0 -0
  159. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/workflow/simple_task.py +0 -0
  160. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/workflow/task.py +0 -0
  161. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus/workflow/workflow.py +0 -0
  162. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus.egg-info/dependency_links.txt +0 -0
  163. {autobyteus-1.0.4 → autobyteus-1.0.6}/autobyteus.egg-info/top_level.txt +0 -0
  164. {autobyteus-1.0.4 → autobyteus-1.0.6}/pyproject.toml +0 -0
  165. {autobyteus-1.0.4 → autobyteus-1.0.6}/setup.cfg +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: autobyteus
3
- Version: 1.0.4
3
+ Version: 1.0.6
4
4
  Summary: Multi-Agent framework
5
5
  Home-page: https://github.com/AutoByteus/autobyteus
6
6
  Author: Ryan Zheng
@@ -28,7 +28,7 @@ Requires-Dist: Jinja2
28
28
  Requires-Dist: ollama==0.4.5
29
29
  Requires-Dist: mistral_common
30
30
  Requires-Dist: aiohttp
31
- Requires-Dist: autobyteus-llm-client==1.0.9
31
+ Requires-Dist: autobyteus-llm-client==1.1.0
32
32
  Requires-Dist: brui-core==1.0.8
33
33
  Provides-Extra: dev
34
34
  Requires-Dist: coverage; extra == "dev"
@@ -223,7 +223,7 @@ class Agent(EventEmitter):
223
223
 
224
224
  external_tools_section = ""
225
225
  for i, tool in enumerate(self.tools):
226
- external_tools_section += f" {i + 1} {tool.tool_usage_xml()}\n\n"
226
+ external_tools_section += f" {i + 1} {tool.tool_usage()}\n\n"
227
227
  return external_tools_section.strip()
228
228
 
229
229
  def on_task_completed(self, *args, **kwargs):
@@ -18,9 +18,6 @@ class SendMessageTo(BaseTool):
18
18
  except ValueError as e:
19
19
  return f"Error: {str(e)}"
20
20
 
21
- def tool_usage(self) -> str:
22
- return self.tool_usage_xml()
23
-
24
21
  def tool_usage_xml(self) -> str:
25
22
  return '''SendMessageTo: Sends a message to another agent in the group. Usage:
26
23
  <command name="SendMessageTo">
@@ -56,12 +56,13 @@ class AutobyteusModelProvider:
56
56
  value=model_info["value"],
57
57
  provider=LLMProvider(model_info["provider"]), # Convert string to enum
58
58
  llm_class=AutobyteusLLM,
59
+ canonical_name=model_info["canonical_name"], # Add canonical_name
59
60
  default_config=llm_config
60
61
  )
61
62
 
62
63
  LLMFactory.register_model(llm_model)
63
64
  registered_count += 1
64
- logger.debug(f"Registered model: {model_info['name']}")
65
+ logger.debug(f"Registered model: {model_info['name']} with canonical name: {model_info['canonical_name']}")
65
66
 
66
67
  except Exception as e:
67
68
  logger.error(f"Model registration failed: {str(e)}")
@@ -98,6 +98,7 @@ class LLMFactory:
98
98
  value="gpt-4o",
99
99
  provider=LLMProvider.OPENAI,
100
100
  llm_class=OpenAILLM,
101
+ canonical_name="gpt-4o",
101
102
  default_config=LLMConfig(
102
103
  rate_limit=40,
103
104
  token_limit=8192,
@@ -105,38 +106,32 @@ class LLMFactory:
105
106
  )
106
107
  ),
107
108
  LLMModel(
108
- name="o1_API",
109
- value="o1",
109
+ name="o3_API",
110
+ value="o3",
110
111
  provider=LLMProvider.OPENAI,
111
112
  llm_class=OpenAILLM,
113
+ canonical_name="o3",
112
114
  default_config=LLMConfig(
113
115
  pricing_config=TokenPricingConfig(15.00, 60.00)
114
116
  )
115
117
  ),
116
118
  LLMModel(
117
- name="o1_MINI_API",
118
- value="o3-mini",
119
+ name="o4_MINI_API",
120
+ value="o4-mini",
119
121
  provider=LLMProvider.OPENAI,
120
122
  llm_class=OpenAILLM,
123
+ canonical_name="o4-mini",
121
124
  default_config=LLMConfig(
122
125
  pricing_config=TokenPricingConfig(1.0, 4.00)
123
126
  )
124
127
  ),
125
- LLMModel(
126
- name="GPT_3_5_TURBO_API",
127
- value="gpt-3.5-turbo",
128
- provider=LLMProvider.OPENAI,
129
- llm_class=OpenAILLM,
130
- default_config=LLMConfig(
131
- pricing_config=TokenPricingConfig(1.50, 2.00)
132
- )
133
- ),
134
128
  # MISTRAL Provider Models
135
129
  LLMModel(
136
130
  name="MISTRAL_LARGE_API",
137
131
  value="mistral-large-latest",
138
132
  provider=LLMProvider.MISTRAL,
139
133
  llm_class=MistralLLM,
134
+ canonical_name="mistral-large",
140
135
  default_config=LLMConfig(
141
136
  pricing_config=TokenPricingConfig(2.00, 6.00)
142
137
  )
@@ -147,6 +142,7 @@ class LLMFactory:
147
142
  value="claude-3-7-sonnet-20250219",
148
143
  provider=LLMProvider.ANTHROPIC,
149
144
  llm_class=ClaudeLLM,
145
+ canonical_name="claude-3.7",
150
146
  default_config=LLMConfig(
151
147
  pricing_config=TokenPricingConfig(3.00, 15.00)
152
148
  )
@@ -156,6 +152,7 @@ class LLMFactory:
156
152
  value="anthropic.claude-3-7-sonnet-20250219-v1:0",
157
153
  provider=LLMProvider.ANTHROPIC,
158
154
  llm_class=ClaudeLLM,
155
+ canonical_name="claude-3.7",
159
156
  default_config=LLMConfig(
160
157
  pricing_config=TokenPricingConfig(3.00, 15.00)
161
158
  )
@@ -166,6 +163,7 @@ class LLMFactory:
166
163
  value="deepseek-chat",
167
164
  provider=LLMProvider.DEEPSEEK,
168
165
  llm_class=DeepSeekLLM,
166
+ canonical_name="deepseek-chat",
169
167
  default_config=LLMConfig(
170
168
  rate_limit=60,
171
169
  token_limit=8000,
@@ -178,6 +176,7 @@ class LLMFactory:
178
176
  value="deepseek-reasoner",
179
177
  provider=LLMProvider.DEEPSEEK,
180
178
  llm_class=DeepSeekLLM,
179
+ canonical_name="deepseek-reasoner",
181
180
  default_config=LLMConfig(
182
181
  rate_limit=60,
183
182
  token_limit=8000,
@@ -190,6 +189,7 @@ class LLMFactory:
190
189
  value="gemini-1-5-pro",
191
190
  provider=LLMProvider.GEMINI,
192
191
  llm_class=OpenAILLM,
192
+ canonical_name="gemini-1.5-pro",
193
193
  default_config=LLMConfig(
194
194
  pricing_config=TokenPricingConfig(1.25, 5.00)
195
195
  )
@@ -199,6 +199,7 @@ class LLMFactory:
199
199
  value="gemini-1-5-flash",
200
200
  provider=LLMProvider.GEMINI,
201
201
  llm_class=OpenAILLM,
202
+ canonical_name="gemini-1.5-flash",
202
203
  default_config=LLMConfig(
203
204
  pricing_config=TokenPricingConfig(0.075, 0.30)
204
205
  )
@@ -209,6 +210,7 @@ class LLMFactory:
209
210
  value="grok-2-1212",
210
211
  provider=LLMProvider.GROK,
211
212
  llm_class=GrokLLM,
213
+ canonical_name="grok-2",
212
214
  default_config=LLMConfig(
213
215
  rate_limit=60,
214
216
  token_limit=8000,
@@ -290,3 +292,21 @@ class LLMFactory:
290
292
  """
291
293
  LLMFactory.ensure_initialized()
292
294
  return LLMFactory._models_by_provider.get(provider, [])
295
+
296
+ @staticmethod
297
+ def get_canonical_name(model_name: str) -> Optional[str]:
298
+ """
299
+ Get the canonical name for a model by its name.
300
+
301
+ Args:
302
+ model_name (str): The model name (e.g., "GPT_4o_API")
303
+
304
+ Returns:
305
+ Optional[str]: The canonical name if found, None otherwise
306
+ """
307
+ LLMFactory.ensure_initialized()
308
+ for models in LLMFactory._models_by_provider.values():
309
+ for model_instance in models:
310
+ if model_instance.name == model_name:
311
+ return model_instance.canonical_name
312
+ return None
@@ -13,6 +13,7 @@ class LLMModel:
13
13
  Represents a single model's metadata:
14
14
  - name (str): A human-readable label, e.g. "GPT-4 Official"
15
15
  - value (str): A unique identifier used in code or APIs, e.g. "gpt-4o"
16
+ - canonical_name (str): A shorter, standardized reference name for prompts, e.g. "gpt-4o" or "claude-3.7"
16
17
  - provider (LLMProvider): The provider enum
17
18
  - llm_class (Type[BaseLLM]): Which Python class to instantiate
18
19
  - default_config (LLMConfig): Default configuration (token limit, etc.)
@@ -26,6 +27,7 @@ class LLMModel:
26
27
  value: str,
27
28
  provider: LLMProvider,
28
29
  llm_class: Type["BaseLLM"],
30
+ canonical_name: str,
29
31
  default_config: Optional[LLMConfig] = None
30
32
  ):
31
33
  # Validate name doesn't already exist as a class attribute
@@ -36,6 +38,7 @@ class LLMModel:
36
38
 
37
39
  self._name = name
38
40
  self._value = value
41
+ self._canonical_name = canonical_name
39
42
  self.provider = provider
40
43
  self.llm_class = llm_class
41
44
  self.default_config = default_config if default_config else LLMConfig()
@@ -58,6 +61,14 @@ class LLMModel:
58
61
  """
59
62
  return self._value
60
63
 
64
+ @property
65
+ def canonical_name(self) -> str:
66
+ """
67
+ A standardized, shorter reference name for this model.
68
+ Useful for prompt engineering and cross-referencing similar models.
69
+ """
70
+ return self._canonical_name
71
+
61
72
  def create_llm(self, custom_config: Optional[LLMConfig] = None) -> "BaseLLM":
62
73
  """
63
74
  Instantiate the LLM class for this model, applying
@@ -69,5 +80,6 @@ class LLMModel:
69
80
  def __repr__(self):
70
81
  return (
71
82
  f"LLMModel(name='{self._name}', value='{self._value}', "
83
+ f"canonical_name='{self._canonical_name}', "
72
84
  f"provider='{self.provider.name}', llm_class='{self.llm_class.__name__}')"
73
85
  )
@@ -79,6 +79,7 @@ class OllamaModelProvider:
79
79
  value=model_name,
80
80
  provider=LLMProvider.OLLAMA,
81
81
  llm_class=OllamaLLM,
82
+ canonical_name=model_name, # Use model_name as the canonical_name
82
83
  default_config=LLMConfig(
83
84
  rate_limit=60,
84
85
  token_limit=8192,
@@ -12,27 +12,16 @@ class AskUserInput(BaseTool):
12
12
  super().__init__()
13
13
  self.logger = logging.getLogger(__name__)
14
14
 
15
- def tool_usage(self):
15
+ @classmethod
16
+ def tool_usage_xml(cls):
16
17
  """
17
- Return a string describing the usage of the AskUserInput tool.
18
+ Return an XML string describing the usage of the AskUserInput tool.
19
+
20
+ Returns:
21
+ str: An XML description of how to use the AskUserInput tool.
18
22
  """
19
- return '''AskUserInput: Requests input from the user based on LLM's prompt.
20
- Usage: <<<AskUserInput(request="[Your request here]")>>>
21
-
22
- Examples:
23
- 1. When needing to request user for search input:
24
- <<<AskUserInput(request="What would you like to search for?")>>>
25
-
26
- 2. When needing to request user for form input:
27
- <<<AskUserInput(request="Please enter your full name:")>>>
28
-
29
- 3. When needing to request user for a choice:
30
- <<<AskUserInput(request="Select an option (1, 2, or 3):")>>>
31
- '''
32
-
33
- def tool_usage_xml(self):
34
23
  return '''AskUserInput: Requests input from the user based on a given context or prompt.
35
- <command name="AskUserInput"
24
+ <command name="AskUserInput">
36
25
  <arg name="request">[Your request here]</arg>
37
26
  </command>
38
27
 
@@ -90,4 +79,4 @@ class AskUserInput(BaseTool):
90
79
  except Exception as e:
91
80
  error_message = f"An error occurred while getting user input: {str(e)}"
92
81
  self.logger.error(error_message)
93
- return f"[Error: {error_message}]"
82
+ return f"[Error: {error_message}]"
@@ -0,0 +1,77 @@
1
+ # File: autobyteus/tools/base_tool.py
2
+
3
+ import logging
4
+ from abc import ABC, abstractmethod
5
+ from typing import Optional, Any
6
+
7
+ from autobyteus.events.event_emitter import EventEmitter
8
+ from autobyteus.events.event_types import EventType
9
+
10
+ from .tool_meta import ToolMeta
11
+
12
+ logger = logging.getLogger('autobyteus')
13
+
14
+ class BaseTool(ABC, EventEmitter, metaclass=ToolMeta):
15
+ """
16
+ Abstract base class for all tools, with auto-registration via ToolMeta.
17
+
18
+ Subclasses inherit a default `get_name` (the class name) and MUST implement
19
+ the abstract class method `tool_usage_xml`, and the abstract instance
20
+ method `_execute`.
21
+ """
22
+ def __init__(self):
23
+ super().__init__()
24
+ self.agent_id: Optional[str] = None
25
+ logger.debug(f"BaseTool instance initializing for potential class {self.__class__.__name__}")
26
+
27
+ @classmethod
28
+ def get_name(cls) -> str:
29
+ """
30
+ Return the name of the tool. Defaults to the class name.
31
+ Can be overridden by child classes if a different registration name is needed.
32
+ """
33
+ return cls.__name__
34
+
35
+ @classmethod
36
+ def tool_usage_xml(cls) -> str:
37
+ """
38
+ Return the static usage description string for the tool in XML format.
39
+ Must be implemented by subclasses.
40
+ """
41
+ pass
42
+
43
+ def set_agent_id(self, agent_id: str):
44
+ """Sets the ID of the agent using this tool instance."""
45
+ self.agent_id = agent_id
46
+ logger.debug(f"Agent ID '{agent_id}' set for tool instance '{self.__class__.get_name()}'")
47
+
48
+ async def execute(self, **kwargs):
49
+ """
50
+ Execute the tool's main functionality by calling _execute.
51
+ Argument validation must be handled within _execute.
52
+ """
53
+ tool_name = self.__class__.get_name()
54
+ logger.info(f"Executing tool '{tool_name}' for agent '{self.agent_id}' with args: {kwargs}")
55
+ try:
56
+ result = await self._execute(**kwargs)
57
+ logger.info(f"Tool '{tool_name}' execution completed successfully.")
58
+ return result
59
+ except Exception as e:
60
+ logger.error(f"Tool '{tool_name}' execution failed: {str(e)}", exc_info=True)
61
+ return f"Error executing tool '{tool_name}': {str(e)}"
62
+
63
+ @abstractmethod
64
+ async def _execute(self, **kwargs) -> Any:
65
+ """
66
+ Implement the actual execution logic in subclasses.
67
+ MUST handle own argument validation.
68
+ """
69
+ pass
70
+
71
+ @classmethod
72
+ def tool_usage(cls) -> str:
73
+ """
74
+ Returns the tool's static XML usage description by calling the class method tool_usage_xml.
75
+ This is a convenience class method.
76
+ """
77
+ return cls.tool_usage_xml()
@@ -27,20 +27,8 @@ class BashExecutor(BaseTool):
27
27
  """
28
28
  super().__init__()
29
29
 
30
- def tool_usage(self):
31
- """
32
- Return a string describing the usage of the BashExecutor tool.
33
-
34
- Returns:
35
- str: A description of how to use the BashExecutor tool.
36
- """
37
- return (
38
- 'BashExecutor: Executes bash commands and retrieves their output. '
39
- 'Usage: <<<BashExecutor(command="bash command")>>>, '
40
- 'where "bash command" is a string containing the command to be executed.'
41
- )
42
-
43
- def tool_usage_xml(self):
30
+ @classmethod
31
+ def tool_usage_xml(cls):
44
32
  """
45
33
  Return an XML string describing the usage of the BashExecutor tool.
46
34
 
@@ -100,4 +88,4 @@ class BashExecutor(BaseTool):
100
88
  except Exception as e:
101
89
  logger.exception(f"An error occurred while executing the command: {str(e)}")
102
90
  self.emit(EventType.TOOL_EXECUTION_FAILED, str(e))
103
- raise
91
+ raise
@@ -13,10 +13,14 @@ class BrowserSessionAwareNavigateTo(BrowserSessionAwareTool):
13
13
  def get_name(self) -> str:
14
14
  return "NavigateTo"
15
15
 
16
- def tool_usage(self):
17
- return "NavigateTo: Navigates to a specified website. Usage: <<<NavigateTo(webpage_url='https://example.com')>>>, where 'https://example.com' is the URL of the website to navigate to."
16
+ @classmethod
17
+ def tool_usage_xml(cls):
18
+ """
19
+ Return an XML string describing the usage of the NavigateTo tool.
18
20
 
19
- def tool_usage_xml(self):
21
+ Returns:
22
+ str: An XML description of how to use the NavigateTo tool.
23
+ """
20
24
  return '''
21
25
  NavigateTo: Navigates to a specified website. Usage:
22
26
  <command name="NavigateTo">
@@ -58,4 +62,4 @@ class BrowserSessionAwareNavigateTo(BrowserSessionAwareTool):
58
62
  result = urlparse(url)
59
63
  return all([result.scheme, result.netloc])
60
64
  except ValueError:
61
- return False
65
+ return False
@@ -14,46 +14,14 @@ class BrowserSessionAwareWebElementTrigger(BrowserSessionAwareTool):
14
14
  def get_name(self) -> str:
15
15
  return "WebElementTrigger"
16
16
 
17
- def tool_usage(self):
18
- return """WebElementTrigger: Triggers actions on web elements on web pages, takes a screenshot, and returns the absolute path of the screenshot.
19
- Usage: <<<WebElementTrigger(webpage_url='url', css_selector='selector', action='action', params='<param><name>param_name</name><value>param_value</value></param>')>>>
20
-
21
- Parameters:
22
- - webpage_url: String. URL of the webpage to interact with.
23
- - css_selector: String. CSS selector to find the target element.
24
- - action: String. Type of interaction to perform on the element. Must be one of:
25
- {', '.join(str(action) for action in WebElementAction)}
26
- - params: String. XML-formatted string containing additional parameters for specific actions.
27
-
28
- Common actions and their parameters:
29
- 1. click: No additional params required.
30
- 2. type: Requires 'text' param. Example: <param><name>text</name><value>Hello, World!</value></param>
31
- 3. select: Requires 'option' param. Example: <param><name>option</name><value>option1</value></param>
32
- 4. check: Optional 'state' param (default: true). Example: <param><name>state</name><value>false</value></param>
33
- 5. submit: No additional params required.
34
- 6. hover: No additional params required.
35
- 7. double_click: No additional params required.
36
-
37
- Return Value:
38
- - String: Absolute path to the screenshot taken after the action is performed.
39
- The screenshot is saved in the current working directory with the filename format:
40
- 'screenshot_<action>_<timestamp>.png'
41
-
42
- Examples:
43
- 1. Typing in a search box:
44
- <<<WebElementTrigger(webpage_url='https://example.com', css_selector='#search-input', action='type', params='<param><name>text</name><value>Python tutorial</value></param>')>>>
45
- Returns: '/path/to/screenshot_type_20230615_120530.png'
46
-
47
- 2. Selecting an option from a dropdown:
48
- <<<WebElementTrigger(webpage_url='https://example.com', css_selector='#country-select', action='select', params='<param><name>option</name><value>USA</value></param>')>>>
49
- Returns: '/path/to/screenshot_select_20230615_120545.png'
50
-
51
- 3. Clicking a button:
52
- <<<WebElementTrigger(webpage_url='https://example.com', css_selector='.submit-button', action='click')>>>
53
- Returns: '/path/to/screenshot_click_20230615_120600.png'
54
- """
55
-
56
- def tool_usage_xml(self):
17
+ @classmethod
18
+ def tool_usage_xml(cls):
19
+ """
20
+ Return an XML string describing the usage of the WebElementTrigger tool.
21
+
22
+ Returns:
23
+ str: An XML description of how to use the WebElementTrigger tool.
24
+ """
57
25
  return f'''WebElementTrigger: Triggers actions on web elements on web pages, takes a screenshot, and returns the absolute path of the screenshot.
58
26
  <command name="WebElementTrigger">
59
27
  <arg name="webpage_url">url</arg>
@@ -76,12 +44,9 @@ class BrowserSessionAwareWebElementTrigger(BrowserSessionAwareTool):
76
44
 
77
45
  Common actions and their parameters:
78
46
  1. click: No additional params required.
79
- 2. type: Requires 'text' param.
80
- Example: <param><name>text</name><value>Hello, World!</value></param>
81
- 3. select: Requires 'option' param.
82
- Example: <param><name>option</name><value>option1</value></param>
83
- 4. check: Optional 'state' param (default: true).
84
- Example: <param><name>state</name><value>false</value></param>
47
+ 2. type: Requires 'text' param. Example: <param><name>text</name><value>Hello, World!</value></param>
48
+ 3. select: Requires 'option' param. Example: <param><name>option</name><value>option1</value></param>
49
+ 4. check: Optional 'state' param (default: true). Example: <param><name>state</name><value>false</value></param>
85
50
  5. submit: No additional params required.
86
51
  6. hover: No additional params required.
87
52
  7. double_click: No additional params required.
@@ -174,12 +139,6 @@ class BrowserSessionAwareWebElementTrigger(BrowserSessionAwareTool):
174
139
  raise ValueError(f"Unsupported action: {action}")
175
140
 
176
141
  # Take screenshot after action
177
- #timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
178
- #screenshot_filename = f"screenshot_{action}_{timestamp}.png"
179
- #screenshot_path = os.path.join(os.getcwd(), screenshot_filename)
180
- #await shared_session.page.screenshot(path=screenshot_path, full_page=True)
181
- #absolute_screenshot_path = os.path.abspath(screenshot_path)
182
- #return absolute_screenshot_path
183
142
  return "The WebElementTrigger command is executed"
184
143
 
185
144
  def _parse_params(self, params_str):
@@ -187,7 +146,6 @@ class BrowserSessionAwareWebElementTrigger(BrowserSessionAwareTool):
187
146
  return {}
188
147
 
189
148
  try:
190
- # Wrap the params string in a root element to make it valid XML
191
149
  xml_string = f"<root>{params_str}</root>"
192
150
  root = ET.fromstring(xml_string)
193
151
  params = {}
@@ -198,5 +156,4 @@ class BrowserSessionAwareWebElementTrigger(BrowserSessionAwareTool):
198
156
  params[name_elem.text] = value_elem.text
199
157
  return params
200
158
  except ET.ParseError:
201
- # If parsing fails, return an empty dict
202
- return {}
159
+ return {}
@@ -12,11 +12,15 @@ class BrowserSessionAwareWebPageReader(BrowserSessionAwareTool):
12
12
  def get_name(self) -> str:
13
13
  return "WebPageReader"
14
14
 
15
- def tool_usage(self):
16
- return 'WebPageReader: Reads and cleans the HTML content from a given webpage. Usage: <<<WebPageReader(webpage_url="url_to_read")>>>, where "url_to_read" is a string containing the URL of the webpage to read the content from.'
15
+ @classmethod
16
+ def tool_usage_xml(cls):
17
+ """
18
+ Return an XML string describing the usage of the WebPageReader tool.
17
19
 
18
- def tool_usage_xml(self):
19
- return '''WebPageReader: Reads the HTML content from a given webpage. Usage:
20
+ Returns:
21
+ str: An XML description of how to use the WebPageReader tool.
22
+ """
23
+ return '''WebPageReader: Reads and cleans the HTML content from a given webpage. Usage:
20
24
  <command name="WebPageReader">
21
25
  <arg name="webpage_url">url_to_read</arg>
22
26
  </command>
@@ -26,4 +30,4 @@ where "url_to_read" is a string containing the URL of the webpage to read the co
26
30
  async def perform_action(self, shared_session: SharedBrowserSession, **kwargs):
27
31
  page_content = await shared_session.page.content()
28
32
  cleaned_content = clean(page_content, self.cleaning_mode)
29
- return cleaned_content
33
+ return cleaned_content
@@ -11,10 +11,14 @@ class BrowserSessionAwareWebPageScreenshotTaker(BrowserSessionAwareTool):
11
11
  def get_name(self) -> str:
12
12
  return "WebPageScreenshotTaker"
13
13
 
14
- def tool_usage(self):
15
- return "WebPageScreenshotTaker: Takes a screenshot of a given webpage and saves it to the specified file. Usage: <<<WebPageScreenshotTaker(webpage_url='url_to_screenshot', file_name='screenshot_file_name')>>>, where 'url_to_screenshot' is a string containing the URL of the webpage to take a screenshot of, and 'screenshot_file_name' is the name of the file to save the screenshot (including extension, e.g., 'screenshot.png'). Optionally, 'screenshot_file_name' can include a relative path (e.g., 'images/screenshot.png'). Returns the absolute file path of the saved screenshot."
14
+ @classmethod
15
+ def tool_usage_xml(cls):
16
+ """
17
+ Return an XML string describing the usage of the WebPageScreenshotTaker tool.
16
18
 
17
- def tool_usage_xml(self):
19
+ Returns:
20
+ str: An XML description of how to use the WebPageScreenshotTaker tool.
21
+ """
18
22
  return '''WebPageScreenshotTaker: Takes a screenshot of a given webpage and saves it to the specified file. Usage:
19
23
  <command name="WebPageScreenshotTaker">
20
24
  <arg name="webpage_url">url_to_screenshot</arg>
@@ -31,4 +35,4 @@ Returns the absolute file path of the saved screenshot.
31
35
 
32
36
  await shared_session.page.screenshot(path=file_name, full_page=True)
33
37
  absolute_path = os.path.abspath(file_name)
34
- return absolute_path
38
+ return absolute_path
@@ -46,15 +46,13 @@ class GoogleSearch(BaseTool, UIIntegrator):
46
46
  self.text_area_selector = 'textarea[name="q"]'
47
47
  self.cleaning_mode = cleaning_mode
48
48
 
49
- def tool_usage(self):
50
- """
51
- Return a string describing the usage of the GoogleSearch tool.
52
- """
53
- return 'GoogleSearch: Searches the internet for information. Usage: <<<GoogleSearch(query="search query")>>>, where "search query" is a string.'
54
-
55
- def tool_usage_xml(self):
49
+ @classmethod
50
+ def tool_usage_xml(cls):
56
51
  """
57
52
  Return an XML string describing the usage of the GoogleSearch tool.
53
+
54
+ Returns:
55
+ str: An XML description of how to use the GoogleSearch tool.
58
56
  """
59
57
  return '''GoogleSearch: Searches the internet for information. Usage:
60
58
  <command name="GoogleSearch">
@@ -64,45 +62,21 @@ class GoogleSearch(BaseTool, UIIntegrator):
64
62
  '''
65
63
 
66
64
  async def _execute(self, **kwargs):
67
- """
68
- Perform a Google search using Playwright and return the search results.
69
-
70
- This method initializes the Playwright browser, navigates to Google, performs the search,
71
- and retrieves the results. After initialization, self.page is available as a Playwright
72
- page object for interacting with the web browser.
73
-
74
- Args:
75
- **kwargs: Keyword arguments containing the search query. The query should be specified as 'query'.
76
-
77
- Returns:
78
- str: A string containing the cleaned HTML of the search results.
79
-
80
- Raises:
81
- ValueError: If the 'query' keyword argument is not specified.
82
- """
83
65
  query = kwargs.get('query')
84
66
  if not query:
85
67
  raise ValueError("The 'query' keyword argument must be specified.")
86
68
 
87
- # Call the initialize method from the UIIntegrator class to set up the Playwright browser
88
69
  await self.initialize()
89
- # After initialization, self.page is now available as a Playwright page object
90
-
91
70
  await self.page.goto('https://www.google.com/')
92
71
 
93
- # Find the search box element, type in the search query, and press the Enter key
94
72
  textarea = self.page.locator(self.text_area_selector)
95
73
  await textarea.click()
96
74
  await self.page.type(self.text_area_selector, query)
97
75
  await self.page.keyboard.press('Enter')
98
76
  await self.page.wait_for_load_state()
99
77
 
100
- # Wait for the search results to load
101
- # Wait for the search results to load, we didnt use main because main will contain a lot of base64 encoded images. This will consume a lot of tokens.
102
- #search_result_div = await self.page.wait_for_selector('div.main', state="visible", timeout=10000)
103
78
  search_result_div = await self.page.wait_for_selector('#search', state="visible", timeout=10000)
104
79
  await asyncio.sleep(2)
105
- # Get the content of the div
106
80
  search_result = await search_result_div.inner_html()
107
81
  cleaned_search_result = clean(search_result, mode=self.cleaning_mode)
108
82
  await self.close()
@@ -110,4 +84,4 @@ class GoogleSearch(BaseTool, UIIntegrator):
110
84
  <GoogleSearchResultStart>
111
85
  {cleaned_search_result}
112
86
  </GoogleSearchResultEnd>
113
- '''
87
+ '''