@marimo-team/islands 0.25.3-dev15 → 0.25.3-dev150

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 (502) hide show
  1. package/dist/{ConnectedDataExplorerComponent-CNMliVzw.js → ConnectedDataExplorerComponent-BAiSVaHj.js} +17 -15
  2. package/dist/{ErrorBoundary-z1rqMOCq.js → ErrorBoundary-C2DyVAla.js} +16 -16
  3. package/dist/{abnfDiagram-VCTEODGH-D-Ez91gV.js → abnfDiagram-VCTEODGH-BBHN92-F.js} +2 -2
  4. package/dist/any-language-editor-3E24SnCV.js +75 -0
  5. package/dist/{architectureDiagram-5GKGNRK7-CTpcNtO8.js → architectureDiagram-5GKGNRK7-C0Rd64qh.js} +1 -1
  6. package/dist/{arrays-CN1djC4k.js → arrays-R6JsImiT.js} +8 -0
  7. package/dist/assets/__vite-browser-external-BgQNn4dS.js +1 -0
  8. package/dist/assets/worker-FKe3RHT4.js +113 -0
  9. package/dist/{button-CvjkwdSk.js → button-BQRdqQi1.js} +199 -192
  10. package/dist/{capabilities-CQ5IjhzL.js → capabilities-CI4xUPsp.js} +2 -2
  11. package/dist/{chat-ui-DaHynk8g.js → chat-ui-CvB8Map3.js} +1142 -1141
  12. package/dist/{check-EDwSwP89.js → check-SpOMoCLP.js} +1 -1
  13. package/dist/{chunk-IMKFNOWR-DGxi-zeo.js → chunk-IMKFNOWR-hJXey5p2.js} +1 -1
  14. package/dist/{chunk-SHT3W25Y-CV9J3rAB.js → chunk-SHT3W25Y-JMzTmmVW.js} +1 -1
  15. package/dist/{chunk-SVP7TREG-BL-9Fqgg.js → chunk-SVP7TREG-BIyoHTXi.js} +1 -1
  16. package/dist/{chunk-TICWLB2K-Cu_XMjDM.js → chunk-TICWLB2K-CCzH2Uwa.js} +1 -1
  17. package/dist/{chunk-YOKDWASO-DPZk8vhS.js → chunk-YOKDWASO-DKplTrBY.js} +20 -20
  18. package/dist/{classDiagram-ZZMXUADV-BXXV13Hq.js → classDiagram-ZZMXUADV-DB1kOPS6.js} +2 -2
  19. package/dist/{classDiagram-v2-VYDZK3BY-B7FXJ1Cp.js → classDiagram-v2-VYDZK3BY-CPaFL0OB.js} +2 -2
  20. package/dist/{code-visibility-BFMjPeTv.js → code-visibility-DIEAT978.js} +6 -6
  21. package/dist/{common-JHV-U5GC.js → common-BA_SF-5o.js} +6827 -6647
  22. package/dist/{copy-icon-Ft7t9bqz.js → copy-icon-C1trdvVt.js} +3 -3
  23. package/dist/{cynefinDiagram-5FMLGOSQ-CH96rwba.js → cynefinDiagram-5FMLGOSQ-CF93uliH.js} +1 -1
  24. package/dist/{dagre-GXQ25YYZ-BD3PmpFY.js → dagre-GXQ25YYZ-BBB-_p9D.js} +1 -1
  25. package/dist/{data-grid-overlay-editor-BkL0DXBi.js → data-grid-overlay-editor-Byuku-gi.js} +5 -5
  26. package/dist/{data-grid-types-BH_r7g7l.js → data-grid-types-0PJ-9N5n.js} +1 -1
  27. package/dist/{diagram-S7CK7UJ4-BsSJJldB.js → diagram-S7CK7UJ4-BynCnbyt.js} +1 -1
  28. package/dist/{diagram-UQ7AKVKN-muQtNZc4.js → diagram-UQ7AKVKN-svOxikMa.js} +1 -1
  29. package/dist/{diagram-VX7I27RA-CdhuZAqR.js → diagram-VX7I27RA-BVQSnPx0.js} +1 -1
  30. package/dist/{diagram-Z3DM3KII-BD8mXjOj.js → diagram-Z3DM3KII-nR1J0BH5.js} +1 -1
  31. package/dist/{dialog-CEBFZNyc.js → dialog-DgeqyrEZ.js} +3 -3
  32. package/dist/{dist-DpBpA_n1.js → dist-Lm-D-Vr6.js} +3 -3
  33. package/dist/{dropdown-menu-CP_qCYHC.js → dropdown-menu-GWcGCcxE.js} +1277 -1229
  34. package/dist/{ebnfDiagram-PWID7BFC-BIN1sweE.js → ebnfDiagram-PWID7BFC-C9tq9-Qo.js} +2 -2
  35. package/dist/{erDiagram-RLTQ6QDP-Ctp5cfoN.js → erDiagram-RLTQ6QDP-BiaeB7Fi.js} +1 -1
  36. package/dist/{error-banner-D-WCIiMt.js → error-banner-D40pmfQQ.js} +83 -83
  37. package/dist/{error-entries-Bv6bZPF3.js → error-entries-CmFDQ9CA.js} +1018 -977
  38. package/dist/{feedback-button-do3RdfYX.js → feedback-button-BwgAjZDg.js} +23 -23
  39. package/dist/{flowDiagram-HODETNUW-3EfLrlFb.js → flowDiagram-HODETNUW-f-sLm87k.js} +2 -2
  40. package/dist/{formats-27CW_UP4.js → formats-CCxaLPNs.js} +3 -3
  41. package/dist/{ganttDiagram-EL5Y4UJY-BQT16JSc.js → ganttDiagram-EL5Y4UJY-Dh_4cBJZ.js} +2 -2
  42. package/dist/{glide-data-editor-B2KXsLT5.js → glide-data-editor-BCX4vz1V.js} +370 -368
  43. package/dist/{glide-utils-DJyqh0EM.js → glide-utils-Dz_F4pAY.js} +16 -16
  44. package/dist/{globals-Cnjg2Own.js → globals-2FASSt-d.js} +3 -3
  45. package/dist/{highlighted-body-KPVGNVTW-zwjq21tf.js → highlighted-body-KPVGNVTW-3Ziwfz-V.js} +2 -2
  46. package/dist/{html-to-image-Bf8QMGi4.js → html-to-image-BrC8OJcj.js} +632 -595
  47. package/dist/{infoDiagram-27XIBGKW-DipQoHxl.js → infoDiagram-27XIBGKW-BHrWywBe.js} +1 -1
  48. package/dist/{ishikawaDiagram-5VMMS53U-DgFMjSGz.js → ishikawaDiagram-5VMMS53U-Da4s0Reg.js} +1 -1
  49. package/dist/{kanban-definition-UXKFOSKX-w1ACVjgl.js → kanban-definition-UXKFOSKX-DDf1GVLj.js} +1 -1
  50. package/dist/{label-BDKF3Afc.js → label-D9_-zSg-.js} +3 -3
  51. package/dist/{linear-Cnaq3Tfb.js → linear-DWERh7eI.js} +121 -73
  52. package/dist/{loader-BQOfjTIJ.js → loader-DOVB0Syl.js} +12 -12
  53. package/dist/main.js +7553 -7232
  54. package/dist/{mermaid-CHo49Yv-.js → mermaid-ClwTt7OD.js} +38 -38
  55. package/dist/mermaid-HWGCJPDP-Du3-HPQA.js +2 -0
  56. package/dist/{mindmap-definition-YA3MSWOX-CrT0KSfX.js → mindmap-definition-YA3MSWOX-D60oMZtT.js} +1 -1
  57. package/dist/{number-overlay-editor-DBsAEYkJ.js → number-overlay-editor-6JHsXwu3.js} +3 -3
  58. package/dist/{objects-CzUgoMIF.js → objects-DCmMvZtn.js} +1 -3
  59. package/dist/{once-BtE-wKRL.js → once-eG8Vmvjd.js} +1 -1
  60. package/dist/{pegDiagram-XKGWAZYB-BqvywNJA.js → pegDiagram-XKGWAZYB-B9wFpMga.js} +2 -2
  61. package/dist/{pieDiagram-E7YTZNPT-BfxJ_XCc.js → pieDiagram-E7YTZNPT-BZwvMuBT.js} +1 -1
  62. package/dist/precisionRound-DhAzeRcm.js +49 -0
  63. package/dist/{process-output-BZg56CCb.js → process-output-Bw-vzyoy.js} +5 -5
  64. package/dist/{quadrantDiagram-AXDQQJYC-Ccw0xMjN.js → quadrantDiagram-AXDQQJYC-Blrm7V7_.js} +1 -1
  65. package/dist/{railroadDiagram-O6MQD6OU-8vFLVTPu.js → railroadDiagram-O6MQD6OU-DqhZGsN2.js} +2 -2
  66. package/dist/{react-vega-BED0DjiB.js → react-vega-C4T9Rb_w.js} +12284 -12270
  67. package/dist/{requirementDiagram-BXWQKSXE-a_MxGvxe.js → requirementDiagram-BXWQKSXE-CL5dYARV.js} +1 -1
  68. package/dist/{reveal-component-IkMCCFzA.js → reveal-component-BGe2tbbp.js} +14 -14
  69. package/dist/{select-BButFi-d.js → select-CkF_GBxO.js} +537 -458
  70. package/dist/{sequenceDiagram-WJ2MYXX4-CXFMnxGh.js → sequenceDiagram-WJ2MYXX4-BSUCRd2x.js} +1 -1
  71. package/dist/{spec-BwarBpUJ.js → spec-DiSh_qJC.js} +41 -11
  72. package/dist/{stateDiagram-D77RDMKH-DQeA_CwI.js → stateDiagram-D77RDMKH-B-1Hvyb0.js} +2 -2
  73. package/dist/{stateDiagram-v2-MP3YSRHH-BxxQucm1.js → stateDiagram-v2-MP3YSRHH--HtiR4yB.js} +2 -2
  74. package/dist/style.css +1 -1
  75. package/dist/{swimlanes-42K2YHIH-Do6L-cYg.js → swimlanes-42K2YHIH-Bdfhrd-2.js} +1 -1
  76. package/dist/{swimlanesDiagram-VR7AAH4N-DUzPvSVU.js → swimlanesDiagram-VR7AAH4N-BJIfxSz0.js} +2 -2
  77. package/dist/{swiper-component-DKntyn8p.js → swiper-component-BkCm-kLg.js} +2 -2
  78. package/dist/{time-BieKwdYS.js → time-BaMbJs4z.js} +18 -18
  79. package/dist/{timeline-definition-24CTP7MA-D3c46WM5.js → timeline-definition-24CTP7MA-Cs4EfFD3.js} +1 -1
  80. package/dist/{toDate-UtiwmnH2.js → toDate-DGvRHwTk.js} +19 -18
  81. package/dist/{toast-B9UMEi8u.js → toast-Btbve3Lm.js} +231 -213
  82. package/dist/{tooltip-BO1REbqs.js → tooltip-CJ4Rqasp.js} +327 -303
  83. package/dist/{use-restore-focus-BEM7sFWl.js → use-restore-focus-CmGwRNId.js} +1482 -1433
  84. package/dist/{useAsyncData-Deh5kszT.js → useAsyncData-BmVgnMP5.js} +15 -14
  85. package/dist/{useDateFormatter-D8XruNGG.js → useDateFormatter-eCL_SdeG.js} +2 -2
  86. package/dist/{useDeepCompareMemoize-DXwzRINI.js → useDeepCompareMemoize-Ch_AeGu6.js} +1 -1
  87. package/dist/{useIframeCapabilities-DBETvvPl.js → useIframeCapabilities-CSdWn6NP.js} +1 -1
  88. package/dist/{useLifecycle-j7D9uD1o.js → useLifecycle-B5BX921H.js} +3 -3
  89. package/dist/{useTheme-CRnjkku0.js → useTheme-Bq9pi_vz.js} +6 -6
  90. package/dist/{vega-component-BeF9dfyO.js → vega-component-BgyZ-COt.js} +147 -147
  91. package/dist/{vega-embed-container-BNHE18G9.js → vega-embed-container--LYZqguO.js} +2 -2
  92. package/dist/{vega-loader.browser-DNST6uVf.js → vega-loader.browser-B9Pz0EGP.js} +298 -507
  93. package/dist/{vennDiagram-4TSXK5OY-BSZD8JcZ.js → vennDiagram-4TSXK5OY-DRu0vRjO.js} +1 -1
  94. package/dist/{wardleyDiagram-VM6X3IG4-48cUWkfA.js → wardleyDiagram-VM6X3IG4-DzbDxwDY.js} +1 -1
  95. package/dist/{xychartDiagram-S5SC5T6Z-CswYgYeu.js → xychartDiagram-S5SC5T6Z-CLWj6ZFQ.js} +2 -2
  96. package/package.json +16 -16
  97. package/src/__tests__/module-entry.test.ts +44 -0
  98. package/src/__tests__/mount.test.ts +1 -21
  99. package/src/__tests__/{host-imports.test.ts → replica-imports.test.ts} +12 -11
  100. package/src/components/ai/__tests__/ai-model-dropdown.test.tsx +63 -0
  101. package/src/components/ai/ai-model-dropdown.tsx +11 -6
  102. package/src/components/app-config/ai-config.tsx +7 -2
  103. package/src/components/chat/__tests__/message-queue.test.tsx +17 -0
  104. package/src/components/chat/acp/__tests__/session-tabs.test.tsx +43 -0
  105. package/src/components/chat/acp/__tests__/state.test.ts +2 -2
  106. package/src/components/chat/acp/blocks.tsx +3 -2
  107. package/src/components/chat/acp/session-tabs.tsx +8 -3
  108. package/src/components/chat/chat-components.tsx +2 -0
  109. package/src/components/chat/chat-panel.tsx +9 -8
  110. package/src/components/chat/chat-utils.ts +4 -8
  111. package/src/components/data-table/TableTopBar.tsx +2 -0
  112. package/src/components/data-table/__tests__/chart-spec-model.test.ts +195 -195
  113. package/src/components/data-table/__tests__/column-explorer.test.tsx +27 -1
  114. package/src/components/data-table/__tests__/columns.test.tsx +105 -0
  115. package/src/components/data-table/__tests__/context-menu-interaction.test.tsx +130 -0
  116. package/src/components/data-table/__tests__/data-table.test.tsx +1 -0
  117. package/src/components/data-table/__tests__/date-popover.test.tsx +72 -0
  118. package/src/components/data-table/__tests__/export-actions.test.tsx +105 -0
  119. package/src/components/data-table/__tests__/keyboard-selection.test.tsx +188 -0
  120. package/src/components/data-table/__tests__/search-highlight.test.tsx +109 -0
  121. package/src/components/data-table/__tests__/url-detector.test.tsx +74 -0
  122. package/src/components/data-table/cell-selection/feature.ts +2 -2
  123. package/src/components/data-table/cell-selection/types.ts +2 -2
  124. package/src/components/data-table/charts/__tests__/chart-panel.test.tsx +74 -1
  125. package/src/components/data-table/charts/__tests__/spec-snapshot.test.ts +20 -20
  126. package/src/components/data-table/charts/__tests__/spec.test.ts +78 -52
  127. package/src/components/data-table/charts/__tests__/storage.test.ts +4 -1
  128. package/src/components/data-table/charts/chart-spec/spec.ts +68 -43
  129. package/src/components/data-table/charts/charts.tsx +40 -30
  130. package/src/components/data-table/charts/storage.ts +16 -5
  131. package/src/components/data-table/column-explorer-panel/column-explorer.tsx +1 -1
  132. package/src/components/data-table/column-summary/chart-spec-model.tsx +23 -16
  133. package/src/components/data-table/column-summary/column-summary.tsx +2 -4
  134. package/src/components/data-table/column-visibility-dropdown.tsx +8 -13
  135. package/src/components/data-table/columns.tsx +45 -46
  136. package/src/components/data-table/context-menu.tsx +36 -20
  137. package/src/components/data-table/data-table.tsx +13 -1
  138. package/src/components/data-table/date-popover.tsx +6 -4
  139. package/src/components/data-table/export-actions.tsx +76 -48
  140. package/src/components/data-table/range-focus/atoms.ts +4 -6
  141. package/src/components/data-table/range-focus/use-cell-range-selection.ts +65 -38
  142. package/src/components/data-table/range-focus/use-scroll-into-view.ts +21 -2
  143. package/src/components/data-table/renderers.tsx +16 -7
  144. package/src/components/data-table/row-viewer-panel/__tests__/row-viewer.test.tsx +24 -1
  145. package/src/components/data-table/row-viewer-panel/row-viewer.tsx +4 -4
  146. package/src/components/data-table/search-highlight.tsx +79 -0
  147. package/src/components/data-table/types.ts +1 -0
  148. package/src/components/data-table/url-detector.tsx +49 -9
  149. package/src/components/datasources/__tests__/column-actions.test.tsx +97 -0
  150. package/src/components/datasources/__tests__/column-preview.test.tsx +98 -5
  151. package/src/components/datasources/__tests__/datasources-interactions.test.tsx +181 -0
  152. package/src/components/datasources/__tests__/table-list.test.tsx +118 -0
  153. package/src/components/datasources/__tests__/utils.test.ts +57 -6
  154. package/src/components/datasources/column-preview.tsx +13 -4
  155. package/src/components/datasources/datasources.tsx +51 -39
  156. package/src/components/datasources/utils.ts +32 -23
  157. package/src/components/debugger/debugger-code.tsx +5 -0
  158. package/src/components/dependency-graph/dependency-graph-tree.tsx +8 -8
  159. package/src/components/dependency-graph/elements.ts +24 -21
  160. package/src/components/dependency-graph/panels.tsx +2 -1
  161. package/src/components/dependency-graph/utils/__tests__/layout.test.ts +18 -11
  162. package/src/components/editor/SortableCell.tsx +1 -3
  163. package/src/{core/attachments/__tests__/toast.test.tsx → components/editor/__tests__/agent-toast.test.tsx} +1 -1
  164. package/src/components/editor/__tests__/dynamic-favicon.test.tsx +111 -18
  165. package/src/components/editor/__tests__/package-alert.test.tsx +22 -1
  166. package/src/components/editor/actions/__tests__/pair-with-agent-modal.test.tsx +24 -0
  167. package/src/components/editor/actions/pair-with-agent-modal.tsx +18 -15
  168. package/src/components/editor/actions/useRestartKernel.tsx +1 -1
  169. package/src/components/editor/ai/add-cell-with-ai.tsx +3 -3
  170. package/src/components/editor/ai/ai-completion-editor.tsx +1 -0
  171. package/src/components/editor/alerts/__tests__/connection-notice.test.tsx +1 -1
  172. package/src/components/editor/alerts/connection-notice.tsx +1 -1
  173. package/src/components/editor/alerts/startup-logs-alert.tsx +1 -0
  174. package/src/components/editor/app-container.tsx +1 -1
  175. package/src/components/editor/boundary/__tests__/ErrorBoundary.test.tsx +1 -1
  176. package/src/components/editor/cell/CreateCellButton.tsx +10 -12
  177. package/src/components/editor/cell/DeleteButton.tsx +3 -2
  178. package/src/components/editor/cell/RunButton.tsx +2 -2
  179. package/src/components/editor/cell/StopButton.tsx +2 -2
  180. package/src/components/editor/cell/__tests__/useShouldShowInterrupt.test.ts +39 -0
  181. package/src/components/editor/cell/code/__tests__/language-toggle.test.tsx +54 -0
  182. package/src/components/editor/cell/code/cell-editor.tsx +2 -2
  183. package/src/components/editor/cell/code/language-toggle.tsx +8 -7
  184. package/src/components/editor/cell/collapse.tsx +5 -3
  185. package/src/components/editor/cell/useShouldShowInterrupt.ts +2 -12
  186. package/src/components/editor/chrome/components/__tests__/feedback-button.test.tsx +1 -1
  187. package/src/components/editor/chrome/components/feedback-button.tsx +1 -1
  188. package/src/components/editor/chrome/panels/__tests__/packages-panel.test.tsx +31 -2
  189. package/src/components/editor/chrome/panels/__tests__/runtime-details.test.tsx +1 -1
  190. package/src/components/editor/chrome/panels/__tests__/sandbox-recovery.test.tsx +1 -1
  191. package/src/components/editor/chrome/panels/cache-panel.tsx +1 -0
  192. package/src/components/editor/chrome/panels/outline/__tests__/outline-keyboard.test.tsx +84 -0
  193. package/src/components/editor/chrome/panels/outline/floating-outline.tsx +39 -14
  194. package/src/components/editor/chrome/panels/outline/useActiveOutline.tsx +3 -2
  195. package/src/components/editor/chrome/panels/packages-panel.tsx +4 -7
  196. package/src/components/editor/chrome/panels/secrets-panel.tsx +1 -0
  197. package/src/components/editor/chrome/panels/snippets-panel.tsx +5 -1
  198. package/src/components/editor/chrome/wrapper/__tests__/attachment-status.test.tsx +9 -18
  199. package/src/components/editor/chrome/wrapper/__tests__/pending-ai-cells.test.tsx +58 -1
  200. package/src/components/editor/chrome/wrapper/footer-items/attachment-status.tsx +4 -4
  201. package/src/components/editor/chrome/wrapper/footer-items/backend-status.tsx +1 -1
  202. package/src/components/editor/chrome/wrapper/footer-items/lsp-status.tsx +1 -1
  203. package/src/components/editor/chrome/wrapper/footer-items/machine-stats.tsx +1 -1
  204. package/src/components/editor/chrome/wrapper/footer-items/runtime-settings.tsx +1 -7
  205. package/src/components/editor/chrome/wrapper/pending-ai-cells.tsx +12 -2
  206. package/src/components/editor/chrome/wrapper/storage.ts +1 -1
  207. package/src/components/editor/connections/components.tsx +1 -1
  208. package/src/components/editor/controls/Controls.tsx +2 -2
  209. package/src/components/editor/controls/__tests__/command-palette.test.tsx +53 -0
  210. package/src/components/editor/controls/__tests__/keyboard-shortcuts.test.tsx +61 -0
  211. package/src/components/editor/controls/__tests__/notebook-menu-dropdown.test.tsx +1 -1
  212. package/src/components/editor/controls/command-palette.tsx +22 -10
  213. package/src/components/editor/controls/keyboard-shortcuts.tsx +14 -5
  214. package/src/components/editor/dynamic-favicon.tsx +21 -40
  215. package/src/components/editor/errors/__tests__/send-error-report-button.test.tsx +9 -23
  216. package/src/components/editor/errors/send-error-report-button.tsx +3 -6
  217. package/src/components/editor/file-tree/__tests__/file-explorer-interactions.test.tsx +6 -0
  218. package/src/components/editor/file-tree/__tests__/file-explorer-navigation.test.tsx +47 -0
  219. package/src/components/editor/file-tree/__tests__/use-file-search.test.tsx +91 -0
  220. package/src/components/editor/file-tree/file-explorer.tsx +45 -8
  221. package/src/components/editor/file-tree/file-name-input.tsx +1 -0
  222. package/src/components/editor/file-tree/file-viewer.tsx +4 -2
  223. package/src/components/editor/file-tree/use-file-search.ts +35 -21
  224. package/src/components/editor/header/__tests__/status.test.tsx +5 -3
  225. package/src/components/editor/header/app-header.tsx +1 -1
  226. package/src/components/editor/header/status.tsx +40 -20
  227. package/src/components/editor/links/__tests__/cell-link.test.tsx +146 -0
  228. package/src/components/editor/links/cell-link.tsx +14 -5
  229. package/src/components/editor/navigation/focus-utils.ts +4 -4
  230. package/src/components/editor/notebook-banner.tsx +1 -0
  231. package/src/components/editor/notebook-cell.tsx +12 -3
  232. package/src/components/editor/output/MarimoTracebackOutput.tsx +19 -17
  233. package/src/components/editor/output/__tests__/traceback.test.tsx +27 -1
  234. package/src/components/editor/output/ansi-reduce.ts +33 -20
  235. package/src/components/editor/output/console/ConsoleOutput.tsx +19 -25
  236. package/src/components/editor/package-alert.tsx +14 -7
  237. package/src/components/editor/renderers/grid-layout/grid-layout.tsx +12 -6
  238. package/src/components/editor/renderers/vertical-layout/sidebar/toggle.tsx +7 -1
  239. package/src/components/home/components.tsx +17 -31
  240. package/src/components/icons/__tests__/large-spinner.test.tsx +39 -0
  241. package/src/components/icons/large-spinner.tsx +3 -14
  242. package/src/components/icons/spinner.tsx +1 -1
  243. package/src/components/mcp/mcp-status-indicator.tsx +1 -1
  244. package/src/components/pages/__tests__/home-page.test.tsx +116 -0
  245. package/src/components/pages/home-page.tsx +164 -91
  246. package/src/components/scratchpad/scratchpad.test.tsx +95 -0
  247. package/src/components/scratchpad/scratchpad.tsx +16 -3
  248. package/src/components/slides/reveal-component.tsx +4 -2
  249. package/src/components/slides/slide-cell-view.tsx +1 -1
  250. package/src/components/slides/slide-form.tsx +1 -0
  251. package/src/components/tracing/tracing-keyboard.test.tsx +85 -0
  252. package/src/components/tracing/tracing.tsx +45 -41
  253. package/src/components/ui/__tests__/draggable-popover.test.tsx +24 -0
  254. package/src/components/ui/__tests__/range-slider.test.tsx +165 -0
  255. package/src/components/ui/alert-dialog.tsx +1 -1
  256. package/src/components/ui/draggable-popover.tsx +24 -2
  257. package/src/components/ui/range-slider.tsx +22 -9
  258. package/src/core/ai/context/providers/datasource.ts +6 -2
  259. package/src/core/ai/tools/base.ts +16 -7
  260. package/src/core/ai/tools/edit-notebook-tool.ts +47 -45
  261. package/src/core/ai/tools/registry.ts +13 -8
  262. package/src/core/ai/tools/sample-tool.ts +6 -7
  263. package/src/core/cells/__tests__/__snapshots__/cells.test.ts.snap +4 -0
  264. package/src/core/cells/__tests__/cell.test.ts +39 -0
  265. package/src/core/cells/__tests__/cells.test.ts +3 -1
  266. package/src/core/cells/__tests__/collapseConsoleOutputs.test.ts +54 -0
  267. package/src/core/cells/__tests__/notebook-outline.test.ts +113 -0
  268. package/src/core/cells/__tests__/session.test.ts +117 -36
  269. package/src/core/cells/cell.ts +14 -3
  270. package/src/core/cells/cells.ts +3 -1
  271. package/src/core/cells/pending-delete-service.ts +2 -6
  272. package/src/core/cells/session.ts +1 -1
  273. package/src/core/cells/types.ts +10 -1
  274. package/src/core/codemirror/__tests__/setup.test.ts +29 -29
  275. package/src/core/codemirror/cells/__tests__/extensions.test.ts +15 -0
  276. package/src/core/codemirror/cells/extensions.ts +7 -3
  277. package/src/core/codemirror/keymaps/vim.ts +2 -6
  278. package/src/core/codemirror/language/__tests__/sql.test.ts +22 -20
  279. package/src/core/codemirror/language/extension.ts +8 -8
  280. package/src/core/codemirror/language/languages/markdown.ts +8 -6
  281. package/src/core/codemirror/language/languages/python.ts +16 -10
  282. package/src/core/codemirror/language/languages/sql/sql.ts +9 -7
  283. package/src/core/codemirror/language/panel/panel.tsx +1 -0
  284. package/src/core/codemirror/language/types.ts +7 -7
  285. package/src/core/codemirror/readonly/__tests__/extension.test.ts +1 -1
  286. package/src/core/codemirror/readonly/extension.ts +2 -2
  287. package/src/core/codemirror/rtc/extension.ts +24 -12
  288. package/src/core/codemirror/rtc/loro/awareness.ts +34 -19
  289. package/src/core/codemirror/rtc/loro/sync.ts +1 -0
  290. package/src/core/codemirror/utils.ts +1 -0
  291. package/src/core/datasets/__tests__/data-source-discovery.test.ts +5 -5
  292. package/src/core/datasets/data-source-discovery.ts +4 -6
  293. package/src/core/edit-app.tsx +2 -2
  294. package/src/core/export/hooks.ts +1 -1
  295. package/src/core/hotkeys/actions.ts +2 -4
  296. package/src/core/islands/__tests__/bootstrap.test.ts +16 -42
  297. package/src/core/islands/__tests__/bridge.test.ts +31 -26
  298. package/src/core/islands/bootstrap.ts +22 -52
  299. package/src/core/islands/bridge.ts +31 -20
  300. package/src/core/islands/components/__tests__/IslandControls.test.tsx +7 -5
  301. package/src/core/islands/worker/__tests__/controller.test.ts +62 -4
  302. package/src/core/islands/worker/controller.ts +4 -10
  303. package/src/core/islands/worker/worker.tsx +33 -33
  304. package/src/core/kernel/__tests__/RuntimeState.test.ts +1 -1
  305. package/src/core/network/__tests__/connection.test.ts +1 -1
  306. package/src/core/network/connection-notice.ts +1 -1
  307. package/src/core/network/connection.ts +5 -3
  308. package/src/core/network/requests-lazy.ts +1 -1
  309. package/src/core/network/useConnectionNotice.ts +8 -2
  310. package/src/core/notebook/attachments.ts +38 -0
  311. package/src/core/notebook/document/__tests__/codemirror.test.ts +485 -0
  312. package/src/core/notebook/document/__tests__/draft.test.ts +322 -0
  313. package/src/core/notebook/document/__tests__/fixtures.ts +92 -0
  314. package/src/core/notebook/document/__tests__/hooks.test.tsx +391 -0
  315. package/src/core/notebook/document/__tests__/lifecycle-scenarios.test.ts +61 -0
  316. package/src/core/notebook/document/__tests__/model.test.ts +191 -0
  317. package/src/core/notebook/document/__tests__/protocol-fixtures.ts +38 -0
  318. package/src/core/notebook/document/__tests__/recovery-scenarios.test.ts +230 -0
  319. package/src/core/notebook/document/__tests__/scenario-fixture.ts +43 -0
  320. package/src/core/notebook/document/__tests__/scenarios.test.ts +205 -0
  321. package/src/core/notebook/document/__tests__/state.test.ts +438 -0
  322. package/src/core/notebook/document/__tests__/submission.test.ts +203 -0
  323. package/src/core/notebook/document/__tests__/test-host.test.ts +92 -0
  324. package/src/core/notebook/document/__tests__/test-host.ts +247 -0
  325. package/src/core/notebook/document/__tests__/test-notebook.ts +149 -0
  326. package/src/core/notebook/document/__tests__/user.ts +61 -0
  327. package/src/core/notebook/document/codemirror.ts +311 -0
  328. package/src/core/notebook/document/draft.ts +472 -0
  329. package/src/core/notebook/document/hooks.tsx +118 -0
  330. package/src/core/notebook/document/index.ts +15 -0
  331. package/src/core/notebook/document/model.ts +55 -0
  332. package/src/core/notebook/document/select.ts +41 -0
  333. package/src/core/notebook/document/state.ts +374 -0
  334. package/src/core/notebook/document/sync.ts +369 -0
  335. package/src/core/notebook/index.ts +18 -0
  336. package/src/core/notebook/replica/AGENTS.md +11 -0
  337. package/src/core/notebook/replica/__tests__/attachments.test.ts +56 -0
  338. package/src/core/notebook/replica/__tests__/document.test.ts +126 -0
  339. package/src/core/notebook/replica/__tests__/fixtures.ts +79 -0
  340. package/src/core/notebook/replica/__tests__/replica.test.ts +550 -0
  341. package/src/core/notebook/replica/backend.ts +19 -0
  342. package/src/core/notebook/replica/connection.ts +42 -0
  343. package/src/core/notebook/replica/index.ts +13 -0
  344. package/src/core/notebook/replica/replica.ts +286 -0
  345. package/src/core/notebook/replica/resources/attachments.ts +22 -0
  346. package/src/core/notebook/replica/resources/document.ts +101 -0
  347. package/src/core/packages/__tests__/useSandboxController.test.tsx +1 -1
  348. package/src/core/packages/useSandboxController.ts +1 -1
  349. package/src/core/run-app.tsx +3 -3
  350. package/src/core/runtime/__tests__/adapter.test.ts +1 -1
  351. package/src/core/runtime/__tests__/createWsUrl.test.ts +77 -7
  352. package/src/core/runtime/__tests__/runtime.test.ts +32 -58
  353. package/src/core/runtime/adapter.ts +1 -1
  354. package/src/core/runtime/config.ts +2 -2
  355. package/src/core/runtime/runtime.ts +38 -42
  356. package/src/core/runtime/types.ts +0 -2
  357. package/src/core/saving/filename.ts +1 -1
  358. package/src/core/saving/save-component.tsx +13 -4
  359. package/src/core/saving/useAutoSave.ts +1 -1
  360. package/src/core/session/__tests__/backend.test.ts +235 -0
  361. package/src/core/session/__tests__/useNotebookReplica.hook.test.tsx +183 -0
  362. package/src/core/session/__tests__/useNotebookSession.hook.test.tsx +609 -0
  363. package/src/core/session/active-notebook.ts +7 -0
  364. package/src/core/session/backend.ts +125 -0
  365. package/src/core/{websocket → session}/types.ts +2 -2
  366. package/src/core/session/useNotebookReplica.ts +72 -0
  367. package/src/core/{websocket → session}/useNotebookSession.tsx +18 -25
  368. package/src/core/state/__tests__/jotai.test.tsx +108 -0
  369. package/src/core/state/jotai.ts +1 -1
  370. package/src/core/static/__tests__/files.test.ts +38 -10
  371. package/src/core/static/files.ts +2 -0
  372. package/src/core/{websocket → transports}/__tests__/connection-state.test.ts +1 -13
  373. package/src/core/transports/__tests__/server.test.ts +408 -0
  374. package/src/core/transports/__tests__/static.test.ts +175 -0
  375. package/src/core/transports/__tests__/wasm.test.ts +166 -0
  376. package/src/core/{websocket → transports}/connection-state.ts +9 -16
  377. package/src/core/transports/server.ts +152 -0
  378. package/src/core/transports/static.ts +84 -0
  379. package/src/core/transports/wasm.ts +97 -0
  380. package/src/core/wasm/__tests__/bridge.test.ts +213 -50
  381. package/src/core/wasm/__tests__/worker.test.ts +187 -0
  382. package/src/core/wasm/bridge.ts +81 -52
  383. package/src/core/wasm/rpc.ts +15 -3
  384. package/src/core/wasm/store.ts +3 -3
  385. package/src/core/wasm/worker/bootstrap.ts +55 -51
  386. package/src/core/wasm/worker/getMarimoWheel.ts +1 -1
  387. package/src/core/wasm/worker/save-worker.ts +9 -10
  388. package/src/core/wasm/worker/types.ts +29 -18
  389. package/src/core/wasm/worker/worker.ts +97 -44
  390. package/src/css/globals.css +5 -0
  391. package/src/hooks/__tests__/useAsyncData.test.tsx +148 -0
  392. package/src/hooks/__tests__/useDebounce.test.tsx +51 -0
  393. package/src/hooks/__tests__/useDeepCompareMemoize.test.tsx +39 -0
  394. package/src/hooks/__tests__/useDelayElapsed.test.tsx +28 -0
  395. package/src/hooks/__tests__/useInternalStateWithSync.test.tsx +20 -0
  396. package/src/hooks/__tests__/useScript.test.tsx +77 -0
  397. package/src/hooks/__tests__/useStateForKey.test.tsx +257 -0
  398. package/src/hooks/useAsyncData.ts +3 -3
  399. package/src/hooks/useDataSourceDiscovery.ts +6 -4
  400. package/src/hooks/useDebounce.ts +6 -10
  401. package/src/hooks/useDeepCompareMemoize.ts +1 -1
  402. package/src/hooks/useDelayElapsed.ts +14 -10
  403. package/src/hooks/useElapsedTime.ts +3 -3
  404. package/src/hooks/useEventListener.ts +1 -2
  405. package/src/hooks/useInputHistory.ts +4 -7
  406. package/src/hooks/useInternalStateWithSync.ts +6 -6
  407. package/src/hooks/useResizeObserver.ts +4 -7
  408. package/src/hooks/useScript.ts +67 -70
  409. package/src/hooks/useStateForKey.ts +93 -0
  410. package/src/mount.tsx +1 -5
  411. package/src/plugins/__tests__/plugin-object-schemas.test.ts +104 -0
  412. package/src/plugins/core/registerReactComponent.tsx +1 -1
  413. package/src/plugins/impl/CodeEditorPlugin.tsx +1 -1
  414. package/src/plugins/impl/DataEditorPlugin.tsx +1 -1
  415. package/src/plugins/impl/DataTablePlugin.tsx +29 -33
  416. package/src/plugins/impl/DropdownPlugin.tsx +2 -6
  417. package/src/plugins/impl/FileBrowserPlugin.tsx +4 -16
  418. package/src/plugins/impl/FormPlugin.tsx +1 -1
  419. package/src/plugins/impl/RangeSliderPlugin.tsx +16 -2
  420. package/src/plugins/impl/RefreshPlugin.tsx +1 -0
  421. package/src/plugins/impl/SliderPlugin.tsx +6 -8
  422. package/src/plugins/impl/__tests__/DataTablePlugin.test.tsx +117 -1
  423. package/src/plugins/impl/__tests__/FileBrowserPlugin.test.tsx +45 -0
  424. package/src/plugins/impl/__tests__/RangeSliderPlugin.test.tsx +109 -0
  425. package/src/plugins/impl/__tests__/SliderPlugin.test.tsx +24 -3
  426. package/src/plugins/impl/anywidget/__tests__/registry.test.ts +2 -0
  427. package/src/plugins/impl/anywidget/__tests__/widget-binding.test.ts +241 -2
  428. package/src/plugins/impl/anywidget/runtime.ts +21 -9
  429. package/src/plugins/impl/anywidget/widget-binding.ts +160 -82
  430. package/src/plugins/impl/chat/__tests__/chat-prompts.test.tsx +93 -0
  431. package/src/plugins/impl/chat/chat-ui.tsx +14 -11
  432. package/src/plugins/impl/code/any-language-editor.tsx +2 -2
  433. package/src/plugins/impl/data-editor/glide-data-editor.tsx +8 -5
  434. package/src/plugins/impl/data-editor/glide-utils.ts +3 -1
  435. package/src/plugins/impl/data-explorer/ConnectedDataExplorerComponent.tsx +1 -1
  436. package/src/plugins/impl/data-explorer/components/column-summary.tsx +4 -2
  437. package/src/plugins/impl/data-explorer/state/reducer.ts +1 -1
  438. package/src/plugins/impl/data-frames/DataFramePlugin.tsx +1 -2
  439. package/src/plugins/impl/data-frames/__tests__/sidebar.test.tsx +160 -0
  440. package/src/plugins/impl/data-frames/forms/__tests__/__snapshots__/form.test.tsx.snap +66 -66
  441. package/src/plugins/impl/data-frames/panel.tsx +43 -16
  442. package/src/plugins/impl/mpl-interactive/MplInteractivePlugin.tsx +5 -3
  443. package/src/plugins/impl/panel/PanelPlugin.tsx +16 -17
  444. package/src/plugins/impl/panel/__tests__/utils.test.ts +39 -1
  445. package/src/plugins/impl/panel/utils.ts +17 -0
  446. package/src/plugins/impl/plotly/PlotlyPlugin.tsx +2 -5
  447. package/src/plugins/impl/plotly/selection.ts +25 -19
  448. package/src/plugins/impl/vega/VegaPlugin.tsx +2 -3
  449. package/src/plugins/impl/vega/make-selectable.ts +4 -7
  450. package/src/plugins/layout/RoutesPlugin.tsx +1 -1
  451. package/src/stories/__tests__/editor-story.test.tsx +33 -0
  452. package/src/stories/button.stories.tsx +1 -0
  453. package/src/stories/cell.stories.tsx +1 -1
  454. package/src/stories/editor.stories.tsx +24 -17
  455. package/src/stories/form-wrapper.stories.tsx +2 -2
  456. package/src/stories/layout/vertical/one-column.stories.tsx +1 -1
  457. package/src/stories/runtime-story.tsx +1 -1
  458. package/src/stories/select.stories.tsx +2 -2
  459. package/src/stories/switchable-multi-select.stories.tsx +1 -1
  460. package/src/utils/__tests__/arrays.test.ts +35 -0
  461. package/src/utils/__tests__/batch-requests.test.ts +3 -3
  462. package/src/utils/__tests__/numbers.test.ts +105 -1
  463. package/src/utils/__tests__/objects.test.ts +21 -0
  464. package/src/utils/arrays.ts +11 -2
  465. package/src/utils/blob.ts +1 -1
  466. package/src/utils/maps.ts +0 -3
  467. package/src/utils/numbers.ts +79 -18
  468. package/src/utils/objects.ts +4 -9
  469. package/src/utils/once.ts +19 -19
  470. package/src/utils/tracer.ts +9 -5
  471. package/src/utils/zod-utils.ts +1 -3
  472. package/dist/any-language-editor-DZ_YTVus.js +0 -76
  473. package/dist/assets/__vite-browser-external-BXYkiFsk.js +0 -1
  474. package/dist/assets/worker-HPY9fbhz.js +0 -114
  475. package/dist/mermaid-HWGCJPDP-ByCsZnYF.js +0 -2
  476. package/dist/precisionRound-DMIVQrt2.js +0 -97
  477. package/src/core/attachments/state.ts +0 -21
  478. package/src/core/host/AGENTS.md +0 -6
  479. package/src/core/host/__tests__/events.test.ts +0 -46
  480. package/src/core/host/__tests__/notebook-client.test.ts +0 -191
  481. package/src/core/host/__tests__/protocol.test.ts +0 -214
  482. package/src/core/host/connection.ts +0 -81
  483. package/src/core/host/events.ts +0 -60
  484. package/src/core/host/notebook-client.ts +0 -226
  485. package/src/core/host/protocol.ts +0 -1943
  486. package/src/core/state/__tests__/jotai.test.ts +0 -25
  487. package/src/core/wasm/worker/message-buffer.ts +0 -33
  488. package/src/core/websocket/__tests__/createConnectionTransport.test.ts +0 -49
  489. package/src/core/websocket/__tests__/useNotebookClient.hook.test.tsx +0 -140
  490. package/src/core/websocket/__tests__/useNotebookSession.hook.test.tsx +0 -883
  491. package/src/core/websocket/transports/__tests__/basic.test.ts +0 -275
  492. package/src/core/websocket/transports/__tests__/sse.test.ts +0 -335
  493. package/src/core/websocket/transports/__tests__/transport.test.ts +0 -308
  494. package/src/core/websocket/transports/__tests__/ws.test.ts +0 -125
  495. package/src/core/websocket/transports/basic.ts +0 -102
  496. package/src/core/websocket/transports/create.ts +0 -31
  497. package/src/core/websocket/transports/sse.ts +0 -308
  498. package/src/core/websocket/transports/transport.ts +0 -50
  499. package/src/core/websocket/transports/ws.ts +0 -98
  500. package/src/core/websocket/useNotebookClient.ts +0 -80
  501. /package/src/{core/attachments/toast.ts → components/editor/agent-toast.ts} +0 -0
  502. /package/src/core/{websocket → session}/connection-utils.ts +0 -0
