@mariozechner/pi-web-ui 0.5.44 → 0.5.46

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 (346) hide show
  1. package/README.md +178 -99
  2. package/dist/ChatPanel.d.ts +15 -10
  3. package/dist/ChatPanel.d.ts.map +1 -1
  4. package/dist/ChatPanel.js +68 -100
  5. package/dist/ChatPanel.js.map +1 -1
  6. package/dist/{state/agent-session.d.ts → agent/agent.d.ts} +23 -19
  7. package/dist/agent/agent.d.ts.map +1 -0
  8. package/dist/{state/agent-session.js → agent/agent.js} +50 -32
  9. package/dist/agent/agent.js.map +1 -0
  10. package/dist/{state → agent}/transports/AppTransport.d.ts +1 -3
  11. package/dist/agent/transports/AppTransport.d.ts.map +1 -0
  12. package/dist/{state → agent}/transports/AppTransport.js +5 -4
  13. package/dist/{state → agent}/transports/AppTransport.js.map +1 -1
  14. package/dist/{state → agent}/transports/ProviderTransport.d.ts +1 -3
  15. package/dist/agent/transports/ProviderTransport.d.ts.map +1 -0
  16. package/dist/{state → agent}/transports/ProviderTransport.js +6 -7
  17. package/dist/agent/transports/ProviderTransport.js.map +1 -0
  18. package/dist/{state → agent}/transports/index.d.ts.map +1 -1
  19. package/dist/agent/transports/index.js.map +1 -0
  20. package/dist/{state → agent}/transports/proxy-types.d.ts.map +1 -1
  21. package/dist/agent/transports/proxy-types.js.map +1 -0
  22. package/dist/agent/transports/types.d.ts +12 -0
  23. package/dist/agent/transports/types.d.ts.map +1 -0
  24. package/dist/{state → agent}/transports/types.js.map +1 -1
  25. package/dist/{state → agent}/types.d.ts.map +1 -1
  26. package/dist/{state → agent}/types.js.map +1 -1
  27. package/dist/app.css +1 -1
  28. package/dist/components/AgentInterface.d.ts +7 -4
  29. package/dist/components/AgentInterface.d.ts.map +1 -1
  30. package/dist/components/AgentInterface.js +29 -17
  31. package/dist/components/AgentInterface.js.map +1 -1
  32. package/dist/components/ConsoleBlock.d.ts +1 -0
  33. package/dist/components/ConsoleBlock.d.ts.map +1 -1
  34. package/dist/components/ConsoleBlock.js +7 -1
  35. package/dist/components/ConsoleBlock.js.map +1 -1
  36. package/dist/components/ExpandableSection.d.ts +15 -0
  37. package/dist/components/ExpandableSection.d.ts.map +1 -0
  38. package/dist/components/ExpandableSection.js +63 -0
  39. package/dist/components/ExpandableSection.js.map +1 -0
  40. package/dist/components/MessageEditor.d.ts +8 -1
  41. package/dist/components/MessageEditor.d.ts.map +1 -1
  42. package/dist/components/MessageEditor.js +149 -6
  43. package/dist/components/MessageEditor.js.map +1 -1
  44. package/dist/components/MessageList.d.ts +3 -2
  45. package/dist/components/MessageList.d.ts.map +1 -1
  46. package/dist/components/MessageList.js +14 -1
  47. package/dist/components/MessageList.js.map +1 -1
  48. package/dist/components/Messages.d.ts +15 -6
  49. package/dist/components/Messages.d.ts.map +1 -1
  50. package/dist/components/Messages.js +17 -83
  51. package/dist/components/Messages.js.map +1 -1
  52. package/dist/components/ProviderKeyInput.d.ts.map +1 -1
  53. package/dist/components/ProviderKeyInput.js +6 -5
  54. package/dist/components/ProviderKeyInput.js.map +1 -1
  55. package/dist/components/SandboxedIframe.d.ts +29 -7
  56. package/dist/components/SandboxedIframe.d.ts.map +1 -1
  57. package/dist/components/SandboxedIframe.js +350 -282
  58. package/dist/components/SandboxedIframe.js.map +1 -1
  59. package/dist/components/message-renderer-registry.d.ts +12 -0
  60. package/dist/components/message-renderer-registry.d.ts.map +1 -0
  61. package/dist/components/message-renderer-registry.js +12 -0
  62. package/dist/components/message-renderer-registry.js.map +1 -0
  63. package/dist/components/sandbox/ArtifactsRuntimeProvider.d.ts +35 -0
  64. package/dist/components/sandbox/ArtifactsRuntimeProvider.d.ts.map +1 -0
  65. package/dist/components/sandbox/ArtifactsRuntimeProvider.js +189 -0
  66. package/dist/components/sandbox/ArtifactsRuntimeProvider.js.map +1 -0
  67. package/dist/components/sandbox/AttachmentsRuntimeProvider.d.ts +17 -0
  68. package/dist/components/sandbox/AttachmentsRuntimeProvider.d.ts.map +1 -0
  69. package/dist/components/sandbox/AttachmentsRuntimeProvider.js +64 -0
  70. package/dist/components/sandbox/AttachmentsRuntimeProvider.js.map +1 -0
  71. package/dist/components/sandbox/ConsoleRuntimeProvider.d.ts +42 -0
  72. package/dist/components/sandbox/ConsoleRuntimeProvider.d.ts.map +1 -0
  73. package/dist/components/sandbox/ConsoleRuntimeProvider.js +161 -0
  74. package/dist/components/sandbox/ConsoleRuntimeProvider.js.map +1 -0
  75. package/dist/components/sandbox/FileDownloadRuntimeProvider.d.ts +30 -0
  76. package/dist/components/sandbox/FileDownloadRuntimeProvider.d.ts.map +1 -0
  77. package/dist/components/sandbox/FileDownloadRuntimeProvider.js +97 -0
  78. package/dist/components/sandbox/FileDownloadRuntimeProvider.js.map +1 -0
  79. package/dist/components/sandbox/RuntimeMessageBridge.d.ts +19 -0
  80. package/dist/components/sandbox/RuntimeMessageBridge.d.ts.map +1 -0
  81. package/dist/components/sandbox/RuntimeMessageBridge.js +74 -0
  82. package/dist/components/sandbox/RuntimeMessageBridge.js.map +1 -0
  83. package/dist/components/sandbox/RuntimeMessageRouter.d.ts +65 -0
  84. package/dist/components/sandbox/RuntimeMessageRouter.d.ts.map +1 -0
  85. package/dist/components/sandbox/RuntimeMessageRouter.js +168 -0
  86. package/dist/components/sandbox/RuntimeMessageRouter.js.map +1 -0
  87. package/dist/components/sandbox/SandboxRuntimeProvider.d.ts +33 -0
  88. package/dist/components/sandbox/SandboxRuntimeProvider.d.ts.map +1 -0
  89. package/dist/components/sandbox/SandboxRuntimeProvider.js +2 -0
  90. package/dist/components/sandbox/SandboxRuntimeProvider.js.map +1 -0
  91. package/dist/dialogs/ApiKeyPromptDialog.d.ts.map +1 -1
  92. package/dist/dialogs/ApiKeyPromptDialog.js +2 -5
  93. package/dist/dialogs/ApiKeyPromptDialog.js.map +1 -1
  94. package/dist/dialogs/ModelSelector.js.map +1 -1
  95. package/dist/dialogs/PersistentStorageDialog.d.ts +17 -0
  96. package/dist/dialogs/PersistentStorageDialog.d.ts.map +1 -0
  97. package/dist/dialogs/PersistentStorageDialog.js +144 -0
  98. package/dist/dialogs/PersistentStorageDialog.js.map +1 -0
  99. package/dist/dialogs/SessionListDialog.d.ts +19 -0
  100. package/dist/dialogs/SessionListDialog.d.ts.map +1 -0
  101. package/dist/dialogs/SessionListDialog.js +152 -0
  102. package/dist/dialogs/SessionListDialog.js.map +1 -0
  103. package/dist/dialogs/SettingsDialog.d.ts.map +1 -1
  104. package/dist/dialogs/SettingsDialog.js +1 -0
  105. package/dist/dialogs/SettingsDialog.js.map +1 -1
  106. package/dist/index.d.ts +34 -16
  107. package/dist/index.d.ts.map +1 -1
  108. package/dist/index.js +32 -14
  109. package/dist/index.js.map +1 -1
  110. package/dist/prompts/prompts.d.ts +11 -0
  111. package/dist/prompts/prompts.d.ts.map +1 -0
  112. package/dist/prompts/prompts.js +272 -0
  113. package/dist/prompts/prompts.js.map +1 -0
  114. package/dist/storage/app-storage.d.ts +17 -12
  115. package/dist/storage/app-storage.d.ts.map +1 -1
  116. package/dist/storage/app-storage.js +13 -20
  117. package/dist/storage/app-storage.js.map +1 -1
  118. package/dist/storage/backends/indexeddb-storage-backend.d.ts +27 -0
  119. package/dist/storage/backends/indexeddb-storage-backend.d.ts.map +1 -0
  120. package/dist/storage/backends/indexeddb-storage-backend.js +166 -0
  121. package/dist/storage/backends/indexeddb-storage-backend.js.map +1 -0
  122. package/dist/storage/store.d.ts +23 -0
  123. package/dist/storage/store.d.ts.map +1 -0
  124. package/dist/storage/store.js +26 -0
  125. package/dist/storage/store.js.map +1 -0
  126. package/dist/storage/stores/provider-keys-store.d.ts +14 -0
  127. package/dist/storage/stores/provider-keys-store.d.ts.map +1 -0
  128. package/dist/storage/stores/provider-keys-store.js +27 -0
  129. package/dist/storage/stores/provider-keys-store.js.map +1 -0
  130. package/dist/storage/stores/sessions-store.d.ts +31 -0
  131. package/dist/storage/stores/sessions-store.d.ts.map +1 -0
  132. package/dist/storage/stores/sessions-store.js +113 -0
  133. package/dist/storage/stores/sessions-store.js.map +1 -0
  134. package/dist/storage/stores/settings-store.d.ts +14 -0
  135. package/dist/storage/stores/settings-store.d.ts.map +1 -0
  136. package/dist/storage/stores/settings-store.js +28 -0
  137. package/dist/storage/stores/settings-store.js.map +1 -0
  138. package/dist/storage/types.d.ts +156 -22
  139. package/dist/storage/types.d.ts.map +1 -1
  140. package/dist/tools/artifacts/ArtifactElement.d.ts +0 -1
  141. package/dist/tools/artifacts/ArtifactElement.d.ts.map +1 -1
  142. package/dist/tools/artifacts/ArtifactElement.js +0 -1
  143. package/dist/tools/artifacts/ArtifactElement.js.map +1 -1
  144. package/dist/tools/artifacts/ArtifactPill.d.ts +4 -0
  145. package/dist/tools/artifacts/ArtifactPill.d.ts.map +1 -0
  146. package/dist/tools/artifacts/ArtifactPill.js +22 -0
  147. package/dist/tools/artifacts/ArtifactPill.js.map +1 -0
  148. package/dist/tools/artifacts/Console.d.ts +18 -0
  149. package/dist/tools/artifacts/Console.d.ts.map +1 -0
  150. package/dist/tools/artifacts/Console.js +95 -0
  151. package/dist/tools/artifacts/Console.js.map +1 -0
  152. package/dist/tools/artifacts/DocxArtifact.d.ts +22 -0
  153. package/dist/tools/artifacts/DocxArtifact.d.ts.map +1 -0
  154. package/dist/tools/artifacts/DocxArtifact.js +208 -0
  155. package/dist/tools/artifacts/DocxArtifact.js.map +1 -0
  156. package/dist/tools/artifacts/ExcelArtifact.d.ts +24 -0
  157. package/dist/tools/artifacts/ExcelArtifact.d.ts.map +1 -0
  158. package/dist/tools/artifacts/ExcelArtifact.js +216 -0
  159. package/dist/tools/artifacts/ExcelArtifact.js.map +1 -0
  160. package/dist/tools/artifacts/GenericArtifact.d.ts +19 -0
  161. package/dist/tools/artifacts/GenericArtifact.d.ts.map +1 -0
  162. package/dist/tools/artifacts/GenericArtifact.js +117 -0
  163. package/dist/tools/artifacts/GenericArtifact.js.map +1 -0
  164. package/dist/tools/artifacts/HtmlArtifact.d.ts +8 -11
  165. package/dist/tools/artifacts/HtmlArtifact.d.ts.map +1 -1
  166. package/dist/tools/artifacts/HtmlArtifact.js +56 -88
  167. package/dist/tools/artifacts/HtmlArtifact.js.map +1 -1
  168. package/dist/tools/artifacts/ImageArtifact.d.ts +20 -0
  169. package/dist/tools/artifacts/ImageArtifact.d.ts.map +1 -0
  170. package/dist/tools/artifacts/ImageArtifact.js +120 -0
  171. package/dist/tools/artifacts/ImageArtifact.js.map +1 -0
  172. package/dist/tools/artifacts/MarkdownArtifact.d.ts +0 -1
  173. package/dist/tools/artifacts/MarkdownArtifact.d.ts.map +1 -1
  174. package/dist/tools/artifacts/MarkdownArtifact.js +0 -4
  175. package/dist/tools/artifacts/MarkdownArtifact.js.map +1 -1
  176. package/dist/tools/artifacts/PdfArtifact.d.ts +25 -0
  177. package/dist/tools/artifacts/PdfArtifact.d.ts.map +1 -0
  178. package/dist/tools/artifacts/PdfArtifact.js +184 -0
  179. package/dist/tools/artifacts/PdfArtifact.js.map +1 -0
  180. package/dist/tools/artifacts/SvgArtifact.d.ts +0 -1
  181. package/dist/tools/artifacts/SvgArtifact.d.ts.map +1 -1
  182. package/dist/tools/artifacts/SvgArtifact.js +0 -4
  183. package/dist/tools/artifacts/SvgArtifact.js.map +1 -1
  184. package/dist/tools/artifacts/TextArtifact.d.ts +0 -1
  185. package/dist/tools/artifacts/TextArtifact.d.ts.map +1 -1
  186. package/dist/tools/artifacts/TextArtifact.js +0 -4
  187. package/dist/tools/artifacts/TextArtifact.js.map +1 -1
  188. package/dist/tools/artifacts/artifacts-tool-renderer.d.ts +11 -0
  189. package/dist/tools/artifacts/artifacts-tool-renderer.d.ts.map +1 -0
  190. package/dist/tools/artifacts/artifacts-tool-renderer.js +262 -0
  191. package/dist/tools/artifacts/artifacts-tool-renderer.js.map +1 -0
  192. package/dist/tools/artifacts/artifacts.d.ts +10 -13
  193. package/dist/tools/artifacts/artifacts.d.ts.map +1 -1
  194. package/dist/tools/artifacts/artifacts.js +166 -344
  195. package/dist/tools/artifacts/artifacts.js.map +1 -1
  196. package/dist/tools/artifacts/index.d.ts +1 -0
  197. package/dist/tools/artifacts/index.d.ts.map +1 -1
  198. package/dist/tools/artifacts/index.js +1 -0
  199. package/dist/tools/artifacts/index.js.map +1 -1
  200. package/dist/tools/extract-document.d.ts +24 -0
  201. package/dist/tools/extract-document.d.ts.map +1 -0
  202. package/dist/tools/extract-document.js +193 -0
  203. package/dist/tools/extract-document.js.map +1 -0
  204. package/dist/tools/index.d.ts +9 -7
  205. package/dist/tools/index.d.ts.map +1 -1
  206. package/dist/tools/index.js +17 -13
  207. package/dist/tools/index.js.map +1 -1
  208. package/dist/tools/javascript-repl.d.ts +16 -15
  209. package/dist/tools/javascript-repl.d.ts.map +1 -1
  210. package/dist/tools/javascript-repl.js +101 -133
  211. package/dist/tools/javascript-repl.js.map +1 -1
  212. package/dist/tools/renderer-registry.d.ts +12 -0
  213. package/dist/tools/renderer-registry.d.ts.map +1 -1
  214. package/dist/tools/renderer-registry.js +78 -0
  215. package/dist/tools/renderer-registry.js.map +1 -1
  216. package/dist/tools/renderers/BashRenderer.d.ts +2 -4
  217. package/dist/tools/renderers/BashRenderer.d.ts.map +1 -1
  218. package/dist/tools/renderers/BashRenderer.js +30 -26
  219. package/dist/tools/renderers/BashRenderer.js.map +1 -1
  220. package/dist/tools/renderers/CalculateRenderer.d.ts +2 -4
  221. package/dist/tools/renderers/CalculateRenderer.d.ts.map +1 -1
  222. package/dist/tools/renderers/CalculateRenderer.js +32 -28
  223. package/dist/tools/renderers/CalculateRenderer.js.map +1 -1
  224. package/dist/tools/renderers/DefaultRenderer.d.ts +2 -4
  225. package/dist/tools/renderers/DefaultRenderer.d.ts.map +1 -1
  226. package/dist/tools/renderers/DefaultRenderer.js +78 -18
  227. package/dist/tools/renderers/DefaultRenderer.js.map +1 -1
  228. package/dist/tools/renderers/GetCurrentTimeRenderer.d.ts +2 -4
  229. package/dist/tools/renderers/GetCurrentTimeRenderer.d.ts.map +1 -1
  230. package/dist/tools/renderers/GetCurrentTimeRenderer.js +57 -21
  231. package/dist/tools/renderers/GetCurrentTimeRenderer.js.map +1 -1
  232. package/dist/tools/types.d.ts +5 -2
  233. package/dist/tools/types.d.ts.map +1 -1
  234. package/dist/utils/i18n.d.ts +424 -1
  235. package/dist/utils/i18n.d.ts.map +1 -1
  236. package/dist/utils/i18n.js +131 -7
  237. package/dist/utils/i18n.js.map +1 -1
  238. package/example/package.json +2 -1
  239. package/example/src/custom-messages.ts +112 -0
  240. package/example/src/main.ts +391 -38
  241. package/package.json +48 -43
  242. package/scripts/count-prompt-tokens.ts +88 -0
  243. package/src/ChatPanel.ts +93 -101
  244. package/src/{state/agent-session.ts → agent/agent.ts} +80 -55
  245. package/src/{state → agent}/transports/AppTransport.ts +6 -6
  246. package/src/{state → agent}/transports/ProviderTransport.ts +13 -7
  247. package/src/{state → agent}/transports/types.ts +8 -2
  248. package/src/components/AgentInterface.ts +32 -16
  249. package/src/components/ConsoleBlock.ts +5 -1
  250. package/src/components/ExpandableSection.ts +46 -0
  251. package/src/components/MessageEditor.ts +159 -5
  252. package/src/components/MessageList.ts +18 -3
  253. package/src/components/Messages.ts +48 -89
  254. package/src/components/ProviderKeyInput.ts +6 -5
  255. package/src/components/SandboxedIframe.ts +412 -321
  256. package/src/components/message-renderer-registry.ts +28 -0
  257. package/src/components/sandbox/ArtifactsRuntimeProvider.ts +219 -0
  258. package/src/components/sandbox/AttachmentsRuntimeProvider.ts +66 -0
  259. package/src/components/sandbox/ConsoleRuntimeProvider.ts +187 -0
  260. package/src/components/sandbox/FileDownloadRuntimeProvider.ts +110 -0
  261. package/src/components/sandbox/RuntimeMessageBridge.ts +82 -0
  262. package/src/components/sandbox/RuntimeMessageRouter.ts +216 -0
  263. package/src/components/sandbox/SandboxRuntimeProvider.ts +35 -0
  264. package/src/dialogs/ApiKeyPromptDialog.ts +2 -5
  265. package/src/dialogs/ModelSelector.ts +2 -2
  266. package/src/dialogs/PersistentStorageDialog.ts +141 -0
  267. package/src/dialogs/SessionListDialog.ts +148 -0
  268. package/src/dialogs/SettingsDialog.ts +1 -0
  269. package/src/index.ts +61 -20
  270. package/src/prompts/prompts.ts +282 -0
  271. package/src/storage/app-storage.ts +27 -24
  272. package/src/storage/backends/indexeddb-storage-backend.ts +193 -0
  273. package/src/storage/store.ts +33 -0
  274. package/src/storage/stores/provider-keys-store.ts +33 -0
  275. package/src/storage/stores/sessions-store.ts +130 -0
  276. package/src/storage/stores/settings-store.ts +34 -0
  277. package/src/storage/types.ts +182 -22
  278. package/src/tools/artifacts/ArtifactElement.ts +0 -1
  279. package/src/tools/artifacts/ArtifactPill.ts +25 -0
  280. package/src/tools/artifacts/Console.ts +93 -0
  281. package/src/tools/artifacts/DocxArtifact.ts +213 -0
  282. package/src/tools/artifacts/ExcelArtifact.ts +231 -0
  283. package/src/tools/artifacts/GenericArtifact.ts +117 -0
  284. package/src/tools/artifacts/HtmlArtifact.ts +64 -94
  285. package/src/tools/artifacts/ImageArtifact.ts +116 -0
  286. package/src/tools/artifacts/MarkdownArtifact.ts +0 -1
  287. package/src/tools/artifacts/PdfArtifact.ts +201 -0
  288. package/src/tools/artifacts/SvgArtifact.ts +0 -1
  289. package/src/tools/artifacts/TextArtifact.ts +0 -1
  290. package/src/tools/artifacts/artifacts-tool-renderer.ts +298 -0
  291. package/src/tools/artifacts/artifacts.ts +190 -366
  292. package/src/tools/artifacts/index.ts +1 -0
  293. package/src/tools/extract-document.ts +250 -0
  294. package/src/tools/index.ts +25 -14
  295. package/src/tools/javascript-repl.ts +138 -160
  296. package/src/tools/renderer-registry.ts +98 -0
  297. package/src/tools/renderers/BashRenderer.ts +33 -30
  298. package/src/tools/renderers/CalculateRenderer.ts +36 -31
  299. package/src/tools/renderers/DefaultRenderer.ts +84 -21
  300. package/src/tools/renderers/GetCurrentTimeRenderer.ts +68 -23
  301. package/src/tools/types.ts +10 -2
  302. package/src/utils/i18n.ts +203 -8
  303. package/dist/state/agent-session.d.ts.map +0 -1
  304. package/dist/state/agent-session.js.map +0 -1
  305. package/dist/state/transports/AppTransport.d.ts.map +0 -1
  306. package/dist/state/transports/ProviderTransport.d.ts.map +0 -1
  307. package/dist/state/transports/ProviderTransport.js.map +0 -1
  308. package/dist/state/transports/index.js.map +0 -1
  309. package/dist/state/transports/proxy-types.js.map +0 -1
  310. package/dist/state/transports/types.d.ts +0 -11
  311. package/dist/state/transports/types.d.ts.map +0 -1
  312. package/dist/storage/backends/chrome-storage-backend.d.ts +0 -18
  313. package/dist/storage/backends/chrome-storage-backend.d.ts.map +0 -1
  314. package/dist/storage/backends/chrome-storage-backend.js +0 -67
  315. package/dist/storage/backends/chrome-storage-backend.js.map +0 -1
  316. package/dist/storage/backends/indexeddb-backend.d.ts +0 -20
  317. package/dist/storage/backends/indexeddb-backend.d.ts.map +0 -1
  318. package/dist/storage/backends/indexeddb-backend.js +0 -89
  319. package/dist/storage/backends/indexeddb-backend.js.map +0 -1
  320. package/dist/storage/backends/local-storage-backend.d.ts +0 -18
  321. package/dist/storage/backends/local-storage-backend.d.ts.map +0 -1
  322. package/dist/storage/backends/local-storage-backend.js +0 -69
  323. package/dist/storage/backends/local-storage-backend.js.map +0 -1
  324. package/dist/storage/repositories/provider-keys-repository.d.ts +0 -34
  325. package/dist/storage/repositories/provider-keys-repository.d.ts.map +0 -1
  326. package/dist/storage/repositories/provider-keys-repository.js +0 -50
  327. package/dist/storage/repositories/provider-keys-repository.js.map +0 -1
  328. package/dist/storage/repositories/settings-repository.d.ts +0 -34
  329. package/dist/storage/repositories/settings-repository.d.ts.map +0 -1
  330. package/dist/storage/repositories/settings-repository.js +0 -46
  331. package/dist/storage/repositories/settings-repository.js.map +0 -1
  332. package/src/storage/backends/chrome-storage-backend.ts +0 -82
  333. package/src/storage/backends/indexeddb-backend.ts +0 -107
  334. package/src/storage/backends/local-storage-backend.ts +0 -74
  335. package/src/storage/repositories/provider-keys-repository.ts +0 -55
  336. package/src/storage/repositories/settings-repository.ts +0 -51
  337. /package/dist/{state → agent}/transports/index.d.ts +0 -0
  338. /package/dist/{state → agent}/transports/index.js +0 -0
  339. /package/dist/{state → agent}/transports/proxy-types.d.ts +0 -0
  340. /package/dist/{state → agent}/transports/proxy-types.js +0 -0
  341. /package/dist/{state → agent}/transports/types.js +0 -0
  342. /package/dist/{state → agent}/types.d.ts +0 -0
  343. /package/dist/{state → agent}/types.js +0 -0
  344. /package/src/{state → agent}/transports/index.ts +0 -0
  345. /package/src/{state → agent}/transports/proxy-types.ts +0 -0
  346. /package/src/{state → agent}/types.ts +0 -0
