@_vrsen/openswarm 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (316) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +152 -0
  3. package/bin/openswarm.js +38 -0
  4. package/config.py +34 -0
  5. package/data_analyst_agent/.cursor/rules/data_analyst.mdc +43 -0
  6. package/data_analyst_agent/__init__.py +3 -0
  7. package/data_analyst_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  8. package/data_analyst_agent/__pycache__/data_analyst_agent.cpython-312.pyc +0 -0
  9. package/data_analyst_agent/data_analyst_agent.py +45 -0
  10. package/data_analyst_agent/instructions.md +173 -0
  11. package/data_analyst_agent/test_files/test_file.csv +21 -0
  12. package/data_analyst_agent/tools/__init__.py +6 -0
  13. package/deep_research/__init__.py +1 -0
  14. package/deep_research/__pycache__/__init__.cpython-312.pyc +0 -0
  15. package/deep_research/__pycache__/deep_research.cpython-312.pyc +0 -0
  16. package/deep_research/deep_research.py +27 -0
  17. package/deep_research/instructions.md +104 -0
  18. package/deep_research/tools/__init__.py +1 -0
  19. package/docs_agent/__init__.py +3 -0
  20. package/docs_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  21. package/docs_agent/__pycache__/docs_agent.cpython-312.pyc +0 -0
  22. package/docs_agent/docs_agent.py +61 -0
  23. package/docs_agent/instructions.md +418 -0
  24. package/docs_agent/tools/ConvertDocument.py +323 -0
  25. package/docs_agent/tools/CreateDocument.py +287 -0
  26. package/docs_agent/tools/ListDocuments.py +134 -0
  27. package/docs_agent/tools/ModifyDocument.py +247 -0
  28. package/docs_agent/tools/RestoreDocument.py +79 -0
  29. package/docs_agent/tools/ViewDocument.py +153 -0
  30. package/docs_agent/tools/__init__.py +1 -0
  31. package/docs_agent/tools/__pycache__/ConvertDocument.cpython-312.pyc +0 -0
  32. package/docs_agent/tools/__pycache__/CreateDocument.cpython-312.pyc +0 -0
  33. package/docs_agent/tools/__pycache__/ListDocuments.cpython-312.pyc +0 -0
  34. package/docs_agent/tools/__pycache__/ModifyDocument.cpython-312.pyc +0 -0
  35. package/docs_agent/tools/__pycache__/RestoreDocument.cpython-312.pyc +0 -0
  36. package/docs_agent/tools/__pycache__/ViewDocument.cpython-312.pyc +0 -0
  37. package/docs_agent/tools/__pycache__/__init__.cpython-312.pyc +0 -0
  38. package/docs_agent/tools/utils/__init__.py +1 -0
  39. package/docs_agent/tools/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  40. package/docs_agent/tools/utils/__pycache__/doc_file_utils.cpython-312.pyc +0 -0
  41. package/docs_agent/tools/utils/__pycache__/html_docx_blocks.cpython-312.pyc +0 -0
  42. package/docs_agent/tools/utils/__pycache__/html_docx_constants.cpython-312.pyc +0 -0
  43. package/docs_agent/tools/utils/__pycache__/html_docx_core.cpython-312.pyc +0 -0
  44. package/docs_agent/tools/utils/__pycache__/html_docx_css.cpython-312.pyc +0 -0
  45. package/docs_agent/tools/utils/__pycache__/html_docx_images.cpython-312.pyc +0 -0
  46. package/docs_agent/tools/utils/__pycache__/html_docx_page.cpython-312.pyc +0 -0
  47. package/docs_agent/tools/utils/__pycache__/html_docx_paragraphs.cpython-312.pyc +0 -0
  48. package/docs_agent/tools/utils/__pycache__/html_docx_playwright.cpython-312.pyc +0 -0
  49. package/docs_agent/tools/utils/__pycache__/html_docx_selectors.cpython-312.pyc +0 -0
  50. package/docs_agent/tools/utils/__pycache__/html_docx_shared.cpython-312.pyc +0 -0
  51. package/docs_agent/tools/utils/__pycache__/html_validation.cpython-312.pyc +0 -0
  52. package/docs_agent/tools/utils/doc_file_utils.py +29 -0
  53. package/docs_agent/tools/utils/html_docx_blocks.py +262 -0
  54. package/docs_agent/tools/utils/html_docx_constants.py +78 -0
  55. package/docs_agent/tools/utils/html_docx_core.py +138 -0
  56. package/docs_agent/tools/utils/html_docx_css.py +262 -0
  57. package/docs_agent/tools/utils/html_docx_images.py +293 -0
  58. package/docs_agent/tools/utils/html_docx_page.py +185 -0
  59. package/docs_agent/tools/utils/html_docx_paragraphs.py +342 -0
  60. package/docs_agent/tools/utils/html_docx_playwright.py +184 -0
  61. package/docs_agent/tools/utils/html_docx_selectors.py +196 -0
  62. package/docs_agent/tools/utils/html_docx_shared.py +23 -0
  63. package/docs_agent/tools/utils/html_docx_tables.py +942 -0
  64. package/docs_agent/tools/utils/html_validation.py +102 -0
  65. package/helpers.py +59 -0
  66. package/image_generation_agent/__init__.py +1 -0
  67. package/image_generation_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  68. package/image_generation_agent/__pycache__/image_generation_agent.cpython-312.pyc +0 -0
  69. package/image_generation_agent/image_generation_agent.py +31 -0
  70. package/image_generation_agent/instructions.md +80 -0
  71. package/image_generation_agent/tools/CombineImages.py +211 -0
  72. package/image_generation_agent/tools/EditImages.py +200 -0
  73. package/image_generation_agent/tools/GenerateImages.py +184 -0
  74. package/image_generation_agent/tools/RemoveBackground.py +108 -0
  75. package/image_generation_agent/tools/__init__.py +2 -0
  76. package/image_generation_agent/tools/__pycache__/CombineImages.cpython-312.pyc +0 -0
  77. package/image_generation_agent/tools/__pycache__/EditImages.cpython-312.pyc +0 -0
  78. package/image_generation_agent/tools/__pycache__/GenerateImages.cpython-312.pyc +0 -0
  79. package/image_generation_agent/tools/__pycache__/RemoveBackground.cpython-312.pyc +0 -0
  80. package/image_generation_agent/tools/utils/__init__.py +2 -0
  81. package/image_generation_agent/tools/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  82. package/image_generation_agent/tools/utils/__pycache__/image_io.cpython-312.pyc +0 -0
  83. package/image_generation_agent/tools/utils/image_io.py +308 -0
  84. package/onboard.py +325 -0
  85. package/orchestrator/__init__.py +3 -0
  86. package/orchestrator/__pycache__/__init__.cpython-312.pyc +0 -0
  87. package/orchestrator/__pycache__/orchestrator.cpython-312.pyc +0 -0
  88. package/orchestrator/instructions.md +90 -0
  89. package/orchestrator/orchestrator.py +33 -0
  90. package/package.json +49 -0
  91. package/patches/__init__.py +1 -0
  92. package/patches/__pycache__/__init__.cpython-312.pyc +0 -0
  93. package/patches/__pycache__/patch_agency_swarm_dual_comms.cpython-312.pyc +0 -0
  94. package/patches/__pycache__/patch_file_attachment_refs.cpython-312.pyc +0 -0
  95. package/patches/__pycache__/patch_ipython_interpreter_composio.cpython-312.pyc +0 -0
  96. package/patches/dom-to-pptx+1.1.5.patch +133440 -0
  97. package/patches/patch_agency_swarm_dual_comms.py +199 -0
  98. package/patches/patch_file_attachment_refs.py +74 -0
  99. package/patches/patch_ipython_interpreter_composio.py +54 -0
  100. package/pyproject.toml +67 -0
  101. package/run.py +343 -0
  102. package/server.py +26 -0
  103. package/shared_instructions.md +119 -0
  104. package/shared_tools/CopyFile.py +68 -0
  105. package/shared_tools/ExecuteTool.py +184 -0
  106. package/shared_tools/FindTools.py +101 -0
  107. package/shared_tools/ManageConnections.py +43 -0
  108. package/shared_tools/SearchTools.py +44 -0
  109. package/shared_tools/__init__.py +7 -0
  110. package/shared_tools/__pycache__/CopyFile.cpython-312.pyc +0 -0
  111. package/shared_tools/__pycache__/ExecuteTool.cpython-312.pyc +0 -0
  112. package/shared_tools/__pycache__/FindTools.cpython-312.pyc +0 -0
  113. package/shared_tools/__pycache__/ManageConnections.cpython-312.pyc +0 -0
  114. package/shared_tools/__pycache__/SearchTools.cpython-312.pyc +0 -0
  115. package/shared_tools/__pycache__/__init__.cpython-312.pyc +0 -0
  116. package/slides_agent/.cursor/rules/slides-agent-workflow.mdc +9 -0
  117. package/slides_agent/__init__.py +1 -0
  118. package/slides_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  119. package/slides_agent/__pycache__/slides_agent.cpython-312.pyc +0 -0
  120. package/slides_agent/instructions.md +298 -0
  121. package/slides_agent/pptx/SKILL.md +528 -0
  122. package/slides_agent/pptx/html2pptx.md +625 -0
  123. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chart.xsd +1499 -0
  124. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-chartDrawing.xsd +146 -0
  125. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-diagram.xsd +1085 -0
  126. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-lockedCanvas.xsd +11 -0
  127. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-main.xsd +3081 -0
  128. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-picture.xsd +23 -0
  129. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-spreadsheetDrawing.xsd +185 -0
  130. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/dml-wordprocessingDrawing.xsd +287 -0
  131. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/pml.xsd +1676 -0
  132. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-additionalCharacteristics.xsd +28 -0
  133. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-bibliography.xsd +144 -0
  134. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-commonSimpleTypes.xsd +174 -0
  135. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlDataProperties.xsd +25 -0
  136. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-customXmlSchemaProperties.xsd +18 -0
  137. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesCustom.xsd +59 -0
  138. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesExtended.xsd +56 -0
  139. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-documentPropertiesVariantTypes.xsd +195 -0
  140. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-math.xsd +582 -0
  141. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/shared-relationshipReference.xsd +25 -0
  142. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/sml.xsd +4439 -0
  143. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-main.xsd +570 -0
  144. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-officeDrawing.xsd +509 -0
  145. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-presentationDrawing.xsd +12 -0
  146. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-spreadsheetDrawing.xsd +108 -0
  147. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/vml-wordprocessingDrawing.xsd +96 -0
  148. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/wml.xsd +3646 -0
  149. package/slides_agent/pptx/ooxml/schemas/ISO-IEC29500-4_2016/xml.xsd +116 -0
  150. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-contentTypes.xsd +42 -0
  151. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-coreProperties.xsd +50 -0
  152. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-digSig.xsd +49 -0
  153. package/slides_agent/pptx/ooxml/schemas/ecma/fouth-edition/opc-relationships.xsd +33 -0
  154. package/slides_agent/pptx/ooxml/schemas/mce/mc.xsd +75 -0
  155. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-2010.xsd +560 -0
  156. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-2012.xsd +67 -0
  157. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-2018.xsd +14 -0
  158. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-cex-2018.xsd +20 -0
  159. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-cid-2016.xsd +13 -0
  160. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-sdtdatahash-2020.xsd +4 -0
  161. package/slides_agent/pptx/ooxml/schemas/microsoft/wml-symex-2015.xsd +8 -0
  162. package/slides_agent/pptx/ooxml/scripts/pack.py +169 -0
  163. package/slides_agent/pptx/ooxml/scripts/unpack.py +29 -0
  164. package/slides_agent/pptx/ooxml/scripts/validate.py +69 -0
  165. package/slides_agent/pptx/ooxml/scripts/validation/__init__.py +15 -0
  166. package/slides_agent/pptx/ooxml/scripts/validation/base.py +951 -0
  167. package/slides_agent/pptx/ooxml/scripts/validation/docx.py +274 -0
  168. package/slides_agent/pptx/ooxml/scripts/validation/pptx.py +315 -0
  169. package/slides_agent/pptx/ooxml/scripts/validation/redlining.py +279 -0
  170. package/slides_agent/pptx/ooxml.md +427 -0
  171. package/slides_agent/pptx/scripts/html2pptx.js +1092 -0
  172. package/slides_agent/pptx/scripts/inventory.py +1020 -0
  173. package/slides_agent/pptx/scripts/rearrange.py +231 -0
  174. package/slides_agent/pptx/scripts/replace.py +385 -0
  175. package/slides_agent/pptx/scripts/thumbnail.py +451 -0
  176. package/slides_agent/slides_agent.py +109 -0
  177. package/slides_agent/test_deck/_theme.css +92 -0
  178. package/slides_agent/test_deck/assets/placeholder.svg +11 -0
  179. package/slides_agent/test_deck/slide_01_title.html +10 -0
  180. package/slides_agent/test_deck/slide_02_image_split.html +23 -0
  181. package/slides_agent/test_deck/slide_03_kpi.html +21 -0
  182. package/slides_agent/tools/ApplyPptxTextReplacements.py +91 -0
  183. package/slides_agent/tools/BuildPptxFromHtmlSlides.py +221 -0
  184. package/slides_agent/tools/CheckSlide.py +218 -0
  185. package/slides_agent/tools/CheckSlideCanvasOverflow.py +221 -0
  186. package/slides_agent/tools/CreateImageMontage.py +261 -0
  187. package/slides_agent/tools/CreatePptxThumbnailGrid.py +168 -0
  188. package/slides_agent/tools/DeleteSlide.py +78 -0
  189. package/slides_agent/tools/DownloadImage.py +79 -0
  190. package/slides_agent/tools/EnsureRasterImage.py +157 -0
  191. package/slides_agent/tools/ExtractPptxTextInventory.py +104 -0
  192. package/slides_agent/tools/GenerateImage.py +189 -0
  193. package/slides_agent/tools/ImageSearch.py +127 -0
  194. package/slides_agent/tools/InsertNewSlides.py +393 -0
  195. package/slides_agent/tools/ManageTheme.py +112 -0
  196. package/slides_agent/tools/ModifySlide.py +563 -0
  197. package/slides_agent/tools/ReadSlide.py +26 -0
  198. package/slides_agent/tools/RearrangePptxSlidesFromTemplate.py +114 -0
  199. package/slides_agent/tools/RestoreSnapshot.py +89 -0
  200. package/slides_agent/tools/SlideScreenshot.py +66 -0
  201. package/slides_agent/tools/__init__.py +54 -0
  202. package/slides_agent/tools/__pycache__/ApplyPptxTextReplacements.cpython-312.pyc +0 -0
  203. package/slides_agent/tools/__pycache__/BuildPptxFromHtmlSlides.cpython-312.pyc +0 -0
  204. package/slides_agent/tools/__pycache__/CheckSlide.cpython-312.pyc +0 -0
  205. package/slides_agent/tools/__pycache__/CheckSlideCanvasOverflow.cpython-312.pyc +0 -0
  206. package/slides_agent/tools/__pycache__/CreateImageMontage.cpython-312.pyc +0 -0
  207. package/slides_agent/tools/__pycache__/CreatePptxThumbnailGrid.cpython-312.pyc +0 -0
  208. package/slides_agent/tools/__pycache__/DeleteSlide.cpython-312.pyc +0 -0
  209. package/slides_agent/tools/__pycache__/DownloadImage.cpython-312.pyc +0 -0
  210. package/slides_agent/tools/__pycache__/EnsureRasterImage.cpython-312.pyc +0 -0
  211. package/slides_agent/tools/__pycache__/ExtractPptxTextInventory.cpython-312.pyc +0 -0
  212. package/slides_agent/tools/__pycache__/GenerateImage.cpython-312.pyc +0 -0
  213. package/slides_agent/tools/__pycache__/ImageSearch.cpython-312.pyc +0 -0
  214. package/slides_agent/tools/__pycache__/InsertNewSlides.cpython-312.pyc +0 -0
  215. package/slides_agent/tools/__pycache__/ManageTheme.cpython-312.pyc +0 -0
  216. package/slides_agent/tools/__pycache__/ModifySlide.cpython-312.pyc +0 -0
  217. package/slides_agent/tools/__pycache__/ReadSlide.cpython-312.pyc +0 -0
  218. package/slides_agent/tools/__pycache__/RearrangePptxSlidesFromTemplate.cpython-312.pyc +0 -0
  219. package/slides_agent/tools/__pycache__/RestoreSnapshot.cpython-312.pyc +0 -0
  220. package/slides_agent/tools/__pycache__/SlideScreenshot.cpython-312.pyc +0 -0
  221. package/slides_agent/tools/__pycache__/__init__.cpython-312.pyc +0 -0
  222. package/slides_agent/tools/__pycache__/slide_file_utils.cpython-312.pyc +0 -0
  223. package/slides_agent/tools/__pycache__/slide_html_utils.cpython-312.pyc +0 -0
  224. package/slides_agent/tools/__pycache__/template_registry.cpython-312.pyc +0 -0
  225. package/slides_agent/tools/deck_utils.py +31 -0
  226. package/slides_agent/tools/html2pptx_runner.js +1183 -0
  227. package/slides_agent/tools/html_writer_instructions.md +149 -0
  228. package/slides_agent/tools/slide_file_utils.py +108 -0
  229. package/slides_agent/tools/slide_html_utils.py +354 -0
  230. package/slides_agent/tools/template_registry.py +55 -0
  231. package/swarm.py +82 -0
  232. package/video_generation_agent/__init__.py +1 -0
  233. package/video_generation_agent/__pycache__/__init__.cpython-312.pyc +0 -0
  234. package/video_generation_agent/__pycache__/video_generation_agent.cpython-312.pyc +0 -0
  235. package/video_generation_agent/instructions.md +178 -0
  236. package/video_generation_agent/tools/AddSubtitles.py +425 -0
  237. package/video_generation_agent/tools/CombineImages.py +166 -0
  238. package/video_generation_agent/tools/CombineVideos.py +113 -0
  239. package/video_generation_agent/tools/EditAudio.py +297 -0
  240. package/video_generation_agent/tools/EditImage.py +144 -0
  241. package/video_generation_agent/tools/EditVideoContent.py +369 -0
  242. package/video_generation_agent/tools/GenerateImage.py +133 -0
  243. package/video_generation_agent/tools/GenerateVideo.py +556 -0
  244. package/video_generation_agent/tools/TrimVideo.py +233 -0
  245. package/video_generation_agent/tools/__init__.py +1 -0
  246. package/video_generation_agent/tools/__pycache__/AddSubtitles.cpython-312.pyc +0 -0
  247. package/video_generation_agent/tools/__pycache__/CombineImages.cpython-312.pyc +0 -0
  248. package/video_generation_agent/tools/__pycache__/CombineVideos.cpython-312.pyc +0 -0
  249. package/video_generation_agent/tools/__pycache__/EditAudio.cpython-312.pyc +0 -0
  250. package/video_generation_agent/tools/__pycache__/EditImage.cpython-312.pyc +0 -0
  251. package/video_generation_agent/tools/__pycache__/EditVideoContent.cpython-312.pyc +0 -0
  252. package/video_generation_agent/tools/__pycache__/GenerateImage.cpython-312.pyc +0 -0
  253. package/video_generation_agent/tools/__pycache__/GenerateVideo.cpython-312.pyc +0 -0
  254. package/video_generation_agent/tools/__pycache__/TrimVideo.cpython-312.pyc +0 -0
  255. package/video_generation_agent/tools/utils/__init__.py +1 -0
  256. package/video_generation_agent/tools/utils/__pycache__/__init__.cpython-312.pyc +0 -0
  257. package/video_generation_agent/tools/utils/__pycache__/image_utils.cpython-312.pyc +0 -0
  258. package/video_generation_agent/tools/utils/__pycache__/video_utils.cpython-312.pyc +0 -0
  259. package/video_generation_agent/tools/utils/image_utils.py +174 -0
  260. package/video_generation_agent/tools/utils/video_utils.py +522 -0
  261. package/video_generation_agent/video_generation_agent.py +26 -0
  262. package/virtual_assistant/__init__.py +1 -0
  263. package/virtual_assistant/__pycache__/__init__.cpython-312.pyc +0 -0
  264. package/virtual_assistant/__pycache__/virtual_assistant.cpython-312.pyc +0 -0
  265. package/virtual_assistant/instructions.md +206 -0
  266. package/virtual_assistant/tools/AddLabelToEmail.py +154 -0
  267. package/virtual_assistant/tools/CheckEventsForDate.py +218 -0
  268. package/virtual_assistant/tools/CheckUnreadSlackMessages.py +216 -0
  269. package/virtual_assistant/tools/CreateCalendarEvent.py +261 -0
  270. package/virtual_assistant/tools/DeleteCalendarEvent.py +137 -0
  271. package/virtual_assistant/tools/DeleteDraft.py +95 -0
  272. package/virtual_assistant/tools/DraftEmail.py +239 -0
  273. package/virtual_assistant/tools/EditFile.py +113 -0
  274. package/virtual_assistant/tools/FindEmails.py +330 -0
  275. package/virtual_assistant/tools/GetCurrentTime.py +69 -0
  276. package/virtual_assistant/tools/GetSlackUserInfo.py +117 -0
  277. package/virtual_assistant/tools/ListDirectory.py +113 -0
  278. package/virtual_assistant/tools/ListSkills.py +94 -0
  279. package/virtual_assistant/tools/ManageLabels.py +295 -0
  280. package/virtual_assistant/tools/ProductSearch.py +254 -0
  281. package/virtual_assistant/tools/ReadEmail.py +251 -0
  282. package/virtual_assistant/tools/ReadFile.py +108 -0
  283. package/virtual_assistant/tools/ReadSlackMessages.py +191 -0
  284. package/virtual_assistant/tools/RemoveLabelFromEmail.py +137 -0
  285. package/virtual_assistant/tools/RescheduleCalendarEvent.py +227 -0
  286. package/virtual_assistant/tools/ScholarSearch.py +216 -0
  287. package/virtual_assistant/tools/SendDraft.py +101 -0
  288. package/virtual_assistant/tools/SendSlackMessage.py +148 -0
  289. package/virtual_assistant/tools/WriteFile.py +95 -0
  290. package/virtual_assistant/tools/__init__.py +1 -0
  291. package/virtual_assistant/tools/__pycache__/AddLabelToEmail.cpython-312.pyc +0 -0
  292. package/virtual_assistant/tools/__pycache__/CheckEventsForDate.cpython-312.pyc +0 -0
  293. package/virtual_assistant/tools/__pycache__/CheckUnreadSlackMessages.cpython-312.pyc +0 -0
  294. package/virtual_assistant/tools/__pycache__/CreateCalendarEvent.cpython-312.pyc +0 -0
  295. package/virtual_assistant/tools/__pycache__/DeleteCalendarEvent.cpython-312.pyc +0 -0
  296. package/virtual_assistant/tools/__pycache__/DeleteDraft.cpython-312.pyc +0 -0
  297. package/virtual_assistant/tools/__pycache__/DraftEmail.cpython-312.pyc +0 -0
  298. package/virtual_assistant/tools/__pycache__/EditFile.cpython-312.pyc +0 -0
  299. package/virtual_assistant/tools/__pycache__/FindEmails.cpython-312.pyc +0 -0
  300. package/virtual_assistant/tools/__pycache__/GetCurrentTime.cpython-312.pyc +0 -0
  301. package/virtual_assistant/tools/__pycache__/GetSlackUserInfo.cpython-312.pyc +0 -0
  302. package/virtual_assistant/tools/__pycache__/ListDirectory.cpython-312.pyc +0 -0
  303. package/virtual_assistant/tools/__pycache__/ListSkills.cpython-312.pyc +0 -0
  304. package/virtual_assistant/tools/__pycache__/ManageLabels.cpython-312.pyc +0 -0
  305. package/virtual_assistant/tools/__pycache__/ProductSearch.cpython-312.pyc +0 -0
  306. package/virtual_assistant/tools/__pycache__/ReadEmail.cpython-312.pyc +0 -0
  307. package/virtual_assistant/tools/__pycache__/ReadFile.cpython-312.pyc +0 -0
  308. package/virtual_assistant/tools/__pycache__/ReadSlackMessages.cpython-312.pyc +0 -0
  309. package/virtual_assistant/tools/__pycache__/RemoveLabelFromEmail.cpython-312.pyc +0 -0
  310. package/virtual_assistant/tools/__pycache__/RescheduleCalendarEvent.cpython-312.pyc +0 -0
  311. package/virtual_assistant/tools/__pycache__/ScholarSearch.cpython-312.pyc +0 -0
  312. package/virtual_assistant/tools/__pycache__/SendDraft.cpython-312.pyc +0 -0
  313. package/virtual_assistant/tools/__pycache__/SendSlackMessage.cpython-312.pyc +0 -0
  314. package/virtual_assistant/tools/__pycache__/WriteFile.cpython-312.pyc +0 -0
  315. package/virtual_assistant/tools/__pycache__/__init__.cpython-312.pyc +0 -0
  316. package/virtual_assistant/virtual_assistant.py +52 -0