@@ -155,13 +155,15 @@ export class SQLLanguageAdapter implements LanguageAdapter<SQLLanguageAdapterMet
155
155
  return this.parser.isSupported(pythonCode);
156
156
  }
157
157
 
158
- public getExtension(
159
- _cellId: CellId,
160
- _completionConfig: CompletionConfig,
161
- _hotkeys: HotkeyProvider,
162
- _placeholderType: PlaceholderType,
163
- lspConfig: LSPConfig & { diagnostics: DiagnosticsConfig },
164
- ): Extension[] {
158
+ public getExtension({
159
+ lspConfig,
160
+ }: {
161
+ cellId: CellId;
162
+ completionConfig: CompletionConfig;
163
+ hotkeys: HotkeyProvider;
164
+ placeholderType: PlaceholderType;
165
+ lspConfig: LSPConfig & { diagnostics: DiagnosticsConfig };
166
+ }): Extension[] {
165
167
  const analysis = createSQLAnalysis();
166
168
  const extensions = [
167
169
  // This can be updated with a dispatch effect
@@ -101,6 +101,7 @@ export const LanguagePanelComponent: React.FC<{
101
101
  {metadata.engine === DUCKDB_ENGINE && <SQLModeSelect />}
102
102
  <Tooltip content="Format SQL">
103
103
  <Button
104
+ aria-label="Format SQL"
104
105
  variant="text"
105
106
  size="icon"
106
107
  onClick={async () => {
@@ -26,13 +26,13 @@ export interface LanguageAdapter<M = Record<string, any>> {
26
26
  transformIn(code: string): [string, number, M];
27
27
  transformOut(code: string, metadata: M): [string, number];
28
28
  isSupported(code: string): boolean;
29
- getExtension(
30
- cellId: CellId,
31
- completionConfig: CompletionConfig,
32
- hotkeys: HotkeyProvider,
33
- placeholderType: PlaceholderType,
34
- lspConfig: LSPConfig & { diagnostics?: DiagnosticsConfig },
35
- ): Extension[];
29
+ getExtension(options: {
30
+ cellId: CellId;
31
+ completionConfig: CompletionConfig;
32
+ hotkeys: HotkeyProvider;
33
+ placeholderType: PlaceholderType;
34
+ lspConfig: LSPConfig & { diagnostics?: DiagnosticsConfig };
35
+ }): Extension[];
36
36
  }
37
37
 
38
38
  export type LanguageMetadataOf<T extends LanguageAdapter> =
@@ -4,7 +4,7 @@ import { EditorState } from "@codemirror/state";
4
4
  import { EditorView } from "@codemirror/view";
5
5
  import { createStore } from "jotai";
6
6
  import { describe, expect, it } from "vitest";
7
- import { ConnectionState } from "@/core/websocket/types";
7
+ import { ConnectionState } from "@/core/session/types";
8
8
  import { connectionAtom } from "../../../network/connection";
9
9
  import { dynamicReadonly, isEditorReadonly } from "../extension";
10
10
 
@@ -5,9 +5,9 @@ import type { createStore } from "jotai";
5
5
  import {
6
6
  isAppConnected,
7
7
  isAppConnecting,
8
- } from "@/core/websocket/connection-utils";
8
+ } from "@/core/session/connection-utils";
9
9
  import { connectionAtom } from "../../network/connection";
10
- import { ConnectionState } from "../../websocket/types";
10
+ import { ConnectionState } from "../../session/types";
11
11
 
12
12
  /**
13
13
  * State effect for updating readonly status based on connection
@@ -207,7 +207,13 @@ export function realTimeCollaboration(
207
207
  extension: [
208
208
  languageObserverExtension(cellId),
209
209
  languageListenerExtension(cellId),
210
- loroAwarenessPlugin(doc, awareness, userState, () => loroText, cellId),
210
+ loroAwarenessPlugin({
211
+ doc,
212
+ awareness,
213
+ user: userState,
214
+ getTextFromDoc: () => loroText,
215
+ cellId,
216
+ }),
211
217
  loroSyncPlugin(doc, ["codes", cellId], () => {
212
218
  return loroText;
213
219
  }),
@@ -419,14 +425,21 @@ function languageListenerExtension(cellId: CellId) {
419
425
  /**
420
426
  * Create a plugin to observe awareness changes
421
427
  */
422
- function loroAwarenessPlugin(
423
- doc: LoroDoc,
424
- awareness: Awareness<AwarenessState>,
425
- user: UserState,
426
- getTextFromDoc: (doc: LoroDoc) => LoroText,
427
- cellId: CellId,
428
- getUserId?: () => Uid,
429
- ): Extension[] {
428
+ function loroAwarenessPlugin({
429
+ doc,
430
+ awareness,
431
+ user,
432
+ getTextFromDoc,
433
+ cellId,
434
+ getUserId,
435
+ }: {
436
+ doc: LoroDoc;
437
+ awareness: Awareness<AwarenessState>;
438
+ user: UserState;
439
+ getTextFromDoc: (doc: LoroDoc) => LoroText;
440
+ cellId: CellId;
441
+ getUserId?: () => Uid;
442
+ }): Extension[] {
430
443
  const scopeId = `loro:cell:${cellId}` as ScopeId;
431
444
 
432
445
  return [
@@ -435,15 +448,14 @@ function loroAwarenessPlugin(
435
448
  createSelectionLayer(),
436
449
  ViewPlugin.define(
437
450
  (view) =>
438
- new AwarenessPlugin(
439
- view,
451
+ new AwarenessPlugin(view, {
440
452
  doc,
441
453
  user,
442
454
  awareness,
443
455
  getTextFromDoc,
444
456
  scopeId,
445
457
  getUserId,
446
- ),
458
+ }),
447
459
  ),
448
460
  ViewPlugin.define(
449
461
  (view) => new RemoteAwarenessPlugin(view, doc, awareness, scopeId),
@@ -208,13 +208,19 @@ export class RemoteCursorMarker implements LayerMarker {
208
208
  private name: string;
209
209
  private colorClassName: string;
210
210
 
211
- public constructor(
212
- left: number,
213
- top: number,
214
- height: number,
215
- name: string,
216
- colorClassName: string,
217
- ) {
211
+ public constructor({
212
+ left,
213
+ top,
214
+ height,
215
+ name,
216
+ colorClassName,
217
+ }: {
218
+ left: number;
219
+ top: number;
220
+ height: number;
221
+ name: string;
222
+ colorClassName: string;
223
+ }) {
218
224
  this.left = left;
219
225
  this.top = top;
220
226
  this.height = height;
@@ -271,13 +277,13 @@ export class RemoteCursorMarker implements LayerMarker {
271
277
  const baseLeft = left - view.scrollDOM.scrollLeft;
272
278
  const baseTop = rect.top - view.scrollDOM.scrollTop;
273
279
  return [
274
- new RemoteCursorMarker(
275
- absolutePosition.left - baseLeft,
276
- absolutePosition.top - baseTop,
277
- absolutePosition.bottom - absolutePosition.top,
278
- displayName,
280
+ new RemoteCursorMarker({
281
+ left: absolutePosition.left - baseLeft,
282
+ top: absolutePosition.top - baseTop,
283
+ height: absolutePosition.bottom - absolutePosition.top,
284
+ name: displayName,
279
285
  colorClassName,
280
- ),
286
+ }),
281
287
  ];
282
288
  }
283
289
 
@@ -375,12 +381,21 @@ export class AwarenessPlugin implements PluginValue {
375
381
 
376
382
  public constructor(
377
383
  view: EditorView,
378
- doc: LoroDoc,
379
- user: UserState,
380
- awareness: Awareness<AwarenessState>,
381
- getTextFromDoc: (doc: LoroDoc) => LoroText,
382
- scopeId: ScopeId,
383
- getUserId?: () => Uid,
384
+ {
385
+ doc,
386
+ user,
387
+ awareness,
388
+ getTextFromDoc,
389
+ scopeId,
390
+ getUserId,
391
+ }: {
392
+ doc: LoroDoc;
393
+ user: UserState;
394
+ awareness: Awareness<AwarenessState>;
395
+ getTextFromDoc: (doc: LoroDoc) => LoroText;
396
+ scopeId: ScopeId;
397
+ getUserId?: () => Uid;
398
+ },
384
399
  ) {
385
400
  this.view = view;
386
401
  this.doc = doc;
@@ -148,6 +148,7 @@ export class LoroSyncPluginValue implements PluginValue {
148
148
  return;
149
149
  }
150
150
  let adj = 0;
151
+ // oxlint-disable-next-line marimo/prefer-object-params -- CodeMirror supplies positional change ranges and inserted text.
151
152
  update.changes.iterChanges((fromA, toA, fromB, toB, insert) => {
152
153
  const insertText = insert.sliceString(0, insert.length, "\n");
153
154
  if (fromA !== toA) {
@@ -122,6 +122,7 @@ export function hasNewLines(tr: Transaction | ViewUpdate): boolean {
122
122
 
123
123
  let hasNewLines = false;
124
124
  // Iterate through all changes in the transaction
125
+ // oxlint-disable-next-line marimo/prefer-object-params -- CodeMirror supplies positional change ranges and inserted text.
125
126
  tr.changes.iterChanges((fromA, toA, fromB, toB, inserted) => {
126
127
  // Check if the inserted text contains line breaks
127
128
  if (inserted.toString().includes("\n")) {
@@ -4,7 +4,7 @@ import { requestId } from "@/__tests__/branded";
4
4
  import type { DataSourceDiscoveryResult } from "@/core/kernel/messages";
5
5
  import { connectionAtom } from "@/core/network/connection";
6
6
  import { store } from "@/core/state/jotai";
7
- import { ConnectionState } from "@/core/websocket/types";
7
+ import { ConnectionState } from "@/core/session/types";
8
8
  import {
9
9
  fetchDataSourceDiscovery,
10
10
  invalidateDataSourceDiscovery,
@@ -185,8 +185,8 @@ describe("isDetectedSourceConnected", () => {
185
185
  });
186
186
  const emptySnapshot = {
187
187
  dialects: [] as string[],
188
- storageProtocols: [] as string[],
189
- storageBackendTypes: [] as string[],
188
+ storageProtocols: new Set<string>(),
189
+ storageBackendTypes: new Set<string>(),
190
190
  };
191
191
 
192
192
  it("does not hide a source when nothing is connected", () => {
@@ -242,7 +242,7 @@ describe("isDetectedSourceConnected", () => {
242
242
  expect(
243
243
  isDetectedSourceConnected(s3, {
244
244
  ...emptySnapshot,
245
- storageProtocols: ["s3"],
245
+ storageProtocols: new Set(["s3"]),
246
246
  }),
247
247
  ).toBe(true);
248
248
  });
@@ -262,7 +262,7 @@ describe("isDetectedSourceConnected", () => {
262
262
  expect(
263
263
  isDetectedSourceConnected(hf, {
264
264
  ...emptySnapshot,
265
- storageBackendTypes: ["huggingface"],
265
+ storageBackendTypes: new Set(["huggingface"]),
266
266
  }),
267
267
  ).toBe(true);
268
268
  });
@@ -27,8 +27,8 @@ export function matchesDiscoveryGroup(
27
27
  */
28
28
  export interface LiveConnectionSnapshot {
29
29
  dialects: readonly string[];
30
- storageProtocols: readonly string[];
31
- storageBackendTypes: readonly string[];
30
+ storageProtocols: ReadonlySet<string>;
31
+ storageBackendTypes: ReadonlySet<string>;
32
32
  }
33
33
 
34
34
  /**
@@ -47,15 +47,13 @@ export function isDetectedSourceConnected(
47
47
  }
48
48
 
49
49
  if (
50
- match.protocols.some((protocol) =>
51
- snapshot.storageProtocols.includes(protocol),
52
- )
50
+ match.protocols.some((protocol) => snapshot.storageProtocols.has(protocol))
53
51
  ) {
54
52
  return true;
55
53
  }
56
54
 
57
55
  return match.backendTypes.some((backendType) =>
58
- snapshot.storageBackendTypes.includes(backendType),
56
+ snapshot.storageBackendTypes.has(backendType),
59
57
  );
60
58
  }
61
59
 
@@ -41,7 +41,7 @@ import { viewStateAtom } from "./mode";
41
41
  import { useRequestClient } from "./network/requests";
42
42
  import { useFilename } from "./saving/filename";
43
43
  import { lastSavedNotebookAtom } from "./saving/state";
44
- import { useNotebookSession } from "./websocket/useNotebookSession";
44
+ import { useNotebookSession } from "./session/useNotebookSession";
45
45
 
46
46
  interface AppProps {
47
47
  /**
@@ -81,7 +81,7 @@ export const EditApp: React.FC<AppProps> = ({
81
81
  return () => {
82
82
  RuntimeState.INSTANCE.stop();
83
83
  };
84
- }, []);
84
+ }, [sendComponentValues]);
85
85
 
86
86
  const { connection, reconnect } = useNotebookSession({
87
87
  autoInstantiate: userConfig.runtime.auto_instantiate,
@@ -16,7 +16,7 @@ import { connectionAtom } from "../network/connection";
16
16
  import { useRequestClient } from "../network/requests";
17
17
  import type { UpdateCellOutputsRequest } from "../network/types";
18
18
  import { VirtualFileTracker } from "../static/virtual-file-tracker";
19
- import { ConnectionState } from "../websocket/types";
19
+ import { ConnectionState } from "../session/types";
20
20
 
21
21
  const DELAY = 5000; // 5 seconds;
22
22
 
@@ -2,6 +2,7 @@
2
2
  import { atom, useAtomValue, useSetAtom } from "jotai";
3
3
  import useEvent from "react-use-event-hook";
4
4
  import type { HotkeyAction } from "@/core/hotkeys/hotkeys";
5
+ import { Objects } from "@/utils/objects";
5
6
 
6
7
  /**
7
8
  * Map of registered keyboard shortcuts and their callbacks.
@@ -29,10 +30,7 @@ export function useSetRegisteredAction() {
29
30
  },
30
31
  ),
31
32
  unregisterAction: useEvent((shortcut: HotkeyAction) => {
32
- set((actions) => {
33
- const { [shortcut]: unused, ...rest } = actions;
34
- return rest;
35
- });
33
+ set((actions) => Objects.omit(actions, [shortcut]));
36
34
  }),
37
35
  };
38
36
  }
@@ -3,22 +3,20 @@
3
3
  import { createStore } from "jotai";
4
4
  import { afterEach, describe, expect, it, vi } from "vitest";
5
5
  import { RuntimeState } from "@/core/kernel/RuntimeState";
6
- import { attachmentsAtom } from "@/core/attachments/state";
7
- import { Logger } from "@/utils/Logger";
8
6
  import { initializeIslands } from "../bootstrap";
9
7
  import type { IslandsPyodideBridge } from "../bridge";
10
8
  import { islandsHydratedAtom, islandsPendingInitialRunsAtom } from "../state";
11
- import type { IslandsKernelMessage } from "../worker/worker";
9
+ import type { NotificationMessage } from "@/core/kernel/messages";
12
10
 
13
- function completedRun(sessionGeneration: number): IslandsKernelMessage {
14
- return {
15
- sessionGeneration,
16
- message: JSON.stringify({
17
- op: "completed-run",
18
- data: { op: "completed-run", run_id: null },
19
- }) as IslandsKernelMessage["message"],
20
- };
21
- }
11
+ type Consumer = (
12
+ notification: NotificationMessage,
13
+ sessionGeneration: number,
14
+ ) => void;
15
+
16
+ const completedRun = {
17
+ op: "completed-run",
18
+ run_id: null,
19
+ } as NotificationMessage;
22
20
 
23
21
  describe("initializeIslands", () => {
24
22
  afterEach(vi.restoreAllMocks);
@@ -28,9 +26,9 @@ describe("initializeIslands", () => {
28
26
  root.innerHTML =
29
27
  '<marimo-island data-app-id="app-1" data-reactive="true"></marimo-island>';
30
28
 
31
- let consumeMessage: ((message: IslandsKernelMessage) => void) | undefined;
29
+ let consumeMessage: Consumer | undefined;
32
30
  const bridge = {
33
- consumeMessages: (consumer: (message: IslandsKernelMessage) => void) => {
31
+ consumeNotifications: (consumer: Consumer) => {
34
32
  consumeMessage = consumer;
35
33
  },
36
34
  sendComponentValues: vi.fn(),
@@ -50,38 +48,14 @@ describe("initializeIslands", () => {
50
48
  expect(store.get(islandsHydratedAtom)).toBe(false);
51
49
  store.set(islandsPendingInitialRunsAtom, new Set([1, 2]));
52
50
 
53
- const errors = vi.spyOn(Logger, "error");
54
- consumeMessage?.({
55
- sessionGeneration: 1,
56
- message: JSON.stringify({
57
- op: "attachments",
58
- data: {
59
- op: "attachments",
60
- attachments: [
61
- {
62
- id: "a1",
63
- kind: "agent",
64
- name: "Pi",
65
- since: "2026-10-14T00:00:00Z",
66
- notebook_id: "nb-test",
67
- identity: "pi-thread",
68
- },
69
- ],
70
- },
71
- }) as IslandsKernelMessage["message"],
72
- });
73
- expect(errors).not.toHaveBeenCalled();
74
- expect(store.get(attachmentsAtom)).toEqual([]);
75
- expect(store.get(islandsPendingInitialRunsAtom)).toEqual(new Set([1, 2]));
76
-
77
- consumeMessage?.(completedRun(1));
51
+ consumeMessage?.(completedRun, 1);
78
52
  expect(store.get(islandsHydratedAtom)).toBe(false);
79
53
 
80
- consumeMessage?.(completedRun(1));
81
- consumeMessage?.(completedRun(0));
54
+ consumeMessage?.(completedRun, 1);
55
+ consumeMessage?.(completedRun, 0);
82
56
  expect(store.get(islandsHydratedAtom)).toBe(false);
83
57
 
84
- consumeMessage?.(completedRun(2));
58
+ consumeMessage?.(completedRun, 2);
85
59
  expect(store.get(islandsHydratedAtom)).toBe(true);
86
60
  });
87
61
  });
@@ -10,7 +10,6 @@ import {
10
10
  } from "@/__tests__/branded";
11
11
  import { notebookAtom } from "@/core/cells/cells";
12
12
  import { islandsPendingInitialRunsAtom } from "@/core/islands/state";
13
- import type { IslandsKernelMessage } from "../worker/worker";
14
13
 
15
14
  type Base64String = components["schemas"]["Base64String"];
16
15
  interface TestIslandApp {
@@ -89,9 +88,6 @@ vi.mock("@/core/wasm/rpc", () => ({
89
88
  startSession: mockStartSessionRequest,
90
89
  stopSession: mockStopSessionRequest,
91
90
  },
92
- send: {
93
- consumerReady: vi.fn(),
94
- },
95
91
  },
96
92
  addMessageListener: vi.fn(
97
93
  (name: string, listener: (payload: never) => void) => {
@@ -177,17 +173,22 @@ describe("IslandsPyodideBridge", () => {
177
173
  });
178
174
  }
179
175
 
180
- function sendKernelMessage(sessionGeneration: number) {
181
- const listener = mockMessageListeners.get("kernelMessage");
176
+ function sendNotebookEvent(sessionGeneration: number, frame: unknown) {
177
+ const listener = mockMessageListeners.get("notebookEvent");
182
178
  if (!listener) {
183
- throw new Error("Missing kernel message listener");
179
+ throw new Error("Missing notebook event listener");
184
180
  }
185
- const message = {
186
- message: "" as IslandsKernelMessage["message"],
187
- sessionGeneration,
188
- };
189
- listener(message as never);
190
- return message;
181
+ listener({ event: JSON.stringify(frame), sessionGeneration } as never);
182
+ }
183
+
184
+ /** Send a notification and return the call the consumer should receive. */
185
+ function sendKernelMessage(sessionGeneration: number) {
186
+ const notification = { op: "interrupted" };
187
+ sendNotebookEvent(sessionGeneration, {
188
+ event: "marimo",
189
+ data: { marimo: notification },
190
+ });
191
+ return [notification, sessionGeneration];
191
192
  }
192
193
 
193
194
  async function initializeSingleApp() {
@@ -300,7 +301,7 @@ describe("IslandsPyodideBridge", () => {
300
301
  describe("app lifecycle", () => {
301
302
  it("ignores messages after a session yields ownership", async () => {
302
303
  const consumeMessage = vi.fn();
303
- bridge.consumeMessages(consumeMessage);
304
+ bridge.consumeNotifications(consumeMessage);
304
305
  mockSingleApp();
305
306
  await bridge.initializeApps();
306
307
 
@@ -319,10 +320,7 @@ describe("IslandsPyodideBridge", () => {
319
320
  sendKernelMessage(1);
320
321
  const currentMessage = sendKernelMessage(2);
321
322
 
322
- expect(consumeMessage.mock.calls).toEqual([
323
- [firstMessage],
324
- [currentMessage],
325
- ]);
323
+ expect(consumeMessage.mock.calls).toEqual([firstMessage, currentMessage]);
326
324
 
327
325
  finishReplacement();
328
326
  await replacement;
@@ -330,7 +328,7 @@ describe("IslandsPyodideBridge", () => {
330
328
 
331
329
  it("restores message ownership when replacement fails", async () => {
332
330
  const consumeMessage = vi.fn();
333
- bridge.consumeMessages(consumeMessage);
331
+ bridge.consumeNotifications(consumeMessage);
334
332
  mockSingleApp();
335
333
  await bridge.initializeApps();
336
334
  mockReplaceSessionRequest.mockRejectedValueOnce(
@@ -344,12 +342,12 @@ describe("IslandsPyodideBridge", () => {
344
342
  const previousMessage = sendKernelMessage(1);
345
343
  sendKernelMessage(2);
346
344
 
347
- expect(consumeMessage.mock.calls).toEqual([[previousMessage]]);
345
+ expect(consumeMessage.mock.calls).toEqual([previousMessage]);
348
346
  });
349
347
 
350
348
  it("ignores messages while their session is stopping", async () => {
351
349
  const consumeMessage = vi.fn();
352
- bridge.consumeMessages(consumeMessage);
350
+ bridge.consumeNotifications(consumeMessage);
353
351
  mockSingleApp();
354
352
  await bridge.initializeApps();
355
353
  let finishStop!: () => void;
@@ -373,7 +371,7 @@ describe("IslandsPyodideBridge", () => {
373
371
 
374
372
  it("forwards messages from every app in a multi-app document", async () => {
375
373
  const consumeMessage = vi.fn();
376
- bridge.consumeMessages(consumeMessage);
374
+ bridge.consumeNotifications(consumeMessage);
377
375
  mockParseMarimoIslandApps.mockReturnValue([app(), app("app-2")]);
378
376
  mockCreateMarimoFile
379
377
  .mockReturnValueOnce("generated app 1")
@@ -385,10 +383,17 @@ describe("IslandsPyodideBridge", () => {
385
383
  const secondMessage = sendKernelMessage(2);
386
384
  sendKernelMessage(3);
387
385
 
388
- expect(consumeMessage.mock.calls).toEqual([
389
- [firstMessage],
390
- [secondMessage],
391
- ]);
386
+ expect(consumeMessage.mock.calls).toEqual([firstMessage, secondMessage]);
387
+ });
388
+
389
+ it("delivers only the notebook stream's marimo notifications", async () => {
390
+ const consumeMessage = vi.fn();
391
+ bridge.consumeNotifications(consumeMessage);
392
+ await initializeSingleApp();
393
+ sendNotebookEvent(1, { event: "ready", id: "3", data: {} });
394
+ const notification = sendKernelMessage(1);
395
+
396
+ expect(consumeMessage.mock.calls).toEqual([notification]);
392
397
  });
393
398
 
394
399
  it("holds controls until the first app session is ready", async () => {