@@ -0,0 +1,216 @@
1
+ import type { SandboxRuntimeProvider } from "./SandboxRuntimeProvider.js";
2
+
3
+ // Type declaration for chrome extension API (when available)
4
+ declare const chrome: any;
5
+
6
+ /**
7
+ * Message consumer interface - components that want to receive messages from sandboxes
8
+ */
9
+ export interface MessageConsumer {
10
+ /**
11
+ * Handle a message from a sandbox.
12
+ * All consumers receive all messages - decide internally what to handle.
13
+ */
14
+ handleMessage(message: any): Promise<void>;
15
+ }
16
+
17
+ /**
18
+ * Sandbox context - tracks active sandboxes and their consumers
19
+ */
20
+ interface SandboxContext {
21
+ sandboxId: string;
22
+ iframe: HTMLIFrameElement | null; // null until setSandboxIframe() or null for user scripts
23
+ providers: SandboxRuntimeProvider[];
24
+ consumers: Set<MessageConsumer>;
25
+ }
26
+
27
+ /**
28
+ * Centralized message router for all runtime communication.
29
+ *
30
+ * This singleton replaces all individual window.addEventListener("message") calls
31
+ * with a single global listener that routes messages to the appropriate handlers.
32
+ * Also handles user script messages from chrome.runtime.onUserScriptMessage.
33
+ *
34
+ * Benefits:
35
+ * - Single global listener instead of multiple independent listeners
36
+ * - Automatic cleanup when sandboxes are destroyed
37
+ * - Support for bidirectional communication (providers) and broadcasting (consumers)
38
+ * - Works with both sandbox iframes and user scripts
39
+ * - Clear lifecycle management
40
+ */
41
+ export class RuntimeMessageRouter {
42
+ private sandboxes = new Map<string, SandboxContext>();
43
+ private messageListener: ((e: MessageEvent) => void) | null = null;
44
+ private userScriptMessageListener:
45
+ | ((message: any, sender: any, sendResponse: (response: any) => void) => boolean)
46
+ | null = null;
47
+
48
+ /**
49
+ * Register a new sandbox with its runtime providers.
50
+ * Call this BEFORE creating the iframe (for sandbox contexts) or executing user script.
51
+ */
52
+ registerSandbox(sandboxId: string, providers: SandboxRuntimeProvider[], consumers: MessageConsumer[]): void {
53
+ this.sandboxes.set(sandboxId, {
54
+ sandboxId,
55
+ iframe: null, // Will be set via setSandboxIframe() for sandbox contexts
56
+ providers,
57
+ consumers: new Set(consumers),
58
+ });
59
+
60
+ // Setup global listener if not already done
61
+ this.setupListener();
62
+ }
63
+
64
+ /**
65
+ * Update the iframe reference for a sandbox.
66
+ * Call this AFTER creating the iframe.
67
+ * This is needed so providers can send responses back to the sandbox.
68
+ */
69
+ setSandboxIframe(sandboxId: string, iframe: HTMLIFrameElement): void {
70
+ const context = this.sandboxes.get(sandboxId);
71
+ if (context) {
72
+ context.iframe = iframe;
73
+ }
74
+ }
75
+
76
+ /**
77
+ * Unregister a sandbox and remove all its consumers.
78
+ * Call this when the sandbox is destroyed.
79
+ */
80
+ unregisterSandbox(sandboxId: string): void {
81
+ this.sandboxes.delete(sandboxId);
82
+
83
+ // If no more sandboxes, remove global listeners
84
+ if (this.sandboxes.size === 0) {
85
+ // Remove iframe listener
86
+ if (this.messageListener) {
87
+ window.removeEventListener("message", this.messageListener);
88
+ this.messageListener = null;
89
+ }
90
+
91
+ // Remove user script listener
92
+ if (this.userScriptMessageListener && typeof chrome !== "undefined" && chrome.runtime?.onUserScriptMessage) {
93
+ chrome.runtime.onUserScriptMessage.removeListener(this.userScriptMessageListener);
94
+ this.userScriptMessageListener = null;
95
+ }
96
+ }
97
+ }
98
+
99
+ /**
100
+ * Add a message consumer for a sandbox.
101
+ * Consumers receive broadcast messages (console, execution-complete, etc.)
102
+ */
103
+ addConsumer(sandboxId: string, consumer: MessageConsumer): void {
104
+ const context = this.sandboxes.get(sandboxId);
105
+ if (context) {
106
+ context.consumers.add(consumer);
107
+ }
108
+ }
109
+
110
+ /**
111
+ * Remove a message consumer from a sandbox.
112
+ */
113
+ removeConsumer(sandboxId: string, consumer: MessageConsumer): void {
114
+ const context = this.sandboxes.get(sandboxId);
115
+ if (context) {
116
+ context.consumers.delete(consumer);
117
+ }
118
+ }
119
+
120
+ /**
121
+ * Setup the global message listeners (called automatically)
122
+ */
123
+ private setupListener(): void {
124
+ // Setup sandbox iframe listener
125
+ if (!this.messageListener) {
126
+ this.messageListener = async (e: MessageEvent) => {
127
+ const { sandboxId, messageId } = e.data;
128
+ if (!sandboxId) return;
129
+
130
+ const context = this.sandboxes.get(sandboxId);
131
+ if (!context) {
132
+ return;
133
+ }
134
+
135
+ // Create respond() function for bidirectional communication
136
+ const respond = (response: any) => {
137
+ context.iframe?.contentWindow?.postMessage(
138
+ {
139
+ type: "runtime-response",
140
+ messageId,
141
+ sandboxId,
142
+ ...response,
143
+ },
144
+ "*",
145
+ );
146
+ };
147
+
148
+ // 1. Try provider handlers first (for bidirectional comm)
149
+ for (const provider of context.providers) {
150
+ if (provider.handleMessage) {
151
+ await provider.handleMessage(e.data, respond);
152
+ // Don't stop - let consumers also handle the message
153
+ }
154
+ }
155
+
156
+ // 2. Broadcast to consumers (one-way messages or lifecycle events)
157
+ for (const consumer of context.consumers) {
158
+ await consumer.handleMessage(e.data);
159
+ // Don't stop - let all consumers see the message
160
+ }
161
+ };
162
+
163
+ window.addEventListener("message", this.messageListener);
164
+ }
165
+
166
+ // Setup user script message listener
167
+ if (!this.userScriptMessageListener) {
168
+ // Guard: check if we're in extension context
169
+ if (typeof chrome === "undefined" || !chrome.runtime?.onUserScriptMessage) {
170
+ return;
171
+ }
172
+
173
+ this.userScriptMessageListener = (message: any, _sender: any, sendResponse: (response: any) => void) => {
174
+ const { sandboxId } = message;
175
+ if (!sandboxId) return false;
176
+
177
+ const context = this.sandboxes.get(sandboxId);
178
+ if (!context) return false;
179
+
180
+ const respond = (response: any) => {
181
+ sendResponse({
182
+ ...response,
183
+ sandboxId,
184
+ });
185
+ };
186
+
187
+ // Route to providers (async)
188
+ (async () => {
189
+ // 1. Try provider handlers first (for bidirectional comm)
190
+ for (const provider of context.providers) {
191
+ if (provider.handleMessage) {
192
+ await provider.handleMessage(message, respond);
193
+ // Don't stop - let consumers also handle the message
194
+ }
195
+ }
196
+
197
+ // 2. Broadcast to consumers (one-way messages or lifecycle events)
198
+ for (const consumer of context.consumers) {
199
+ await consumer.handleMessage(message);
200
+ // Don't stop - let all consumers see the message
201
+ }
202
+ })();
203
+
204
+ return true; // Indicates async response
205
+ };
206
+
207
+ chrome.runtime.onUserScriptMessage.addListener(this.userScriptMessageListener);
208
+ }
209
+ }
210
+ }
211
+
212
+ /**
213
+ * Global singleton instance.
214
+ * Import this from wherever you need to interact with the message router.
215
+ */
216
+ export const RUNTIME_MESSAGE_ROUTER = new RuntimeMessageRouter();
@@ -0,0 +1,35 @@
1
+ /**
2
+ * Interface for providing runtime capabilities to sandboxed iframes.
3
+ * Each provider injects data and runtime functions into the sandbox context.
4
+ */
5
+ export interface SandboxRuntimeProvider {
6
+ /**
7
+ * Returns data to inject into window scope.
8
+ * Keys become window properties (e.g., { attachments: [...] } -> window.attachments)
9
+ */
10
+ getData(): Record<string, any>;
11
+
12
+ /**
13
+ * Returns a runtime function that will be stringified and executed in the sandbox.
14
+ * The function receives sandboxId and has access to data from getData() via window.
15
+ *
16
+ * IMPORTANT: This function will be converted to string via .toString() and injected
17
+ * into the sandbox, so it cannot reference external variables or imports.
18
+ */
19
+ getRuntime(): (sandboxId: string) => void;
20
+
21
+ /**
22
+ * Optional message handler for bidirectional communication.
23
+ * All providers receive all messages - decide internally what to handle.
24
+ *
25
+ * @param message - The message from the sandbox
26
+ * @param respond - Function to send a response back to the sandbox
27
+ */
28
+ handleMessage?(message: any, respond: (response: any) => void): Promise<void>;
29
+
30
+ /**
31
+ * Optional documentation describing what globals/functions this provider injects.
32
+ * This will be appended to tool descriptions dynamically so the LLM knows what's available.
33
+ */
34
+ getDescription(): string;
35
+ }
@@ -29,7 +29,7 @@ export class ApiKeyPromptDialog extends DialogBase {
29
29
 
30
30
  // Poll for key existence - when key is added, resolve and close
31
31
  const checkInterval = setInterval(async () => {
32
- const hasKey = await getAppStorage().providerKeys.hasKey(this.provider);
32
+ const hasKey = !!(await getAppStorage().providerKeys.get(this.provider));
33
33
  if (hasKey) {
34
34
  clearInterval(checkInterval);
35
35
  if (this.resolvePromise) {
@@ -64,11 +64,8 @@ export class ApiKeyPromptDialog extends DialogBase {
64
64
  children: html`
65
65
  ${DialogHeader({
66
66
  title: i18n("API Key Required"),
67
- description: i18n("Enter your API key for {provider}").replace("{provider}", this.provider),
68
67
  })}
69
- <div class="mt-4">
70
- <provider-key-input .provider=${this.provider}></provider-key-input>
71
- </div>
68
+ <provider-key-input .provider=${this.provider}></provider-key-input>
72
69
  `,
73
70
  })}
74
71
  `;
@@ -101,7 +101,7 @@ export class ModelSelector extends DialogBase {
101
101
 
102
102
  // Fetch details for each model and convert to Model format
103
103
  const ollamaModelPromises: Promise<Model<any> | null>[] = models
104
- .map(async (model) => {
104
+ .map(async (model: any) => {
105
105
  try {
106
106
  // Get model details
107
107
  const details = await ollama.show({
@@ -144,7 +144,7 @@ export class ModelSelector extends DialogBase {
144
144
  return null;
145
145
  }
146
146
  })
147
- .filter((m) => m !== null);
147
+ .filter((m: any) => m !== null);
148
148
 
149
149
  const results = await Promise.all(ollamaModelPromises);
150
150
  this.ollamaModels = results.filter((m): m is Model<any> => m !== null);
@@ -0,0 +1,141 @@
1
+ import { Button, DialogBase, DialogContent, DialogHeader, html } from "@mariozechner/mini-lit";
2
+ import { customElement, state } from "lit/decorators.js";
3
+ import { i18n } from "../utils/i18n.js";
4
+
5
+ @customElement("persistent-storage-dialog")
6
+ export class PersistentStorageDialog extends DialogBase {
7
+ @state() private requesting = false;
8
+
9
+ private resolvePromise?: (userApproved: boolean) => void;
10
+
11
+ protected modalWidth = "min(500px, 90vw)";
12
+ protected modalHeight = "auto";
13
+
14
+ /**
15
+ * Request persistent storage permission.
16
+ * Returns true if browser granted persistent storage, false otherwise.
17
+ */
18
+ static async request(): Promise<boolean> {
19
+ // Check if already persisted
20
+ if (navigator.storage?.persisted) {
21
+ const alreadyPersisted = await navigator.storage.persisted();
22
+ if (alreadyPersisted) {
23
+ console.log("✓ Persistent storage already granted");
24
+ return true;
25
+ }
26
+ }
27
+
28
+ // Show dialog and wait for user response
29
+ const dialog = new PersistentStorageDialog();
30
+ dialog.open();
31
+
32
+ const userApproved = await new Promise<boolean>((resolve) => {
33
+ dialog.resolvePromise = resolve;
34
+ });
35
+
36
+ if (!userApproved) {
37
+ console.warn("⚠ User declined persistent storage - sessions may be lost");
38
+ return false;
39
+ }
40
+
41
+ // User approved, request from browser
42
+ if (!navigator.storage?.persist) {
43
+ console.warn("⚠ Persistent storage API not available");
44
+ return false;
45
+ }
46
+
47
+ try {
48
+ const granted = await navigator.storage.persist();
49
+ if (granted) {
50
+ console.log("✓ Persistent storage granted - sessions will be preserved");
51
+ } else {
52
+ console.warn("⚠ Browser denied persistent storage - sessions may be lost under storage pressure");
53
+ }
54
+ return granted;
55
+ } catch (error) {
56
+ console.error("Failed to request persistent storage:", error);
57
+ return false;
58
+ }
59
+ }
60
+
61
+ private handleGrant() {
62
+ if (this.resolvePromise) {
63
+ this.resolvePromise(true);
64
+ this.resolvePromise = undefined;
65
+ }
66
+ this.close();
67
+ }
68
+
69
+ private handleDeny() {
70
+ if (this.resolvePromise) {
71
+ this.resolvePromise(false);
72
+ this.resolvePromise = undefined;
73
+ }
74
+ this.close();
75
+ }
76
+
77
+ override close() {
78
+ super.close();
79
+ if (this.resolvePromise) {
80
+ this.resolvePromise(false);
81
+ }
82
+ }
83
+
84
+ protected override renderContent() {
85
+ return html`
86
+ ${DialogContent({
87
+ children: html`
88
+ ${DialogHeader({
89
+ title: i18n("Storage Permission Required"),
90
+ description: i18n("This app needs persistent storage to save your conversations"),
91
+ })}
92
+
93
+ <div class="mt-4 flex flex-col gap-4">
94
+ <div class="flex gap-3 p-4 bg-warning/10 border border-warning/20 rounded-lg">
95
+ <div class="flex-shrink-0 text-warning">
96
+ <svg width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
97
+ <path d="M10.29 3.86L1.82 18a2 2 0 0 0 1.71 3h16.94a2 2 0 0 0 1.71-3L13.71 3.86a2 2 0 0 0-3.42 0z"></path>
98
+ <line x1="12" y1="9" x2="12" y2="13"></line>
99
+ <line x1="12" y1="17" x2="12.01" y2="17"></line>
100
+ </svg>
101
+ </div>
102
+ <div class="text-sm">
103
+ <p class="font-medium text-foreground mb-1">${i18n("Why is this needed?")}</p>
104
+ <p class="text-muted-foreground">
105
+ ${i18n(
106
+ "Without persistent storage, your browser may delete saved conversations when it needs disk space. Granting this permission ensures your chat history is preserved.",
107
+ )}
108
+ </p>
109
+ </div>
110
+ </div>
111
+
112
+ <div class="text-sm text-muted-foreground">
113
+ <p class="mb-2">${i18n("What this means:")}</p>
114
+ <ul class="list-disc list-inside space-y-1 ml-2">
115
+ <li>${i18n("Your conversations will be saved locally in your browser")}</li>
116
+ <li>${i18n("Data will not be deleted automatically to free up space")}</li>
117
+ <li>${i18n("You can still manually clear data at any time")}</li>
118
+ <li>${i18n("No data is sent to external servers")}</li>
119
+ </ul>
120
+ </div>
121
+ </div>
122
+
123
+ <div class="mt-6 flex gap-3 justify-end">
124
+ ${Button({
125
+ variant: "outline",
126
+ onClick: () => this.handleDeny(),
127
+ disabled: this.requesting,
128
+ children: i18n("Continue Anyway"),
129
+ })}
130
+ ${Button({
131
+ variant: "default",
132
+ onClick: () => this.handleGrant(),
133
+ disabled: this.requesting,
134
+ children: this.requesting ? i18n("Requesting...") : i18n("Grant Permission"),
135
+ })}
136
+ </div>
137
+ `,
138
+ })}
139
+ `;
140
+ }
141
+ }
@@ -0,0 +1,148 @@
1
+ import { DialogBase, DialogContent, DialogHeader, html } from "@mariozechner/mini-lit";
2
+ import { customElement, state } from "lit/decorators.js";
3
+ import { getAppStorage } from "../storage/app-storage.js";
4
+ import type { SessionMetadata } from "../storage/types.js";
5
+ import { formatUsage } from "../utils/format.js";
6
+ import { i18n } from "../utils/i18n.js";
7
+
8
+ @customElement("session-list-dialog")
9
+ export class SessionListDialog extends DialogBase {
10
+ @state() private sessions: SessionMetadata[] = [];
11
+ @state() private loading = true;
12
+
13
+ private onSelectCallback?: (sessionId: string) => void;
14
+ private onDeleteCallback?: (sessionId: string) => void;
15
+ private deletedSessions = new Set<string>();
16
+ private closedViaSelection = false;
17
+
18
+ protected modalWidth = "min(600px, 90vw)";
19
+ protected modalHeight = "min(700px, 90vh)";
20
+
21
+ static async open(onSelect: (sessionId: string) => void, onDelete?: (sessionId: string) => void) {
22
+ const dialog = new SessionListDialog();
23
+ dialog.onSelectCallback = onSelect;
24
+ dialog.onDeleteCallback = onDelete;
25
+ dialog.open();
26
+ await dialog.loadSessions();
27
+ }
28
+
29
+ private async loadSessions() {
30
+ this.loading = true;
31
+ try {
32
+ const storage = getAppStorage();
33
+ this.sessions = await storage.sessions.getAllMetadata();
34
+ } catch (err) {
35
+ console.error("Failed to load sessions:", err);
36
+ this.sessions = [];
37
+ } finally {
38
+ this.loading = false;
39
+ }
40
+ }
41
+
42
+ private async handleDelete(sessionId: string, event: Event) {
43
+ event.stopPropagation();
44
+
45
+ if (!confirm(i18n("Delete this session?"))) {
46
+ return;
47
+ }
48
+
49
+ try {
50
+ const storage = getAppStorage();
51
+ if (!storage.sessions) return;
52
+
53
+ await storage.sessions.deleteSession(sessionId);
54
+ await this.loadSessions();
55
+
56
+ // Track deleted session
57
+ this.deletedSessions.add(sessionId);
58
+ } catch (err) {
59
+ console.error("Failed to delete session:", err);
60
+ }
61
+ }
62
+
63
+ override close() {
64
+ super.close();
65
+
66
+ // Only notify about deleted sessions if dialog wasn't closed via selection
67
+ if (!this.closedViaSelection && this.onDeleteCallback && this.deletedSessions.size > 0) {
68
+ for (const sessionId of this.deletedSessions) {
69
+ this.onDeleteCallback(sessionId);
70
+ }
71
+ }
72
+ }
73
+
74
+ private handleSelect(sessionId: string) {
75
+ this.closedViaSelection = true;
76
+ if (this.onSelectCallback) {
77
+ this.onSelectCallback(sessionId);
78
+ }
79
+ this.close();
80
+ }
81
+
82
+ private formatDate(isoString: string): string {
83
+ const date = new Date(isoString);
84
+ const now = new Date();
85
+ const diff = now.getTime() - date.getTime();
86
+ const days = Math.floor(diff / (1000 * 60 * 60 * 24));
87
+
88
+ if (days === 0) {
89
+ return i18n("Today");
90
+ } else if (days === 1) {
91
+ return i18n("Yesterday");
92
+ } else if (days < 7) {
93
+ return i18n("{days} days ago").replace("{days}", days.toString());
94
+ } else {
95
+ return date.toLocaleDateString();
96
+ }
97
+ }
98
+
99
+ protected override renderContent() {
100
+ return html`
101
+ ${DialogContent({
102
+ className: "h-full flex flex-col",
103
+ children: html`
104
+ ${DialogHeader({
105
+ title: i18n("Sessions"),
106
+ description: i18n("Load a previous conversation"),
107
+ })}
108
+
109
+ <div class="flex-1 overflow-y-auto mt-4 space-y-2">
110
+ ${
111
+ this.loading
112
+ ? html`<div class="text-center py-8 text-muted-foreground">${i18n("Loading...")}</div>`
113
+ : this.sessions.length === 0
114
+ ? html`<div class="text-center py-8 text-muted-foreground">${i18n("No sessions yet")}</div>`
115
+ : this.sessions.map(
116
+ (session) => html`
117
+ <div
118
+ class="group flex items-start gap-3 p-3 rounded-lg border border-border hover:bg-secondary/50 cursor-pointer transition-colors"
119
+ @click=${() => this.handleSelect(session.id)}
120
+ >
121
+ <div class="flex-1 min-w-0">
122
+ <div class="font-medium text-sm text-foreground truncate">${session.title}</div>
123
+ <div class="text-xs text-muted-foreground mt-1">${this.formatDate(session.lastModified)}</div>
124
+ <div class="text-xs text-muted-foreground mt-1">
125
+ ${session.messageCount} ${i18n("messages")} · ${formatUsage(session.usage)}
126
+ </div>
127
+ </div>
128
+ <button
129
+ class="opacity-0 group-hover:opacity-100 p-1 rounded hover:bg-destructive/10 text-destructive transition-opacity"
130
+ @click=${(e: Event) => this.handleDelete(session.id, e)}
131
+ title=${i18n("Delete")}
132
+ >
133
+ <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2">
134
+ <path d="M3 6h18"></path>
135
+ <path d="M19 6v14c0 1-1 2-2 2H7c-1 0-2-1-2-2V6"></path>
136
+ <path d="M8 6V4c0-1 1-2 2-2h4c1 0 2 1 2 2v2"></path>
137
+ </svg>
138
+ </button>
139
+ </div>
140
+ `,
141
+ )
142
+ }
143
+ </div>
144
+ `,
145
+ })}
146
+ `;
147
+ }
148
+ }
@@ -179,6 +179,7 @@ export class SettingsDialog extends LitElement {
179
179
  },
180
180
  width: "min(1000px, 90vw)",
181
181
  height: "min(800px, 90vh)",
182
+ backdropClassName: "bg-black/50 backdrop-blur-sm",
182
183
  children: html`
183
184
  ${DialogContent({
184
185
  className: "h-full p-6",