@@ -0,0 +1,184 @@
1
+ import tempfile
2
+ from pathlib import Path
3
+ from typing import Optional
4
+
5
+ from bs4 import BeautifulSoup
6
+ from playwright.sync_api import sync_playwright
7
+ import subprocess
8
+ from .html_docx_page import _extract_page_geometry_pt
9
+
10
+ _PT_TO_PX = 96.0 / 72.0
11
+
12
+ # Elements that must never be split across a page boundary.
13
+ _UNSPLITTABLE_SELECTORS = "table, img, figure, blockquote, pre, svg"
14
+
15
+ # CSS applied to the inserted page-break div.
16
+ _PB_STYLE = "page-break-before:always;break-before:page;margin:0;padding:0;height:0;"
17
+
18
+ # Block-level tags whose children can directly receive a page-break sibling.
19
+ _BLOCK_PARENTS = frozenset(["BODY", "DIV", "TD", "TH", "SECTION", "ARTICLE", "MAIN"])
20
+
21
+
22
+ def auto_page_breaks(html_content: str) -> str:
23
+ """Insert page-break divs before unsplittable elements that cross a page boundary.
24
+
25
+ Renders the HTML in a single Playwright session at A4 width, identifies every
26
+ table / img / figure / blockquote / pre / svg whose bounding box crosses a page
27
+ boundary, and inserts a zero-height page-break-before div directly before it in
28
+ the live DOM. The modified HTML is returned via page.content().
29
+
30
+ No thresholds — if the element crosses any boundary, it moves to the next page.
31
+ """
32
+ with tempfile.NamedTemporaryFile(
33
+ suffix=".html", delete=False, mode="w", encoding="utf-8"
34
+ ) as fh:
35
+ fh.write(html_content)
36
+ tmp_path = Path(fh.name)
37
+
38
+ try:
39
+ with sync_playwright() as playwright:
40
+ browser = _launch_chromium_with_install(playwright)
41
+ viewport_width_px, page_height_px = _extract_page_geometry_px(html_content)
42
+ page = browser.new_page(
43
+ viewport={"width": viewport_width_px, "height": page_height_px * 20}
44
+ )
45
+ page.emulate_media(media="print")
46
+ page.route(
47
+ "**/*",
48
+ lambda route, request: route.abort()
49
+ if request.resource_type in {"media", "font"}
50
+ else route.continue_(),
51
+ )
52
+ page.goto(tmp_path.as_uri(), wait_until="load")
53
+
54
+ block_parents_js = str(list(_BLOCK_PARENTS))
55
+ page.evaluate(
56
+ f"""([selectors, pageH, pbStyle]) => {{
57
+ const BLOCK_PARENTS = new Set({block_parents_js});
58
+ const processed = new WeakSet();
59
+
60
+ for (const el of document.querySelectorAll(selectors)) {{
61
+ const rect = el.getBoundingClientRect();
62
+ if (rect.height <= 0) continue;
63
+
64
+ // Mark tables that fit within one page — the DOCX converter will
65
+ // apply w:cantSplit to their rows so Word keeps them together.
66
+ if (el.tagName === 'TABLE' && rect.height < pageH) {{
67
+ el.setAttribute('data-docx-cant-split', '1');
68
+ }}
69
+
70
+ // Inject page-break before unsplittable elements that cross a boundary.
71
+ if (rect.height >= pageH) continue;
72
+ const topPage = Math.floor(rect.top / pageH);
73
+ const botPage = Math.floor((rect.bottom - 1) / pageH);
74
+ if (topPage === botPage) continue;
75
+
76
+ let node = el;
77
+ while (node.parentElement && !BLOCK_PARENTS.has(node.parentElement.tagName))
78
+ node = node.parentElement;
79
+
80
+ if (!node.parentElement) continue;
81
+ if (processed.has(node)) continue;
82
+ processed.add(node);
83
+
84
+ const pb = document.createElement('div');
85
+ pb.setAttribute('style', pbStyle);
86
+ node.parentElement.insertBefore(pb, node);
87
+ }}
88
+ }}""",
89
+ [_UNSPLITTABLE_SELECTORS, page_height_px, _PB_STYLE],
90
+ )
91
+
92
+ modified_html = page.content()
93
+ browser.close()
94
+ finally:
95
+ tmp_path.unlink(missing_ok=True)
96
+
97
+ return modified_html
98
+
99
+
100
+ def _extract_page_geometry_px(html_content: str) -> tuple[int, int]:
101
+ width_pt, height_pt, top_pt, _right_pt, bottom_pt, _left_pt = _extract_page_geometry_pt(
102
+ html_content
103
+ )
104
+ viewport_width_px = max(1, round(width_pt * _PT_TO_PX))
105
+ content_height_pt = max(1.0, height_pt - top_pt - bottom_pt)
106
+ page_height_px = max(1, round(content_height_pt * _PT_TO_PX))
107
+ return viewport_width_px, page_height_px
108
+
109
+
110
+ def _annotate_tables(soup: BeautifulSoup) -> str:
111
+ tables = soup.find_all("table")
112
+ for idx, table in enumerate(tables):
113
+ table["data-docx-table-idx"] = str(idx)
114
+ return str(soup)
115
+
116
+
117
+ def _compute_table_auto_widths(html_content: str) -> dict[int, list[float]]:
118
+ widths_by_index: dict[int, list[float]] = {}
119
+ with sync_playwright() as playwright:
120
+ browser = _launch_chromium_with_install(playwright)
121
+ page = browser.new_page(viewport={"width": 1200, "height": 1600})
122
+ page.route(
123
+ "**/*",
124
+ lambda route, request: route.abort()
125
+ if request.resource_type in {"image", "media", "font"}
126
+ else route.continue_(),
127
+ )
128
+ page.set_content(html_content, wait_until="domcontentloaded")
129
+ tables = page.query_selector_all("table[data-docx-table-idx]")
130
+ for table in tables:
131
+ idx_value = table.get_attribute("data-docx-table-idx")
132
+ if idx_value is None:
133
+ continue
134
+ rows = table.query_selector_all("tr")
135
+ if not rows:
136
+ continue
137
+ row = rows[0]
138
+ cells = row.query_selector_all(":scope > td, :scope > th")
139
+ if not cells:
140
+ continue
141
+ widths_px = []
142
+ for cell in cells:
143
+ box = cell.bounding_box()
144
+ if box:
145
+ widths_px.append(box["width"])
146
+ if widths_px:
147
+ widths_by_index[int(idx_value)] = [width * 0.75 for width in widths_px]
148
+ browser.close()
149
+ return widths_by_index
150
+
151
+
152
+ def _extract_auto_widths(
153
+ table_node, table_auto_widths: dict[int, list[float]], column_count: int
154
+ ) -> Optional[list[float]]:
155
+ idx_value = table_node.get("data-docx-table-idx")
156
+ if idx_value is None:
157
+ return None
158
+ try:
159
+ idx = int(idx_value)
160
+ except ValueError:
161
+ return None
162
+ widths = table_auto_widths.get(idx)
163
+ if not widths or len(widths) < column_count:
164
+ return None
165
+ return widths[:column_count]
166
+
167
+
168
+ def _launch_chromium_with_install(playwright_instance):
169
+ try:
170
+ return playwright_instance.chromium.launch()
171
+ except Exception as exc:
172
+ if _is_missing_playwright_browser_error(exc):
173
+ _install_playwright_chromium()
174
+ return playwright_instance.chromium.launch()
175
+ raise
176
+
177
+
178
+ def _is_missing_playwright_browser_error(exc: Exception) -> bool:
179
+ message = str(exc)
180
+ return "Executable doesn't exist" in message or "playwright install" in message
181
+
182
+
183
+ def _install_playwright_chromium() -> None:
184
+ subprocess.run(["playwright", "install", "chromium"], check=True)
@@ -0,0 +1,196 @@
1
+ from typing import Dict, List, Optional, Tuple
2
+
3
+ from bs4 import BeautifulSoup
4
+ from bs4.element import Tag
5
+ import tinycss2
6
+
7
+
8
+ def _parse_style(style: str) -> Dict[str, str]:
9
+ items = {}
10
+ for rule in style.split(";"):
11
+ if ":" not in rule:
12
+ continue
13
+ key, value = rule.split(":", 1)
14
+ key = key.strip().lower()
15
+ value = value.strip()
16
+ if key and value:
17
+ items[key] = value
18
+ return items
19
+
20
+
21
+ def _extract_css_rules(
22
+ soup: BeautifulSoup,
23
+ ) -> List[Tuple[str, Dict[str, str], Tuple[int, int, int], int]]:
24
+ rules: List[Tuple[str, Dict[str, str], Tuple[int, int, int], int]] = []
25
+ order = 0
26
+
27
+ for style_tag in soup.find_all("style"):
28
+ css_text = style_tag.string or style_tag.get_text()
29
+ if not css_text:
30
+ continue
31
+
32
+ stylesheet = tinycss2.parse_stylesheet(
33
+ css_text, skip_comments=True, skip_whitespace=True
34
+ )
35
+ for rule in stylesheet:
36
+ if rule.type != "qualified-rule":
37
+ continue
38
+
39
+ selectors_text = tinycss2.serialize(rule.prelude).strip()
40
+ if not selectors_text:
41
+ continue
42
+
43
+ declarations = tinycss2.parse_declaration_list(
44
+ rule.content, skip_comments=True, skip_whitespace=True
45
+ )
46
+ style_map: Dict[str, str] = {}
47
+ for declaration in declarations:
48
+ if declaration.type != "declaration":
49
+ continue
50
+ name = declaration.name.lower().strip() if declaration.name else ""
51
+ value = tinycss2.serialize(declaration.value).strip()
52
+ if name and value:
53
+ style_map[name] = value
54
+
55
+ for selector in [s.strip() for s in selectors_text.split(",") if s.strip()]:
56
+ pseudo = None
57
+ if "::before" in selector:
58
+ pseudo = "before"
59
+ base_selector = selector.replace("::before", "").strip()
60
+ elif "::after" in selector:
61
+ pseudo = "after"
62
+ base_selector = selector.replace("::after", "").strip()
63
+ else:
64
+ base_selector = selector
65
+
66
+ if not _is_supported_selector(base_selector):
67
+ continue
68
+
69
+ rule_styles = style_map
70
+ if pseudo:
71
+ rule_styles = {f"pseudo-{pseudo}-{k}": v for k, v in style_map.items()}
72
+
73
+ specificity = _selector_specificity(base_selector)
74
+ rules.append((base_selector, rule_styles, specificity, order))
75
+ order += 1
76
+
77
+ return rules
78
+
79
+
80
+ def _compute_style_map(
81
+ element, css_rules: List[Tuple[str, Dict[str, str], Tuple[int, int, int], int]]
82
+ ) -> Dict[str, str]:
83
+ resolved: Dict[str, str] = {}
84
+ matches: List[Tuple[Tuple[int, int, int], int, Dict[str, str]]] = []
85
+
86
+ for selector, styles, specificity, order in css_rules:
87
+ if _matches_selector(element, selector):
88
+ matches.append((specificity, order, styles))
89
+
90
+ matches.sort(key=lambda item: (item[0], item[1]))
91
+ for _, __, styles in matches:
92
+ resolved.update(styles)
93
+
94
+ inline_styles = _parse_style(element.get("style", ""))
95
+ resolved.update(inline_styles)
96
+
97
+ return resolved
98
+
99
+
100
+ def _is_supported_selector(selector: str) -> bool:
101
+ selector = selector.strip()
102
+ if not selector:
103
+ return False
104
+ if any(token in selector for token in ["#", "[", "]", "*", "+", "~"]):
105
+ return False
106
+ return True
107
+
108
+
109
+ def _selector_specificity(selector: str) -> Tuple[int, int, int]:
110
+ selectors = _parse_selector_chain(selector)
111
+ class_count = sum(len(classes) for _, classes in selectors)
112
+ tag_count = sum(1 for tag, _ in selectors if tag)
113
+ return (0, class_count, tag_count)
114
+
115
+
116
+ def _parse_selector(selector: str) -> Tuple[Optional[str], List[str]]:
117
+ selector = selector.strip()
118
+ if selector.startswith("."):
119
+ tag = None
120
+ classes = [cls for cls in selector[1:].split(".") if cls]
121
+ else:
122
+ parts = [part for part in selector.split(".") if part]
123
+ tag = parts[0] if parts else None
124
+ classes = parts[1:] if len(parts) > 1 else []
125
+ return tag, classes
126
+
127
+
128
+ def _matches_selector(element, selector: str) -> bool:
129
+ chain = _parse_selector_chain(selector)
130
+ if not chain:
131
+ return False
132
+ return _matches_selector_chain(element, chain)
133
+
134
+
135
+ def _parse_selector_chain(selector: str) -> List[Tuple[Optional[str], List[str]]]:
136
+ tokens = selector.replace(">", " > ").split()
137
+ if not tokens:
138
+ return []
139
+ selectors: List[Tuple[Optional[str], List[str]]] = []
140
+ for token in tokens:
141
+ if token == ">":
142
+ selectors.append((">", []))
143
+ else:
144
+ selectors.append(_parse_selector(token))
145
+ return selectors
146
+
147
+
148
+ def _matches_selector_chain(element: Tag, chain: List[Tuple[Optional[str], List[str]]]) -> bool:
149
+ idx = len(chain) - 1
150
+ current = element
151
+
152
+ while idx >= 0:
153
+ token = chain[idx]
154
+ if token[0] == ">":
155
+ idx -= 1
156
+ if idx < 0:
157
+ return False
158
+ parent_selector = chain[idx]
159
+ current = current.parent if isinstance(current.parent, Tag) else None
160
+ if current is None or not _matches_simple_selector(current, parent_selector):
161
+ return False
162
+ idx -= 1
163
+ continue
164
+
165
+ if not _matches_simple_selector(current, token):
166
+ return False
167
+
168
+ idx -= 1
169
+ if idx >= 0 and chain[idx][0] != ">":
170
+ ancestor_selector = chain[idx]
171
+ matched = False
172
+ ancestor = current.parent
173
+ while isinstance(ancestor, Tag):
174
+ if _matches_simple_selector(ancestor, ancestor_selector):
175
+ matched = True
176
+ current = ancestor
177
+ break
178
+ ancestor = ancestor.parent
179
+ if not matched:
180
+ return False
181
+ idx -= 1
182
+
183
+ return True
184
+
185
+
186
+ def _matches_simple_selector(
187
+ element: Tag, selector: Tuple[Optional[str], List[str]]
188
+ ) -> bool:
189
+ tag, classes = selector
190
+ if tag and element.name != tag:
191
+ return False
192
+ if classes:
193
+ element_classes = set(element.get("class", []))
194
+ if not all(cls in element_classes for cls in classes):
195
+ return False
196
+ return True
@@ -0,0 +1,23 @@
1
+ def _remove_trailing_empty_paragraph(container) -> None:
2
+ if not hasattr(container, "paragraphs"):
3
+ return
4
+ if not container.paragraphs:
5
+ return
6
+ last = container.paragraphs[-1]
7
+ if last.text.strip():
8
+ return
9
+ # Preserve empty paragraphs that carry a visual border (used as divider lines).
10
+ if "<w:pBdr>" in last._p.xml:
11
+ return
12
+ last._element.getparent().remove(last._element)
13
+
14
+
15
+ def _remove_leading_empty_paragraph(container) -> None:
16
+ if not hasattr(container, "paragraphs"):
17
+ return
18
+ if not container.paragraphs:
19
+ return
20
+ first = container.paragraphs[0]
21
+ if first.text.strip():
22
+ return
23
+ first._element.getparent().remove(first._element)