@marimo-team/islands 0.25.3-dev2 → 0.25.3-dev200

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 (690) hide show
  1. package/dist/{ConnectedDataExplorerComponent-CNSxdKyJ.js → ConnectedDataExplorerComponent-BsWiIPFk.js} +22 -20
  2. package/dist/{ErrorBoundary-DWEpirf3.js → ErrorBoundary-UWARECs-.js} +19 -19
  3. package/dist/{abnfDiagram-VCTEODGH-DQDjNXt3.js → abnfDiagram-VCTEODGH-I2x4Yu25.js} +2 -2
  4. package/dist/any-language-editor-BVFHDDQ3.js +75 -0
  5. package/dist/{architectureDiagram-5GKGNRK7-Nmls7Wxn.js → architectureDiagram-5GKGNRK7-1bSQMKzK.js} +1 -1
  6. package/dist/{arrays-CN1djC4k.js → arrays-DoQ-AILx.js} +15 -27
  7. package/dist/assets/__vite-browser-external-BCJsx8QS.js +1 -0
  8. package/dist/assets/worker-DodjWT_Z.js +113 -0
  9. package/dist/{button-CvjkwdSk.js → button-BQRdqQi1.js} +199 -192
  10. package/dist/{capabilities-CQ5IjhzL.js → capabilities-C2QUNRXi.js} +2 -2
  11. package/dist/{chat-ui-BDpymeoe.js → chat-ui-DXDoSuS4.js} +667 -667
  12. package/dist/{check-EDwSwP89.js → check-C9Mp9eCK.js} +1 -1
  13. package/dist/{chunk-IMKFNOWR-CoIFEo-1.js → chunk-IMKFNOWR-fsCGAJ9G.js} +1 -1
  14. package/dist/{chunk-SHT3W25Y-lHiGx3ZC.js → chunk-SHT3W25Y-D2STW4hj.js} +1 -1
  15. package/dist/{chunk-SVP7TREG-BvsHIrY_.js → chunk-SVP7TREG-CiY7cQG-.js} +1 -1
  16. package/dist/{chunk-TICWLB2K-BC8YIm_n.js → chunk-TICWLB2K-C_t5RBp9.js} +1 -1
  17. package/dist/{chunk-YOKDWASO-DPZk8vhS.js → chunk-YOKDWASO-DKplTrBY.js} +20 -20
  18. package/dist/{classDiagram-ZZMXUADV-Bt98lkkv.js → classDiagram-ZZMXUADV-B2JvZAP4.js} +2 -2
  19. package/dist/{classDiagram-v2-VYDZK3BY-D9bfbcC3.js → classDiagram-v2-VYDZK3BY-L8VsZG5A.js} +2 -2
  20. package/dist/{code-visibility-CLNfgCjd.js → code-visibility-33fxfX1p.js} +45 -49
  21. package/dist/{common-fyD_6mT2.js → common-D09oJJ8Z.js} +7354 -6884
  22. package/dist/{copy-icon-Ft7t9bqz.js → copy-icon-De584pZ4.js} +3 -3
  23. package/dist/{cynefinDiagram-5FMLGOSQ-CgWra7wt.js → cynefinDiagram-5FMLGOSQ-DdllC264.js} +1 -1
  24. package/dist/{dagre-GXQ25YYZ-CFZ8-35c.js → dagre-GXQ25YYZ-BaWHw4_f.js} +1 -1
  25. package/dist/{data-grid-overlay-editor-BmqASKep.js → data-grid-overlay-editor-lGsInXfR.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-lCNQrW7d.js → diagram-S7CK7UJ4-pFt-tUDe.js} +1 -1
  28. package/dist/{diagram-UQ7AKVKN-CQPQ6pP_.js → diagram-UQ7AKVKN-DqGJiBp4.js} +1 -1
  29. package/dist/{diagram-VX7I27RA-Cf3b0llz.js → diagram-VX7I27RA-Dr-yzMjf.js} +1 -1
  30. package/dist/{diagram-Z3DM3KII-Bt4QLrpn.js → diagram-Z3DM3KII-8xzJzv-w.js} +1 -1
  31. package/dist/{dialog-CEBFZNyc.js → dialog-DVRfQuhD.js} +25 -25
  32. package/dist/{dist-F8Ep36rk.js → dist-B1M0bGO3.js} +1 -1
  33. package/dist/{dist-D6d86eNJ.js → dist-BA13RJj5.js} +1 -1
  34. package/dist/{dist-Bvs24R_E.js → dist-BJtmSgcE.js} +48 -48
  35. package/dist/{dist-CN_BeG2I.js → dist-Ba2VIn1K.js} +53 -53
  36. package/dist/{dist-PXYI_yuP.js → dist-Bj4bmwUm.js} +12 -12
  37. package/dist/{dist-DoE4XJBC.js → dist-BmS-ZGjl.js} +8626 -8626
  38. package/dist/{dist-BorMD-uX.js → dist-Bzogh7CW.js} +87 -87
  39. package/dist/{dist-CN8zI-XC.js → dist-CThPVKaP.js} +1385 -1382
  40. package/dist/{dist-DiDibOYr.js → dist-CTi5FTiV.js} +87 -87
  41. package/dist/{dist-diIx5qJW.js → dist-Ck_C32ye.js} +2 -2
  42. package/dist/{dist-BLfKmR-l.js → dist-D1fnFp1J.js} +1 -1
  43. package/dist/{dist-OR1OnN-y.js → dist-D3x9__Fu.js} +46 -46
  44. package/dist/{dist-BMQf5zIS.js → dist-D7mrh5sO.js} +36 -36
  45. package/dist/{dist-CSJ0MDRw.js → dist-D9Q3xjiP.js} +1 -1
  46. package/dist/{dist-BuaRHxOc.js → dist-DP60Ubh8.js} +2 -2
  47. package/dist/{dist-CSbh1PNP.js → dist-DTv9KkpW.js} +12 -12
  48. package/dist/{dist-D-wwqlzJ.js → dist-DVVwOfrD.js} +109 -109
  49. package/dist/{dist-C8fAKSH1.js → dist-DYXM73-k.js} +36 -36
  50. package/dist/{dist-DBtSl3sf.js → dist-DjeybPOb.js} +1 -1
  51. package/dist/{dist-CrSP_H1M.js → dist-DtGn9N4h.js} +197 -197
  52. package/dist/{dist-CLdpGQVr.js → dist-KN80qWCP.js} +2 -2
  53. package/dist/{dist-DpBpA_n1.js → dist-Lm-D-Vr6.js} +3 -3
  54. package/dist/{dist-Cg7gzw-a.js → dist-O0qFpEJh.js} +56 -56
  55. package/dist/{dist-CkTTIdBe.js → dist-OUle2RT7.js} +207 -207
  56. package/dist/{dist-BK4Oj99o.js → dist-T5rh6JvL.js} +1 -1
  57. package/dist/{dropdown-menu-CP_qCYHC.js → dropdown-menu-NlnsmNA6.js} +1481 -1433
  58. package/dist/{ebnfDiagram-PWID7BFC-D3NAyPFY.js → ebnfDiagram-PWID7BFC-Br04Wy-E.js} +2 -2
  59. package/dist/{erDiagram-RLTQ6QDP-Tlu09_Nm.js → erDiagram-RLTQ6QDP-D5-XVgvv.js} +1 -1
  60. package/dist/{error-banner-Da600cwz.js → error-banner-DxJ3s8YO.js} +89 -84
  61. package/dist/{cells-C8iCYvLU.js → error-entries-C2Ux0Fjt.js} +7970 -8605
  62. package/dist/{esm-D2gTsXEV.js → esm-Bbw_Njjx.js} +575 -575
  63. package/dist/{esm-AMFssoNp.js → esm-mDQNEFe_.js} +354 -354
  64. package/dist/feedback-button-B0CMhVv7.js +374 -0
  65. package/dist/{flowDiagram-HODETNUW-CAYbpJmV.js → flowDiagram-HODETNUW-CVl2kREF.js} +2 -2
  66. package/dist/{formats-BGh2thRc.js → formats-BCYthwyc.js} +3 -3
  67. package/dist/{ganttDiagram-EL5Y4UJY-BQT16JSc.js → ganttDiagram-EL5Y4UJY-Dh_4cBJZ.js} +2 -2
  68. package/dist/{glide-data-editor-BkjP14aq.js → glide-data-editor-CL535A5q.js} +370 -368
  69. package/dist/{glide-utils-DJyqh0EM.js → glide-utils-D98laidb.js} +16 -16
  70. package/dist/{globals-BN2O0F8N.js → globals-Bsr6T2yD.js} +3 -3
  71. package/dist/{highlighted-body-KPVGNVTW-zwjq21tf.js → highlighted-body-KPVGNVTW-3Ziwfz-V.js} +2 -2
  72. package/dist/{html-to-image-CZY1pIZH.js → html-to-image-CkH7vdBZ.js} +478 -381
  73. package/dist/{infoDiagram-27XIBGKW-XrDxhr0x.js → infoDiagram-27XIBGKW-BJ4vNcZE.js} +1 -1
  74. package/dist/{ishikawaDiagram-5VMMS53U-CD1muzov.js → ishikawaDiagram-5VMMS53U-B_Jy1Dsm.js} +1 -1
  75. package/dist/{kanban-definition-UXKFOSKX-Dg9W142_.js → kanban-definition-UXKFOSKX-C6MkS9vw.js} +1 -1
  76. package/dist/{label-BDKF3Afc.js → label-Qvw1E97W.js} +3 -3
  77. package/dist/{linear-Cnaq3Tfb.js → linear-DWERh7eI.js} +121 -73
  78. package/dist/{loader-BQOfjTIJ.js → loader-DOVB0Syl.js} +12 -12
  79. package/dist/main.js +9706 -7708
  80. package/dist/{mermaid-CiAXjLpA.js → mermaid-Bh918qrq.js} +52 -52
  81. package/dist/mermaid-HWGCJPDP-Du3-HPQA.js +2 -0
  82. package/dist/{mindmap-definition-YA3MSWOX-DgCidgYJ.js → mindmap-definition-YA3MSWOX-BP3ZTuir.js} +1 -1
  83. package/dist/{number-overlay-editor-BEBWJnbL.js → number-overlay-editor-CzbkG4E2.js} +3 -3
  84. package/dist/{objects-CzUgoMIF.js → objects-DCmMvZtn.js} +1 -3
  85. package/dist/{once-BtE-wKRL.js → once-NnpX_HnX.js} +1 -1
  86. package/dist/{pegDiagram-XKGWAZYB-coOYYKB6.js → pegDiagram-XKGWAZYB-nNGOQtnt.js} +2 -2
  87. package/dist/{pieDiagram-E7YTZNPT-BnXTc3bj.js → pieDiagram-E7YTZNPT-CpRz5BZz.js} +1 -1
  88. package/dist/precisionRound-DhAzeRcm.js +49 -0
  89. package/dist/{process-output-e4jj9Ijt.js → process-output-OujAtFW4.js} +4 -4
  90. package/dist/{quadrantDiagram-AXDQQJYC-Ccw0xMjN.js → quadrantDiagram-AXDQQJYC-Blrm7V7_.js} +1 -1
  91. package/dist/{railroadDiagram-O6MQD6OU-B28-u83n.js → railroadDiagram-O6MQD6OU-BqOEN4I0.js} +2 -2
  92. package/dist/{react-vega-BED0DjiB.js → react-vega-C4T9Rb_w.js} +12284 -12270
  93. package/dist/{requirementDiagram-BXWQKSXE-CdYCTMu0.js → requirementDiagram-BXWQKSXE-CEfg6vu9.js} +1 -1
  94. package/dist/{reveal-component-DK69bOki.js → reveal-component-CbEK0sNX.js} +733 -710
  95. package/dist/{select-BButFi-d.js → select-2KOiReNY.js} +536 -457
  96. package/dist/{sequenceDiagram-WJ2MYXX4-CM3aRAe_.js → sequenceDiagram-WJ2MYXX4-IOmpQcOi.js} +1 -1
  97. package/dist/{spec-BwarBpUJ.js → spec-Dkp64vVQ.js} +41 -11
  98. package/dist/{stateDiagram-D77RDMKH-DOZUMVj8.js → stateDiagram-D77RDMKH-tgU-EY9_.js} +2 -2
  99. package/dist/{stateDiagram-v2-MP3YSRHH-CISYxma6.js → stateDiagram-v2-MP3YSRHH-BofhG6q1.js} +2 -2
  100. package/dist/style.css +1 -1
  101. package/dist/{swimlanes-42K2YHIH-BkSppxp8.js → swimlanes-42K2YHIH-DW4vWDBd.js} +1 -1
  102. package/dist/{swimlanesDiagram-VR7AAH4N-c8G5pGxC.js → swimlanesDiagram-VR7AAH4N-BJcrqUJr.js} +2 -2
  103. package/dist/{swiper-component-DKntyn8p.js → swiper-component-BVfnhbnt.js} +2 -2
  104. package/dist/{time-BieKwdYS.js → time-BaMbJs4z.js} +18 -18
  105. package/dist/{timeline-definition-24CTP7MA-CaMQayqK.js → timeline-definition-24CTP7MA-D_QU3NGs.js} +1 -1
  106. package/dist/{toDate-BNJf01u1.js → toDate-BNDEXbfV.js} +77 -74
  107. package/dist/{toast-B9UMEi8u.js → toast-B5t9o6s_.js} +219 -201
  108. package/dist/{tooltip-BO1REbqs.js → tooltip-s4zZxwKe.js} +325 -301
  109. package/dist/{use-restore-focus-BEM7sFWl.js → use-restore-focus-BgDTd2tc.js} +1482 -1433
  110. package/dist/{useAsyncData-Deh5kszT.js → useAsyncData-ASDni9vH.js} +15 -14
  111. package/dist/{useDateFormatter-D8XruNGG.js → useDateFormatter-D3Tkfzej.js} +2 -2
  112. package/dist/{useDeepCompareMemoize-DXwzRINI.js → useDeepCompareMemoize-B1Ogyf53.js} +1 -1
  113. package/dist/{useIframeCapabilities-DBETvvPl.js → useIframeCapabilities-6a_yDNXp.js} +1 -1
  114. package/dist/{useLifecycle-j7D9uD1o.js → useLifecycle-Bfpa2m7k.js} +28 -25
  115. package/dist/{useTheme-CRnjkku0.js → useTheme-5TwyOh3B.js} +522 -314
  116. package/dist/{vega-component-DG29TAB7.js → vega-component-BHS9UOtC.js} +158 -158
  117. package/dist/{vega-embed-container-BNHE18G9.js → vega-embed-container--LYZqguO.js} +2 -2
  118. package/dist/{vega-loader.browser-DNST6uVf.js → vega-loader.browser-B9Pz0EGP.js} +298 -507
  119. package/dist/{vennDiagram-4TSXK5OY-CF8pfaK3.js → vennDiagram-4TSXK5OY-YFYsNIAh.js} +1 -1
  120. package/dist/{wardleyDiagram-VM6X3IG4-dGPu39d-.js → wardleyDiagram-VM6X3IG4-i_n8mAWC.js} +1 -1
  121. package/dist/{xychartDiagram-S5SC5T6Z-CP6-9q56.js → xychartDiagram-S5SC5T6Z-BYGN95wW.js} +2 -2
  122. package/package.json +16 -16
  123. package/src/__mocks__/document.tsx +63 -0
  124. package/src/__mocks__/notebook.ts +3 -4
  125. package/src/__mocks__/partial.ts +26 -0
  126. package/src/__mocks__/requests.ts +0 -3
  127. package/src/__tests__/fixtures/{pair-preview.ts → pair-config.ts} +3 -2
  128. package/src/__tests__/main.test.tsx +24 -1
  129. package/src/__tests__/module-entry.test.ts +44 -0
  130. package/src/__tests__/mount.test.ts +9 -9
  131. package/src/__tests__/{host-imports.test.ts → replica-imports.test.ts} +12 -11
  132. package/src/components/ai/__tests__/ai-model-dropdown.test.tsx +63 -0
  133. package/src/components/ai/ai-model-dropdown.tsx +11 -6
  134. package/src/components/app-config/ai-config.tsx +7 -2
  135. package/src/components/app-config/app-config-form.tsx +5 -9
  136. package/src/components/app-config/user-config-form.tsx +35 -0
  137. package/src/components/chat/__tests__/message-queue.test.tsx +17 -0
  138. package/src/components/chat/__tests__/notebook-access-selector.test.tsx +64 -0
  139. package/src/components/chat/acp/__tests__/session-tabs.test.tsx +43 -0
  140. package/src/components/chat/acp/__tests__/state.test.ts +2 -2
  141. package/src/components/chat/acp/blocks.tsx +3 -2
  142. package/src/components/chat/acp/session-tabs.tsx +8 -3
  143. package/src/components/chat/chat-components.tsx +2 -0
  144. package/src/components/chat/chat-panel.tsx +20 -101
  145. package/src/components/chat/chat-utils.ts +4 -8
  146. package/src/components/chat/notebook-access-selector.stories.tsx +22 -0
  147. package/src/components/chat/notebook-access-selector.tsx +100 -0
  148. package/src/components/data-table/TableBottomBar.tsx +4 -1
  149. package/src/components/data-table/TableTopBar.tsx +2 -0
  150. package/src/components/data-table/__tests__/chart-spec-model.test.ts +195 -195
  151. package/src/components/data-table/__tests__/column-explorer.test.tsx +27 -1
  152. package/src/components/data-table/__tests__/columns.test.tsx +105 -0
  153. package/src/components/data-table/__tests__/context-menu-interaction.test.tsx +130 -0
  154. package/src/components/data-table/__tests__/context-menu.test.ts +176 -0
  155. package/src/components/data-table/__tests__/data-table.test.tsx +1 -0
  156. package/src/components/data-table/__tests__/date-filter-inputs.test.tsx +24 -1
  157. package/src/components/data-table/__tests__/date-popover.test.tsx +72 -0
  158. package/src/components/data-table/__tests__/export-actions.test.tsx +434 -6
  159. package/src/components/data-table/__tests__/keyboard-selection.test.tsx +188 -0
  160. package/src/components/data-table/__tests__/pagination.test.tsx +28 -1
  161. package/src/components/data-table/__tests__/search-highlight.test.tsx +109 -0
  162. package/src/components/data-table/__tests__/url-detector.test.tsx +74 -0
  163. package/src/components/data-table/cell-selection/feature.ts +2 -2
  164. package/src/components/data-table/cell-selection/types.ts +2 -2
  165. package/src/components/data-table/charts/__tests__/chart-panel.test.tsx +74 -1
  166. package/src/components/data-table/charts/__tests__/spec-snapshot.test.ts +20 -20
  167. package/src/components/data-table/charts/__tests__/spec.test.ts +78 -52
  168. package/src/components/data-table/charts/__tests__/storage.test.ts +4 -1
  169. package/src/components/data-table/charts/chart-spec/spec.ts +68 -43
  170. package/src/components/data-table/charts/charts.tsx +40 -30
  171. package/src/components/data-table/charts/storage.ts +16 -5
  172. package/src/components/data-table/column-explorer-panel/column-explorer.tsx +1 -1
  173. package/src/components/data-table/column-summary/chart-spec-model.tsx +23 -16
  174. package/src/components/data-table/column-summary/column-summary.tsx +2 -4
  175. package/src/components/data-table/column-visibility-dropdown.tsx +8 -13
  176. package/src/components/data-table/columns.tsx +45 -46
  177. package/src/components/data-table/context-menu.tsx +161 -46
  178. package/src/components/data-table/data-table.tsx +17 -1
  179. package/src/components/data-table/date-filter-inputs.tsx +15 -42
  180. package/src/components/data-table/date-popover.tsx +6 -4
  181. package/src/components/data-table/export-actions.tsx +267 -163
  182. package/src/components/data-table/pagination.tsx +44 -33
  183. package/src/components/data-table/range-focus/atoms.ts +4 -6
  184. package/src/components/data-table/range-focus/use-cell-range-selection.ts +65 -38
  185. package/src/components/data-table/range-focus/use-scroll-into-view.ts +21 -2
  186. package/src/components/data-table/renderers.tsx +16 -7
  187. package/src/components/data-table/row-viewer-panel/__tests__/row-viewer.test.tsx +24 -1
  188. package/src/components/data-table/row-viewer-panel/row-viewer.tsx +4 -4
  189. package/src/components/data-table/schemas.ts +14 -36
  190. package/src/components/data-table/search-highlight.tsx +79 -0
  191. package/src/components/data-table/types.ts +1 -0
  192. package/src/components/data-table/url-detector.tsx +49 -9
  193. package/src/components/data-table/utils.ts +18 -0
  194. package/src/components/datasources/__tests__/column-actions.test.tsx +97 -0
  195. package/src/components/datasources/__tests__/column-preview.test.tsx +96 -5
  196. package/src/components/datasources/__tests__/datasources-interactions.test.tsx +181 -0
  197. package/src/components/datasources/__tests__/table-list.test.tsx +118 -0
  198. package/src/components/datasources/__tests__/utils.test.ts +57 -6
  199. package/src/components/datasources/column-preview.tsx +17 -12
  200. package/src/components/datasources/datasources.tsx +56 -43
  201. package/src/components/datasources/utils.ts +32 -23
  202. package/src/components/debugger/debugger-code.tsx +5 -0
  203. package/src/components/dependency-graph/custom-node.tsx +1 -1
  204. package/src/components/dependency-graph/dependency-graph-tree.tsx +8 -8
  205. package/src/components/dependency-graph/elements.ts +24 -21
  206. package/src/components/dependency-graph/minimap-content.tsx +13 -19
  207. package/src/components/dependency-graph/panels.tsx +4 -2
  208. package/src/components/dependency-graph/utils/__tests__/layout.test.ts +18 -11
  209. package/src/components/editor/Output.tsx +9 -2
  210. package/src/components/editor/SortableCell.tsx +1 -3
  211. package/src/components/editor/__tests__/Output.test.tsx +50 -32
  212. package/src/components/editor/__tests__/agent-toast.test.tsx +58 -0
  213. package/src/components/editor/__tests__/data-attributes.test.tsx +28 -14
  214. package/src/components/editor/__tests__/dynamic-favicon.test.tsx +111 -18
  215. package/src/components/editor/__tests__/output-persistence.test.tsx +6 -2
  216. package/src/components/editor/__tests__/package-alert.test.tsx +22 -1
  217. package/src/components/editor/actions/__tests__/name-cell-input.test.tsx +69 -0
  218. package/src/components/editor/actions/__tests__/pair-with-agent-commands.test.ts +80 -252
  219. package/src/components/editor/actions/__tests__/pair-with-agent-modal.test.tsx +218 -40
  220. package/src/components/editor/actions/__tests__/pair-with-agent.test.tsx +2 -6
  221. package/src/components/editor/actions/name-cell-input.tsx +4 -3
  222. package/src/components/editor/actions/pair-with-agent-commands.ts +44 -53
  223. package/src/components/editor/actions/pair-with-agent-modal.tsx +101 -38
  224. package/src/components/editor/actions/useCellActionButton.tsx +26 -31
  225. package/src/components/editor/actions/useConfigActions.tsx +3 -4
  226. package/src/components/editor/actions/useNotebookActions.tsx +19 -23
  227. package/src/components/editor/actions/useRestartKernel.tsx +1 -1
  228. package/src/components/editor/actions/useSetCodeVisibility.ts +11 -12
  229. package/src/components/editor/actions/useSetOutputsExpanded.ts +14 -19
  230. package/src/components/editor/agent-toast.ts +15 -0
  231. package/src/components/editor/ai/add-cell-with-ai.tsx +3 -3
  232. package/src/components/editor/ai/ai-completion-editor.tsx +1 -0
  233. package/src/components/editor/alerts/__tests__/connection-notice.test.tsx +1 -1
  234. package/src/components/editor/alerts/connection-notice.tsx +1 -1
  235. package/src/components/editor/alerts/startup-logs-alert.tsx +1 -0
  236. package/src/components/editor/alerts/stdin-blocking-alert.tsx +1 -1
  237. package/src/components/editor/app-container.tsx +1 -1
  238. package/src/components/editor/boundary/__tests__/ErrorBoundary.test.tsx +1 -1
  239. package/src/components/editor/cell/CreateCellButton.tsx +15 -21
  240. package/src/components/editor/cell/DeleteButton.tsx +3 -2
  241. package/src/components/editor/cell/RunButton.tsx +2 -2
  242. package/src/components/editor/cell/StagedAICell.tsx +10 -2
  243. package/src/components/editor/cell/StopButton.tsx +2 -2
  244. package/src/components/editor/cell/__tests__/StagedAICell.test.tsx +3 -1
  245. package/src/components/editor/cell/__tests__/useShouldShowInterrupt.test.ts +39 -0
  246. package/src/components/editor/cell/cell-actions.tsx +12 -1
  247. package/src/components/editor/cell/code/__tests__/language-toggle.test.tsx +54 -0
  248. package/src/components/editor/cell/code/cell-editor.tsx +36 -43
  249. package/src/components/editor/cell/code/language-toggle.tsx +8 -7
  250. package/src/components/editor/cell/collapse.tsx +11 -4
  251. package/src/components/editor/cell/useAddCell.ts +4 -8
  252. package/src/components/editor/cell/useDeleteCell.tsx +10 -36
  253. package/src/components/editor/cell/useRunCells.ts +2 -5
  254. package/src/components/editor/cell/useShouldShowInterrupt.ts +2 -12
  255. package/src/components/editor/cell/useSplitCell.tsx +10 -6
  256. package/src/components/editor/chrome/components/__tests__/feedback-button.test.tsx +1 -1
  257. package/src/components/editor/chrome/components/feedback-button.tsx +2 -8
  258. package/src/components/editor/chrome/panels/__tests__/packages-panel.test.tsx +31 -2
  259. package/src/components/editor/chrome/panels/__tests__/runtime-details.test.tsx +1 -1
  260. package/src/components/editor/chrome/panels/__tests__/sandbox-recovery.test.tsx +1 -1
  261. package/src/components/editor/chrome/panels/cache-panel.tsx +1 -0
  262. package/src/components/editor/chrome/panels/dependency-graph-panel.tsx +1 -1
  263. package/src/components/editor/chrome/panels/error-panel.tsx +1 -0
  264. package/src/components/editor/chrome/panels/logs-panel.tsx +2 -1
  265. package/src/components/editor/chrome/panels/outline/__tests__/outline-keyboard.test.tsx +84 -0
  266. package/src/components/editor/chrome/panels/outline/floating-outline.tsx +39 -14
  267. package/src/components/editor/chrome/panels/outline/useActiveOutline.tsx +3 -2
  268. package/src/components/editor/chrome/panels/packages-panel.tsx +4 -7
  269. package/src/components/editor/chrome/panels/secrets-panel.tsx +1 -0
  270. package/src/components/editor/chrome/panels/session-panel.tsx +1 -1
  271. package/src/components/editor/chrome/panels/snippets-panel.tsx +10 -12
  272. package/src/components/editor/chrome/panels/variable-panel.tsx +1 -5
  273. package/src/components/editor/chrome/wrapper/__tests__/attachment-status.test.tsx +363 -0
  274. package/src/components/editor/chrome/wrapper/__tests__/document-sync-status.test.tsx +92 -0
  275. package/src/components/editor/chrome/wrapper/__tests__/pending-ai-cells.test.tsx +61 -2
  276. package/src/components/editor/chrome/wrapper/footer-item.tsx +32 -24
  277. package/src/components/editor/chrome/wrapper/footer-items/attachment-status.tsx +237 -0
  278. package/src/components/editor/chrome/wrapper/footer-items/backend-status.tsx +1 -1
  279. package/src/components/editor/chrome/wrapper/footer-items/document-sync-status.tsx +54 -0
  280. package/src/components/editor/chrome/wrapper/footer-items/lsp-status.tsx +1 -1
  281. package/src/components/editor/chrome/wrapper/footer-items/machine-stats.tsx +1 -1
  282. package/src/components/editor/chrome/wrapper/footer-items/runtime-settings.tsx +1 -7
  283. package/src/components/editor/chrome/wrapper/footer.tsx +4 -0
  284. package/src/components/editor/chrome/wrapper/minimap-state.ts +1 -1
  285. package/src/components/editor/chrome/wrapper/pending-ai-cells.tsx +12 -2
  286. package/src/components/editor/chrome/wrapper/storage.ts +1 -1
  287. package/src/components/editor/columns/__tests__/cell-column.test.tsx +1 -1
  288. package/src/components/editor/columns/cell-column.tsx +1 -1
  289. package/src/components/editor/columns/sortable-column.tsx +2 -2
  290. package/src/components/editor/connections/components.tsx +5 -10
  291. package/src/components/editor/controls/Controls.tsx +4 -4
  292. package/src/components/editor/controls/__tests__/command-palette.test.tsx +53 -0
  293. package/src/components/editor/controls/__tests__/keyboard-shortcuts.test.tsx +61 -0
  294. package/src/components/editor/controls/__tests__/notebook-menu-dropdown.test.tsx +10 -4
  295. package/src/components/editor/controls/command-palette.tsx +22 -10
  296. package/src/components/editor/controls/keyboard-shortcuts.tsx +14 -5
  297. package/src/components/editor/documentation.css +34 -11
  298. package/src/components/editor/dynamic-favicon.tsx +21 -40
  299. package/src/components/editor/errors/__tests__/send-error-report-button.test.tsx +536 -0
  300. package/src/components/editor/errors/auto-fix.tsx +4 -8
  301. package/src/components/editor/errors/send-error-report-button.tsx +66 -0
  302. package/src/components/editor/file-tree/__tests__/file-explorer-interactions.test.tsx +6 -0
  303. package/src/components/editor/file-tree/__tests__/file-explorer-navigation.test.tsx +47 -0
  304. package/src/components/editor/file-tree/__tests__/use-file-search.test.tsx +91 -0
  305. package/src/components/editor/file-tree/file-explorer.tsx +48 -15
  306. package/src/components/editor/file-tree/file-name-input.tsx +1 -0
  307. package/src/components/editor/file-tree/file-viewer.tsx +4 -2
  308. package/src/components/editor/file-tree/use-file-search.ts +35 -21
  309. package/src/components/editor/header/__tests__/status.test.tsx +5 -3
  310. package/src/components/editor/header/app-header.tsx +1 -1
  311. package/src/components/editor/header/status.tsx +40 -20
  312. package/src/components/editor/links/__tests__/cell-link.test.tsx +148 -0
  313. package/src/components/editor/links/cell-link-list.tsx +1 -1
  314. package/src/components/editor/links/cell-link.tsx +17 -7
  315. package/src/components/editor/navigation/__tests__/clipboard.test.ts +60 -38
  316. package/src/components/editor/navigation/__tests__/navigation.test.ts +108 -85
  317. package/src/components/editor/navigation/__tests__/selection.test.ts +43 -21
  318. package/src/components/editor/navigation/clipboard.ts +17 -14
  319. package/src/components/editor/navigation/focus-utils.ts +23 -4
  320. package/src/components/editor/navigation/multi-cell-action-toolbar.tsx +17 -33
  321. package/src/components/editor/navigation/navigation.ts +71 -70
  322. package/src/components/editor/navigation/selection.ts +30 -29
  323. package/src/components/editor/notebook-banner.tsx +1 -0
  324. package/src/components/editor/notebook-cell.tsx +29 -31
  325. package/src/components/editor/output/MarimoErrorOutput.tsx +23 -6
  326. package/src/components/editor/output/MarimoTracebackOutput.tsx +54 -37
  327. package/src/components/editor/output/Outputs.css +8 -0
  328. package/src/components/editor/output/__tests__/ansi-reduce.test.ts +18 -0
  329. package/src/components/editor/output/__tests__/traceback.test.tsx +27 -1
  330. package/src/components/editor/output/ansi-reduce.ts +36 -17
  331. package/src/components/editor/output/console/ConsoleOutput.tsx +19 -25
  332. package/src/components/editor/output/console/__tests__/ConsoleOutput.test.tsx +125 -69
  333. package/src/components/editor/package-alert.tsx +14 -7
  334. package/src/components/editor/renderers/cell-array.tsx +22 -33
  335. package/src/components/editor/renderers/grid-layout/grid-layout.tsx +12 -6
  336. package/src/components/editor/renderers/slides-layout/__tests__/plugin.test.ts +0 -1
  337. package/src/components/editor/renderers/slides-layout/slides-layout.tsx +1 -1
  338. package/src/components/editor/renderers/vertical-layout/__tests__/useFocusFirstEditor.test.ts +4 -4
  339. package/src/components/editor/renderers/vertical-layout/sidebar/toggle.tsx +7 -1
  340. package/src/components/editor/renderers/vertical-layout/useFocusFirstEditor.ts +1 -1
  341. package/src/components/editor/renderers/vertical-layout/vertical-layout.tsx +1 -1
  342. package/src/components/editor/stdin-blocking-alert.tsx +1 -1
  343. package/src/components/home/components.tsx +17 -31
  344. package/src/components/icons/__tests__/large-spinner.test.tsx +39 -0
  345. package/src/components/icons/large-spinner.tsx +3 -14
  346. package/src/components/icons/spinner.tsx +1 -1
  347. package/src/components/markdown/markdown-renderer.tsx +4 -8
  348. package/src/components/mcp/mcp-status-indicator.tsx +1 -1
  349. package/src/components/pages/__tests__/home-page.test.tsx +116 -0
  350. package/src/components/pages/edit-page.tsx +19 -17
  351. package/src/components/pages/home-page.tsx +164 -91
  352. package/src/components/scratchpad/scratchpad.test.tsx +97 -0
  353. package/src/components/scratchpad/scratchpad.tsx +20 -11
  354. package/src/components/slides/__tests__/minimap-actions.test.tsx +22 -29
  355. package/src/components/slides/__tests__/minimap.test.ts +38 -19
  356. package/src/components/slides/__tests__/slide-scroll-hint.test.tsx +37 -0
  357. package/src/components/slides/minimap.tsx +17 -12
  358. package/src/components/slides/reveal-component.tsx +58 -26
  359. package/src/components/slides/reveal-slides.css +5 -4
  360. package/src/components/slides/slide-cell-view.tsx +4 -5
  361. package/src/components/slides/slide-form.tsx +1 -0
  362. package/src/components/slides/slide-scroll-hint.tsx +3 -1
  363. package/src/components/sort/SortableCellsProvider.tsx +8 -25
  364. package/src/components/tracing/tracing-keyboard.test.tsx +85 -0
  365. package/src/components/tracing/tracing.tsx +46 -42
  366. package/src/components/ui/__tests__/draggable-popover.test.tsx +24 -0
  367. package/src/components/ui/__tests__/range-slider.test.tsx +165 -0
  368. package/src/components/ui/alert-dialog.tsx +1 -1
  369. package/src/components/ui/draggable-popover.tsx +24 -2
  370. package/src/components/ui/range-slider.tsx +22 -9
  371. package/src/core/MarimoApp.tsx +1 -1
  372. package/src/core/ai/__tests__/staged-cells.test.ts +27 -26
  373. package/src/core/ai/context/providers/__tests__/cell-output.test.ts +8 -12
  374. package/src/core/ai/context/providers/cell-output.ts +2 -2
  375. package/src/core/ai/context/providers/datasource.ts +6 -2
  376. package/src/core/ai/staged-cells.ts +15 -18
  377. package/src/core/ai/tools/__tests__/edit-notebook-tool.test.ts +40 -88
  378. package/src/core/ai/tools/__tests__/registry.test.ts +17 -0
  379. package/src/core/ai/tools/base.ts +18 -15
  380. package/src/core/ai/tools/edit-notebook-tool.ts +86 -80
  381. package/src/core/ai/tools/registry.ts +13 -10
  382. package/src/core/ai/tools/sample-tool.ts +6 -7
  383. package/src/core/cells/__tests__/__snapshots__/cells.test.ts.snap +4 -37
  384. package/src/core/cells/__tests__/actions.test.ts +624 -35
  385. package/src/core/cells/__tests__/add-missing-import.test.ts +7 -8
  386. package/src/core/cells/__tests__/arrange.test.ts +432 -0
  387. package/src/core/cells/__tests__/cell.test.ts +39 -0
  388. package/src/core/cells/__tests__/cells.test.ts +256 -2477
  389. package/src/core/cells/__tests__/collapseConsoleOutputs.test.ts +54 -0
  390. package/src/core/cells/__tests__/document.test.ts +341 -0
  391. package/src/core/cells/__tests__/editor.test.ts +57 -0
  392. package/src/core/cells/__tests__/error-report.test.ts +139 -0
  393. package/src/core/cells/__tests__/flush-document.test.ts +40 -0
  394. package/src/core/cells/__tests__/harness.ts +106 -0
  395. package/src/core/cells/__tests__/layout.test.ts +177 -0
  396. package/src/core/cells/__tests__/notebook-outline.test.ts +120 -0
  397. package/src/core/cells/__tests__/outputs.test.tsx +71 -53
  398. package/src/core/cells/__tests__/session.test.ts +493 -210
  399. package/src/core/cells/__tests__/utils.test.ts +9 -108
  400. package/src/core/cells/__tests__/with-document-save.test.ts +67 -0
  401. package/src/core/cells/actions.ts +636 -6
  402. package/src/core/cells/add-missing-import.ts +47 -43
  403. package/src/core/cells/arrange.ts +529 -0
  404. package/src/core/cells/cell.ts +14 -3
  405. package/src/core/cells/cells.ts +120 -1337
  406. package/src/core/cells/columns.ts +38 -0
  407. package/src/core/cells/document.ts +289 -0
  408. package/src/core/cells/edit.ts +30 -0
  409. package/src/core/cells/editor.ts +82 -0
  410. package/src/core/cells/error-report.ts +63 -0
  411. package/src/core/cells/layout.ts +221 -0
  412. package/src/core/cells/outputs.ts +12 -28
  413. package/src/core/cells/pending-delete-service.ts +3 -7
  414. package/src/core/cells/session.ts +104 -54
  415. package/src/core/cells/types.ts +22 -6
  416. package/src/core/cells/utils.ts +10 -8
  417. package/src/core/codemirror/__tests__/setup.test.ts +29 -29
  418. package/src/core/codemirror/ai/__tests__/resources.test.ts +117 -0
  419. package/src/core/codemirror/ai/resources.ts +1 -1
  420. package/src/core/codemirror/cells/__tests__/extensions.test.ts +42 -1
  421. package/src/core/codemirror/cells/extensions.ts +27 -9
  422. package/src/core/codemirror/cells/state.ts +1 -1
  423. package/src/core/codemirror/copilot/__tests__/getCodes.test.ts +6 -7
  424. package/src/core/codemirror/copilot/getCodes.ts +2 -2
  425. package/src/core/codemirror/format.ts +6 -5
  426. package/src/core/codemirror/keymaps/vim.ts +4 -8
  427. package/src/core/codemirror/language/__tests__/sql.test.ts +22 -20
  428. package/src/core/codemirror/language/__tests__/utils.test.ts +187 -15
  429. package/src/core/codemirror/language/cell-code.ts +114 -0
  430. package/src/core/codemirror/language/extension.ts +52 -35
  431. package/src/core/codemirror/language/languages/markdown.ts +8 -6
  432. package/src/core/codemirror/language/languages/python.ts +16 -10
  433. package/src/core/codemirror/language/languages/sql/sql.ts +16 -24
  434. package/src/core/codemirror/language/panel/panel.tsx +1 -0
  435. package/src/core/codemirror/language/types.ts +7 -7
  436. package/src/core/codemirror/language/utils.ts +9 -39
  437. package/src/core/codemirror/lsp/__tests__/notebook-lsp.test.ts +1 -2
  438. package/src/core/codemirror/lsp/notebook-lsp.ts +6 -5
  439. package/src/core/codemirror/lsp/utils.ts +1 -1
  440. package/src/core/codemirror/readonly/__tests__/extension.test.ts +1 -1
  441. package/src/core/codemirror/readonly/extension.ts +2 -2
  442. package/src/core/codemirror/rtc/extension.ts +24 -13
  443. package/src/core/codemirror/rtc/loro/awareness.ts +34 -19
  444. package/src/core/codemirror/rtc/loro/sync.ts +1 -0
  445. package/src/core/codemirror/utils.ts +1 -0
  446. package/src/core/config/__tests__/app-config.test.ts +64 -0
  447. package/src/core/config/__tests__/config-schema.test.ts +13 -6
  448. package/src/core/config/config-schema.ts +13 -3
  449. package/src/core/config/config.ts +26 -12
  450. package/src/core/config/pair.ts +5 -3
  451. package/src/core/datasets/__tests__/data-source-discovery.test.ts +5 -5
  452. package/src/core/datasets/data-source-discovery.ts +4 -6
  453. package/src/core/documentation/doc-lookup.ts +1 -1
  454. package/src/core/edit-app.tsx +21 -28
  455. package/src/core/errors/error-entries.ts +4 -1
  456. package/src/core/export/hooks.ts +1 -1
  457. package/src/core/export/layout.ts +2 -2
  458. package/src/core/hotkeys/actions.ts +2 -4
  459. package/src/core/islands/__tests__/bootstrap.test.ts +69 -17
  460. package/src/core/islands/__tests__/bridge.test.ts +72 -25
  461. package/src/core/islands/bootstrap.ts +46 -53
  462. package/src/core/islands/bridge.ts +74 -23
  463. package/src/core/islands/components/__tests__/IslandControls.test.tsx +7 -5
  464. package/src/core/islands/components/web-components.tsx +1 -1
  465. package/src/core/islands/worker/__tests__/controller.test.ts +62 -4
  466. package/src/core/islands/worker/controller.ts +4 -10
  467. package/src/core/islands/worker/worker.tsx +33 -33
  468. package/src/core/kernel/__tests__/RuntimeState.test.ts +1 -1
  469. package/src/core/kernel/__tests__/handlers.test.ts +7 -153
  470. package/src/core/kernel/handlers.ts +19 -72
  471. package/src/core/meta/__tests__/code-visibility.test.tsx +78 -70
  472. package/src/core/meta/code-visibility.ts +18 -9
  473. package/src/core/network/__tests__/connection.test.ts +1 -1
  474. package/src/core/network/__tests__/requests-lazy.test.ts +1 -3
  475. package/src/core/network/connection-notice.ts +1 -1
  476. package/src/core/network/connection.ts +5 -3
  477. package/src/core/network/requests-lazy.ts +1 -4
  478. package/src/core/network/requests-network.ts +0 -25
  479. package/src/core/network/requests-static.ts +0 -3
  480. package/src/core/network/requests-toasting.tsx +0 -3
  481. package/src/core/network/types.ts +0 -12
  482. package/src/core/network/useConnectionNotice.ts +8 -2
  483. package/src/core/notebook/__tests__/operations.test.ts +51 -0
  484. package/src/core/notebook/attachments.ts +38 -0
  485. package/src/core/notebook/document/__tests__/codemirror.test.ts +586 -0
  486. package/src/core/notebook/document/__tests__/draft.test.ts +363 -0
  487. package/src/core/notebook/document/__tests__/fixtures.ts +92 -0
  488. package/src/core/notebook/document/__tests__/hold.test.ts +88 -0
  489. package/src/core/notebook/document/__tests__/hooks.test.tsx +391 -0
  490. package/src/core/notebook/document/__tests__/lifecycle-scenarios.test.ts +61 -0
  491. package/src/core/notebook/document/__tests__/model.test.ts +247 -0
  492. package/src/core/notebook/document/__tests__/protocol-fixtures.ts +38 -0
  493. package/src/core/notebook/document/__tests__/recovery-scenarios.test.ts +230 -0
  494. package/src/core/notebook/document/__tests__/scenario-fixture.ts +43 -0
  495. package/src/core/notebook/document/__tests__/scenarios.test.ts +205 -0
  496. package/src/core/notebook/document/__tests__/state.test.ts +459 -0
  497. package/src/core/notebook/document/__tests__/submission.test.ts +203 -0
  498. package/src/core/notebook/document/__tests__/test-host.test.ts +92 -0
  499. package/src/core/notebook/document/__tests__/test-host.ts +247 -0
  500. package/src/core/notebook/document/__tests__/test-notebook.ts +149 -0
  501. package/src/core/notebook/document/__tests__/user.ts +61 -0
  502. package/src/core/notebook/document/codemirror.ts +216 -0
  503. package/src/core/notebook/document/draft.ts +502 -0
  504. package/src/core/notebook/document/hooks.tsx +118 -0
  505. package/src/core/notebook/document/index.ts +24 -0
  506. package/src/core/notebook/document/model.ts +105 -0
  507. package/src/core/notebook/document/select.ts +41 -0
  508. package/src/core/notebook/document/state.ts +378 -0
  509. package/src/core/notebook/document/sync.ts +418 -0
  510. package/src/core/notebook/index.ts +19 -0
  511. package/src/core/notebook/operations.ts +30 -0
  512. package/src/core/notebook/replica/AGENTS.md +11 -0
  513. package/src/core/notebook/replica/__tests__/attachments.test.ts +56 -0
  514. package/src/core/notebook/replica/__tests__/document.test.ts +126 -0
  515. package/src/core/notebook/replica/__tests__/fixtures.ts +79 -0
  516. package/src/core/notebook/replica/__tests__/replica.test.ts +550 -0
  517. package/src/core/notebook/replica/backend.ts +19 -0
  518. package/src/core/{websocket/types.ts → notebook/replica/connection.ts} +10 -15
  519. package/src/core/notebook/replica/index.ts +13 -0
  520. package/src/core/notebook/replica/replica.ts +286 -0
  521. package/src/core/notebook/replica/resources/attachments.ts +22 -0
  522. package/src/core/notebook/replica/resources/document.ts +101 -0
  523. package/src/core/packages/__tests__/useSandboxController.test.tsx +1 -1
  524. package/src/core/packages/useSandboxController.ts +1 -1
  525. package/src/core/run-app.tsx +48 -51
  526. package/src/core/runtime/__tests__/adapter.test.ts +1 -1
  527. package/src/core/runtime/__tests__/createWsUrl.test.ts +77 -7
  528. package/src/core/runtime/__tests__/runtime.test.ts +33 -15
  529. package/src/core/runtime/adapter.ts +1 -1
  530. package/src/core/runtime/config.ts +2 -2
  531. package/src/core/runtime/runtime.ts +39 -30
  532. package/src/core/saving/__tests__/state.test.ts +111 -0
  533. package/src/core/saving/__tests__/useAutoSave.test.tsx +67 -0
  534. package/src/core/saving/filename.ts +1 -1
  535. package/src/core/saving/save-component.tsx +28 -36
  536. package/src/core/saving/state.ts +38 -39
  537. package/src/core/saving/useAutoSave.ts +17 -53
  538. package/src/core/session/__tests__/backend.test.ts +236 -0
  539. package/src/core/session/__tests__/useNotebookReplica.hook.test.tsx +184 -0
  540. package/src/core/{websocket/__tests__/useMarimoKernelConnection.hook.test.tsx → session/__tests__/useNotebookSession.hook.test.tsx} +252 -185
  541. package/src/core/session/active-notebook.ts +22 -0
  542. package/src/core/session/backend.ts +123 -0
  543. package/src/core/session/embedded.ts +7 -0
  544. package/src/core/session/types.ts +17 -0
  545. package/src/core/session/useNotebookReplica.ts +74 -0
  546. package/src/core/{websocket/useMarimoKernelConnection.tsx → session/useNotebookSession.tsx} +120 -273
  547. package/src/core/state/__tests__/jotai.test.tsx +108 -0
  548. package/src/core/state/jotai.ts +1 -1
  549. package/src/core/static/__tests__/files.test.ts +38 -10
  550. package/src/core/static/files.ts +2 -0
  551. package/src/core/{websocket/__tests__/useMarimoKernelConnection.test.ts → transports/__tests__/connection-state.test.ts} +16 -30
  552. package/src/core/transports/__tests__/server.test.ts +408 -0
  553. package/src/core/transports/__tests__/static.test.ts +306 -0
  554. package/src/core/transports/__tests__/wasm.test.ts +166 -0
  555. package/src/core/transports/connection-state.ts +63 -0
  556. package/src/core/transports/server.ts +152 -0
  557. package/src/core/transports/static.ts +166 -0
  558. package/src/core/transports/wasm.ts +97 -0
  559. package/src/core/wasm/__tests__/bridge.test.ts +214 -50
  560. package/src/core/wasm/__tests__/worker.test.ts +187 -0
  561. package/src/core/wasm/bridge.ts +75 -69
  562. package/src/core/wasm/rpc.ts +15 -3
  563. package/src/core/wasm/store.ts +3 -3
  564. package/src/core/wasm/worker/bootstrap.ts +55 -51
  565. package/src/core/wasm/worker/getMarimoWheel.ts +1 -1
  566. package/src/core/wasm/worker/save-worker.ts +9 -10
  567. package/src/core/wasm/worker/types.ts +29 -18
  568. package/src/core/wasm/worker/worker.ts +88 -44
  569. package/src/css/globals.css +66 -22
  570. package/src/hooks/__tests__/useAsyncData.test.tsx +148 -0
  571. package/src/hooks/__tests__/useDebounce.test.tsx +51 -0
  572. package/src/hooks/__tests__/useDeepCompareMemoize.test.tsx +39 -0
  573. package/src/hooks/__tests__/useDelayElapsed.test.tsx +28 -0
  574. package/src/hooks/__tests__/useInternalStateWithSync.test.tsx +20 -0
  575. package/src/hooks/__tests__/useScript.test.tsx +77 -0
  576. package/src/hooks/__tests__/useStateForKey.test.tsx +257 -0
  577. package/src/hooks/useAsyncData.ts +3 -3
  578. package/src/hooks/useDataSourceDiscovery.ts +6 -4
  579. package/src/hooks/useDebounce.ts +6 -10
  580. package/src/hooks/useDeepCompareMemoize.ts +1 -1
  581. package/src/hooks/useDelayElapsed.ts +14 -10
  582. package/src/hooks/useElapsedTime.ts +3 -3
  583. package/src/hooks/useEventListener.ts +1 -2
  584. package/src/hooks/useInputHistory.ts +4 -7
  585. package/src/hooks/useInternalStateWithSync.ts +6 -6
  586. package/src/hooks/useResizeObserver.ts +4 -7
  587. package/src/hooks/useScript.ts +67 -70
  588. package/src/hooks/useStateForKey.ts +93 -0
  589. package/src/mount.tsx +23 -14
  590. package/src/plugins/__tests__/plugin-object-schemas.test.ts +104 -0
  591. package/src/plugins/core/registerReactComponent.tsx +1 -1
  592. package/src/plugins/impl/CodeEditorPlugin.tsx +1 -1
  593. package/src/plugins/impl/DataEditorPlugin.tsx +1 -1
  594. package/src/plugins/impl/DataTablePlugin.tsx +69 -37
  595. package/src/plugins/impl/DropdownPlugin.tsx +2 -6
  596. package/src/plugins/impl/FileBrowserPlugin.tsx +4 -16
  597. package/src/plugins/impl/FormPlugin.tsx +1 -1
  598. package/src/plugins/impl/RangeSliderPlugin.tsx +16 -2
  599. package/src/plugins/impl/RefreshPlugin.tsx +1 -0
  600. package/src/plugins/impl/SliderPlugin.tsx +6 -8
  601. package/src/plugins/impl/__tests__/DataTablePlugin.test.tsx +471 -1
  602. package/src/plugins/impl/__tests__/FileBrowserPlugin.test.tsx +45 -0
  603. package/src/plugins/impl/__tests__/RangeSliderPlugin.test.tsx +109 -0
  604. package/src/plugins/impl/__tests__/SliderPlugin.test.tsx +24 -3
  605. package/src/plugins/impl/anywidget/__tests__/registry.test.ts +153 -0
  606. package/src/plugins/impl/anywidget/__tests__/widget-binding.test.ts +241 -2
  607. package/src/plugins/impl/anywidget/model.ts +3 -1
  608. package/src/plugins/impl/anywidget/registry.ts +18 -14
  609. package/src/plugins/impl/anywidget/runtime.ts +21 -9
  610. package/src/plugins/impl/anywidget/widget-binding.ts +160 -82
  611. package/src/plugins/impl/chat/__tests__/chat-prompts.test.tsx +93 -0
  612. package/src/plugins/impl/chat/chat-ui.tsx +14 -11
  613. package/src/plugins/impl/code/any-language-editor.tsx +2 -2
  614. package/src/plugins/impl/data-editor/glide-data-editor.tsx +8 -5
  615. package/src/plugins/impl/data-editor/glide-utils.ts +3 -1
  616. package/src/plugins/impl/data-explorer/ConnectedDataExplorerComponent.tsx +1 -1
  617. package/src/plugins/impl/data-explorer/components/column-summary.tsx +4 -2
  618. package/src/plugins/impl/data-explorer/state/reducer.ts +1 -1
  619. package/src/plugins/impl/data-frames/DataFramePlugin.tsx +1 -2
  620. package/src/plugins/impl/data-frames/__tests__/sidebar.test.tsx +160 -0
  621. package/src/plugins/impl/data-frames/forms/__tests__/__snapshots__/form.test.tsx.snap +66 -66
  622. package/src/plugins/impl/data-frames/panel.tsx +43 -16
  623. package/src/plugins/impl/mpl-interactive/MplInteractivePlugin.tsx +5 -3
  624. package/src/plugins/impl/panel/PanelPlugin.tsx +16 -17
  625. package/src/plugins/impl/panel/__tests__/utils.test.ts +39 -1
  626. package/src/plugins/impl/panel/utils.ts +17 -0
  627. package/src/plugins/impl/plotly/PlotlyPlugin.tsx +2 -5
  628. package/src/plugins/impl/plotly/selection.ts +25 -19
  629. package/src/plugins/impl/vega/VegaPlugin.tsx +2 -3
  630. package/src/plugins/impl/vega/make-selectable.ts +4 -7
  631. package/src/plugins/layout/RoutesPlugin.tsx +1 -1
  632. package/src/stories/__tests__/editor-story.test.tsx +33 -0
  633. package/src/stories/button.stories.tsx +1 -0
  634. package/src/stories/cell.stories.tsx +2 -5
  635. package/src/stories/data-table.stories.tsx +31 -0
  636. package/src/stories/editor.stories.tsx +24 -17
  637. package/src/stories/form-wrapper.stories.tsx +2 -2
  638. package/src/stories/layout/vertical/one-column.stories.tsx +2 -5
  639. package/src/stories/runtime-story.tsx +23 -17
  640. package/src/stories/select.stories.tsx +2 -2
  641. package/src/stories/switchable-multi-select.stories.tsx +1 -1
  642. package/src/utils/__tests__/arrays.test.ts +35 -0
  643. package/src/utils/__tests__/batch-requests.test.ts +3 -3
  644. package/src/utils/__tests__/{createReducer.test.ts → createReducer.test.tsx} +29 -0
  645. package/src/utils/__tests__/dates.test.ts +116 -0
  646. package/src/utils/__tests__/numbers.test.ts +105 -1
  647. package/src/utils/__tests__/objects.test.ts +21 -0
  648. package/src/utils/arrays.ts +11 -2
  649. package/src/utils/blob.ts +1 -1
  650. package/src/utils/createReducer.ts +53 -26
  651. package/src/utils/dates.ts +94 -0
  652. package/src/utils/maps.ts +0 -3
  653. package/src/utils/numbers.ts +79 -18
  654. package/src/utils/objects.ts +4 -9
  655. package/src/utils/once.ts +19 -19
  656. package/src/utils/tracer.ts +9 -5
  657. package/src/utils/zod-utils.ts +1 -3
  658. package/dist/any-language-editor-B9REGlD9.js +0 -76
  659. package/dist/assets/__vite-browser-external-BXYkiFsk.js +0 -1
  660. package/dist/assets/worker-HPY9fbhz.js +0 -114
  661. package/dist/error-entries-CzoYkIQZ.js +0 -56
  662. package/dist/feedback-button-fND8YT59.js +0 -380
  663. package/dist/mermaid-HWGCJPDP-ByCsZnYF.js +0 -2
  664. package/dist/precisionRound-DMIVQrt2.js +0 -97
  665. package/src/components/editor/navigation/__tests__/state.test.ts +0 -81
  666. package/src/components/editor/navigation/state.ts +0 -65
  667. package/src/core/ai/tools/__tests__/run-cells-tool.test.ts +0 -656
  668. package/src/core/ai/tools/run-cells-tool.ts +0 -303
  669. package/src/core/cells/__tests__/apply-transaction.test.ts +0 -991
  670. package/src/core/cells/__tests__/document-changes.test.ts +0 -1140
  671. package/src/core/cells/__tests__/document-roundtrip.test.ts +0 -392
  672. package/src/core/cells/document-changes.ts +0 -944
  673. package/src/core/host/AGENTS.md +0 -6
  674. package/src/core/host/__tests__/protocol.test.ts +0 -214
  675. package/src/core/host/protocol.ts +0 -1943
  676. package/src/core/state/__tests__/jotai.test.ts +0 -25
  677. package/src/core/wasm/worker/message-buffer.ts +0 -33
  678. package/src/core/websocket/__tests__/useWebSocket.test.ts +0 -49
  679. package/src/core/websocket/transports/__tests__/basic.test.ts +0 -275
  680. package/src/core/websocket/transports/__tests__/sse.test.ts +0 -338
  681. package/src/core/websocket/transports/__tests__/transport.test.ts +0 -308
  682. package/src/core/websocket/transports/__tests__/ws.test.ts +0 -125
  683. package/src/core/websocket/transports/basic.ts +0 -102
  684. package/src/core/websocket/transports/sse.ts +0 -308
  685. package/src/core/websocket/transports/transport.ts +0 -61
  686. package/src/core/websocket/transports/ws.ts +0 -98
  687. package/src/core/websocket/useWebSocket.tsx +0 -88
  688. package/src/utils/__tests__/id-tree.test.ts +0 -2145
  689. package/src/utils/id-tree.tsx +0 -1134
  690. /package/src/core/{websocket → session}/connection-utils.ts +0 -0
@@ -16,7 +16,6 @@ import {
16
16
  useCallback,
17
17
  useEffect,
18
18
  useImperativeHandle,
19
- useMemo,
20
19
  useRef,
21
20
  useState,
22
21
  } from "react";
@@ -43,13 +42,15 @@ import { useResizeObserver } from "@/hooks/useResizeObserver";
43
42
  import { cn } from "@/utils/cn";
44
43
  import type { Milliseconds, Seconds } from "@/utils/time";
45
44
  import {
46
- type CellActions,
47
- createUntouchedCellAtom,
48
- useCellActions,
49
45
  useCellData,
50
46
  useCellHandle,
51
47
  useCellRuntime,
52
48
  } from "../../core/cells/cells";
49
+ import { type CellActions, useCellActions } from "../../core/cells/actions";
50
+ import {
51
+ showHiddenCodeAtom,
52
+ useShowsHiddenCode,
53
+ } from "../../core/cells/editor";
53
54
  import { type CellId, SETUP_CELL_ID } from "../../core/cells/ids";
54
55
  import {
55
56
  cellNeedsRun,
@@ -59,7 +60,7 @@ import {
59
60
  shouldHidePublishedCell,
60
61
  } from "../../core/cells/utils";
61
62
  import type { UserConfig } from "../../core/config/config-schema";
62
- import { isAppInteractionDisabled } from "../../core/websocket/connection-utils";
63
+ import { isAppInteractionDisabled } from "../../core/session/connection-utils";
63
64
  import { useCellRenderCount } from "../../hooks/useCellRenderCount";
64
65
  import type { Theme } from "../../theme/useTheme";
65
66
  import { Functions } from "../../utils/functions";
@@ -86,10 +87,6 @@ import { useRunCell } from "./cell/useRunCells";
86
87
  import { cellDomProps } from "./common";
87
88
  import { SqlValidationErrorBanner } from "./errors/sql-validation-errors";
88
89
  import { useCellNavigationProps } from "./navigation/navigation";
89
- import {
90
- useTemporarilyShownCode,
91
- useTemporarilyShownCodeActions,
92
- } from "./navigation/state";
93
90
  import { type OnRefactorWithAI, OutputArea } from "./Output";
94
91
  import { ConsoleOutput } from "./output/console/ConsoleOutput";
95
92
  import { CellDragHandle, SortableCell } from "./SortableCell";
@@ -168,15 +165,12 @@ function useCellHiddenLogic({
168
165
  editorView: React.RefObject<EditorView | null>;
169
166
  editorViewParentRef: React.RefObject<HTMLDivElement | null>;
170
167
  }) {
171
- const temporarilyVisible = useTemporarilyShownCode(cellId);
172
- const temporarilyShownCodeActions = useTemporarilyShownCodeActions();
173
- const isUntouched = useAtomValue(
174
- useMemo(() => createUntouchedCellAtom(cellId), [cellId]),
175
- );
168
+ const showsHiddenCode = useShowsHiddenCode(cellId);
169
+ const showHiddenCodeNow = useSetAtom(showHiddenCodeAtom);
176
170
 
177
- // The cell code is shown if the cell is not configured to be hidden or if the code is temporarily visible (i.e. when focused).
178
- const isCellCodeShown =
179
- !cellConfig.hide_code || temporarilyVisible || isUntouched;
171
+ // The code is shown unless the cell hides it, and then still while it is
172
+ // being edited or was just created.
173
+ const isCellCodeShown = !cellConfig.hide_code || showsHiddenCode;
180
174
  const isMarkdown = languageAdapter === "markdown";
181
175
  const isMarkdownCodeHidden = isMarkdown && !isCellCodeShown;
182
176
 
@@ -189,7 +183,7 @@ function useCellHiddenLogic({
189
183
 
190
184
  // Default to true
191
185
  const focus = opts?.focus ?? true;
192
- temporarilyShownCodeActions.add(cellId);
186
+ showHiddenCodeNow({ cellId });
193
187
 
194
188
  if (focus) {
195
189
  editorView.current?.focus();
@@ -216,14 +210,10 @@ function useCellHiddenLogic({
216
210
  export type CellComponentActions = Pick<
217
211
  CellActions,
218
212
  | "updateCellCode"
219
- | "createNewCell"
220
213
  | "focusCell"
221
214
  | "moveCell"
222
215
  | "collapseCell"
223
216
  | "expandCell"
224
- | "moveToNextCell"
225
- | "updateCellConfig"
226
- | "clearSerializedEditorState"
227
217
  | "setStdinResponse"
228
218
  | "clearCellConsoleOutput"
229
219
  | "sendToBottom"
@@ -525,13 +515,22 @@ const EditableCellComponent = ({
525
515
  isMarkdownCodeHidden &&
526
516
  isEmptyMarkdownContent &&
527
517
  !needsRun && (
518
+ // Preserve pointer double-click editing; keyboard and assistive clicks activate directly.
519
+ // react-doctor-disable-next-line react-doctor/prefer-tag-over-role
528
520
  <div
521
+ // eslint-disable-next-line jsx-a11y/prefer-tag-over-role
529
522
  role="button"
530
- aria-label="Double-click to edit markdown"
523
+ aria-label="Edit markdown"
531
524
  className="relative cursor-pointer px-3 py-2"
532
525
  onDoubleClick={showHiddenCodeIfMarkdown}
526
+ onClick={(e) => {
527
+ if (e.detail === 0) {
528
+ showHiddenCodeIfMarkdown();
529
+ }
530
+ }}
533
531
  onKeyDown={(e) => {
534
- if (e.key === "Enter") {
532
+ if (e.key === "Enter" || e.key === " ") {
533
+ e.preventDefault();
535
534
  showHiddenCodeIfMarkdown();
536
535
  }
537
536
  }}
@@ -699,7 +698,6 @@ const EditableCellComponent = ({
699
698
  code={cellData.code}
700
699
  config={cellData.config}
701
700
  status={cellRuntime.status}
702
- serializedEditorState={cellData.serializedEditorState}
703
701
  runCell={runCell}
704
702
  setEditorView={setEditorView}
705
703
  userConfig={userConfig}
@@ -919,15 +917,16 @@ const CellLeftSideActions = memo(
919
917
  actions: CellComponentActions;
920
918
  }) => {
921
919
  const connection = useAtomValue(connectionAtom);
922
- const { className, actions, cellId } = props;
920
+ const { className, cellId } = props;
921
+ const { createCell } = useCellActions();
923
922
 
924
923
  const createBelow = useEvent(
925
- (opts: { code?: string; hideCode?: boolean } = {}) =>
926
- actions.createNewCell({ cellId, before: false, ...opts }),
924
+ ({ code, hideCode }: { code?: string; hideCode?: boolean } = {}) =>
925
+ createCell({ after: cellId, code, config: { hide_code: hideCode } }),
927
926
  );
928
927
  const createAbove = useEvent(
929
- (opts: { code?: string; hideCode?: boolean } = {}) =>
930
- actions.createNewCell({ cellId, before: true, ...opts }),
928
+ ({ code, hideCode }: { code?: string; hideCode?: boolean } = {}) =>
929
+ createCell({ before: cellId, code, config: { hide_code: hideCode } }),
931
930
  );
932
931
 
933
932
  const oneClickShortcut = "mod";
@@ -1227,7 +1226,6 @@ const SetupCellComponent = ({
1227
1226
  code={cellData.code}
1228
1227
  config={cellData.config}
1229
1228
  status={cellRuntime.status}
1230
- serializedEditorState={cellData.serializedEditorState}
1231
1229
  runCell={runCell}
1232
1230
  setEditorView={setEditorView}
1233
1231
  userConfig={userConfig}
@@ -21,8 +21,10 @@ import { Button } from "@/components/ui/button";
21
21
  import { Kbd } from "@/components/ui/kbd";
22
22
  import { ExternalLink } from "@/components/ui/links";
23
23
  import { Tooltip } from "@/components/ui/tooltip";
24
+ import { buildErrorReport } from "@/core/cells/error-report";
24
25
  import type { CellId } from "@/core/cells/ids";
25
26
  import { resolvedMarimoConfigAtom } from "@/core/config/config";
27
+ import { viewStateAtom } from "@/core/mode";
26
28
  import { renderHTML } from "@/plugins/core/RenderHTML";
27
29
  import { splitMangledLocals } from "@/utils/local-variables";
28
30
  import type { MarimoError } from "../../../core/kernel/messages";
@@ -32,6 +34,7 @@ import { openPackageManager } from "../chrome/panels/packages-utils";
32
34
  import { useChromeActions } from "../chrome/state";
33
35
  import { AutoFixButton } from "../errors/auto-fix";
34
36
  import { MangledSegments } from "../errors/mangled-local-chip";
37
+ import { SendErrorReportButton } from "../errors/send-error-report-button";
35
38
  import { CellLinkError } from "../links/cell-link";
36
39
  import { processTextForUrls } from "./console/text-rendering";
37
40
 
@@ -93,6 +96,7 @@ const Tip = (props: {
93
96
  interface Props {
94
97
  cellId: CellId | undefined;
95
98
  errors: MarimoError[];
99
+ code?: string;
96
100
  className?: string;
97
101
  }
98
102
 
@@ -102,6 +106,7 @@ interface Props {
102
106
  export const MarimoErrorOutput = ({
103
107
  errors,
104
108
  cellId,
109
+ code,
105
110
  className,
106
111
  }: Props): JSX.Element => {
107
112
  const chromeActions = useChromeActions();
@@ -111,6 +116,9 @@ export const MarimoErrorOutput = ({
111
116
  // only helpful when outputs are displayed above the editor.
112
117
  const showConsoleHint =
113
118
  useAtomValue(resolvedMarimoConfigAtom).display.cell_output === "above";
119
+ // The editor shows tracebacks in the console area, so the inline copy is
120
+ // for views without a console: published apps and present mode.
121
+ const showInlineTraceback = useAtomValue(viewStateAtom).mode !== "edit";
114
122
 
115
123
  let titleContents: string | null =
116
124
  "This cell wasn't run because it has errors";
@@ -199,7 +207,8 @@ export const MarimoErrorOutput = ({
199
207
  e.type === "ancestor-stopped",
200
208
  );
201
209
  const syntaxErrors = errors.filter(
202
- (e): e is Extract<MarimoError, { type: "syntax" }> => e.type === "syntax",
210
+ (e): e is Extract<MarimoError, { type: "syntax" | "lazy-import" }> =>
211
+ e.type === "syntax" || e.type === "lazy-import",
203
212
  );
204
213
  const unknownErrors = errors.filter(
205
214
  (e): e is Extract<MarimoError, { type: "unknown" }> => e.type === "unknown",
@@ -208,7 +217,6 @@ export const MarimoErrorOutput = ({
208
217
  (e): e is Extract<MarimoError, { type: "sql-error" }> =>
209
218
  e.type === "sql-error",
210
219
  );
211
-
212
220
  const openScratchpad = () => {
213
221
  chromeActions.openApplication("scratchpad");
214
222
  };
@@ -558,7 +566,9 @@ export const MarimoErrorOutput = ({
558
566
  <p className="text-muted-foreground">
559
567
  {processTextForUrls(error.msg, `exception-${idx}`)}
560
568
  </p>
561
- {"traceback" in error && error.traceback ? (
569
+ {showInlineTraceback &&
570
+ "traceback" in error &&
571
+ error.traceback ? (
562
572
  <CollapsibleTraceback traceback={error.traceback} />
563
573
  ) : (
564
574
  showConsoleHint && (
@@ -572,9 +582,11 @@ export const MarimoErrorOutput = ({
572
582
  <div>
573
583
  {processTextForUrls(error.msg, `exception-${idx}`)}
574
584
  <CellLinkError cellId={error.raising_cell} />
575
- {"traceback" in error && error.traceback && (
576
- <CollapsibleTraceback traceback={error.traceback} />
577
- )}
585
+ {showInlineTraceback &&
586
+ "traceback" in error &&
587
+ error.traceback && (
588
+ <CollapsibleTraceback traceback={error.traceback} />
589
+ )}
578
590
  </div>
579
591
  )}
580
592
  </li>
@@ -728,6 +740,11 @@ export const MarimoErrorOutput = ({
728
740
  >
729
741
  {title}
730
742
  <div className="flex flex-col gap-4">{renderMessages()}</div>
743
+ {cellId && errors.length > 0 && (
744
+ <SendErrorReportButton
745
+ getContent={() => buildErrorReport(cellId, { code, errors })}
746
+ />
747
+ )}
731
748
  </Alert>
732
749
  );
733
750
  };
@@ -22,6 +22,7 @@ import {
22
22
  import { Kbd } from "@/components/ui/kbd";
23
23
  import { Tooltip } from "@/components/ui/tooltip";
24
24
  import { getCellEditorView } from "@/core/cells/cells";
25
+ import { buildErrorReport } from "@/core/cells/error-report";
25
26
  import type { CellId } from "@/core/cells/ids";
26
27
  import { SCRATCH_CELL_ID } from "@/core/cells/ids";
27
28
  import { toggleBreakpoint } from "@/core/codemirror/cells/debugger-state";
@@ -34,6 +35,7 @@ import { isWasm } from "@/core/wasm/utils";
34
35
  import { renderHTML } from "@/plugins/core/RenderHTML";
35
36
  import { sanitizeHtml } from "@/plugins/core/sanitize-html";
36
37
  import { copyToClipboard } from "@/utils/copy";
38
+ import { parseHtmlContent } from "@/utils/dom";
37
39
  import {
38
40
  containsMangledLocal,
39
41
  splitMangledLocals,
@@ -46,33 +48,45 @@ import {
46
48
  import { useOpenAiAssistant } from "../chrome/wrapper/useOpenAiAssistant";
47
49
  import { AIFixButton, buildFixInChatPrompt } from "../errors/auto-fix";
48
50
  import { MangledSegments } from "../errors/mangled-local-chip";
51
+ import { SendErrorReportButton } from "../errors/send-error-report-button";
49
52
  import { CellLinkTraceback } from "../links/cell-link";
50
53
  import type { OnRefactorWithAI } from "../Output";
51
54
 
52
55
  interface Props {
53
56
  cellId: CellId | undefined;
54
57
  traceback: string;
58
+ tracebackFormat?: "html" | "text";
59
+ code?: string;
55
60
  onRefactorWithAI?: OnRefactorWithAI;
56
61
  }
57
62
 
58
- /**
59
- * List of errors due to violations of Marimo semantics.
60
- */
63
+ /** Render a traceback and actions for its captured execution. */
61
64
  export const MarimoTracebackOutput = ({
62
65
  onRefactorWithAI,
63
66
  traceback,
67
+ tracebackFormat = "html",
64
68
  cellId,
69
+ code,
65
70
  }: Props): JSX.Element => {
66
- const htmlTraceback = renderHTML({
67
- html: traceback,
68
- additionalReplacements: [
69
- replaceTracebackFilenames,
70
- replaceTracebackPrefix,
71
- replaceMangledLocal,
72
- ],
73
- });
71
+ const htmlTraceback =
72
+ tracebackFormat === "text" ? (
73
+ <pre>{traceback}</pre>
74
+ ) : (
75
+ renderHTML({
76
+ html: traceback,
77
+ additionalReplacements: [
78
+ replaceTracebackFilenames,
79
+ replaceTracebackPrefix,
80
+ replaceMangledLocal,
81
+ ],
82
+ })
83
+ );
74
84
 
75
- const lastTracebackLine = lastLine(traceback);
85
+ const textTraceback =
86
+ tracebackFormat === "html"
87
+ ? parseHtmlContent(sanitizeHtml(traceback))
88
+ : traceback;
89
+ const lastTracebackLine = lastLine(textTraceback);
76
90
  const aiFeaturesEnabled = useAtomValue(aiFeaturesEnabledAtom);
77
91
  const openAiAssistant = useOpenAiAssistant();
78
92
 
@@ -131,6 +145,13 @@ export const MarimoTracebackOutput = ({
131
145
  </div>
132
146
  )}
133
147
  <div className="flex gap-2">
148
+ {cellId && lastTracebackLine && (
149
+ <SendErrorReportButton
150
+ getContent={() =>
151
+ buildErrorReport(cellId, { code, traceback, tracebackFormat })
152
+ }
153
+ />
154
+ )}
134
155
  {showAIFix && (
135
156
  <AIFixButton
136
157
  tooltip="Fix with AI"
@@ -186,11 +207,7 @@ export const MarimoTracebackOutput = ({
186
207
  </DropdownMenuItem>
187
208
  <DropdownMenuItem
188
209
  onClick={() => {
189
- // Strip HTML from the traceback (sanitize first to prevent XSS)
190
- const div = document.createElement("div");
191
- div.innerHTML = sanitizeHtml(traceback);
192
- const textContent = div.textContent || "";
193
- copyToClipboard(textContent);
210
+ copyToClipboard(textTraceback);
194
211
  }}
195
212
  >
196
213
  <CopyIcon className="h-4 w-4 mr-2" />
@@ -205,9 +222,7 @@ export const MarimoTracebackOutput = ({
205
222
  };
206
223
 
207
224
  function lastLine(text: string): string {
208
- const el = document.createElement("div");
209
- el.innerHTML = sanitizeHtml(text);
210
- const lines = el.textContent?.split("\n").filter(Boolean);
225
+ const lines = text.split("\n").filter(Boolean);
211
226
  return lines?.at(-1) || "";
212
227
  }
213
228
 
@@ -233,21 +248,22 @@ export const replaceTracebackFilenames = (domNode: DOMNode) => {
233
248
  <Tooltip content={tooltipContent}>
234
249
  <button
235
250
  type="button"
236
- className="ml-1 p-1 rounded-sm hover:bg-muted transition-all inline"
251
+ aria-label={
252
+ debuggerEnabled ? "Toggle breakpoint" : "Insert breakpoint"
253
+ }
254
+ className="ml-1 p-1 rounded-sm hover:bg-muted transition-colors inline"
255
+ onClick={() => {
256
+ if (debuggerEnabled && !isStaticNotebook()) {
257
+ toggleBreakpoint(info.cellId, info.lineNumber);
258
+ return;
259
+ }
260
+ const view = getCellEditorView(info.cellId);
261
+ if (view) {
262
+ insertDebuggerAtLine(view, info.lineNumber);
263
+ }
264
+ }}
237
265
  >
238
- <BugPlayIcon
239
- onClick={() => {
240
- if (debuggerEnabled && !isStaticNotebook()) {
241
- toggleBreakpoint(info.cellId, info.lineNumber);
242
- return;
243
- }
244
- const view = getCellEditorView(info.cellId);
245
- if (view) {
246
- insertDebuggerAtLine(view, info.lineNumber);
247
- }
248
- }}
249
- className="h-3 w-3"
250
- />
266
+ <BugPlayIcon className="h-3 w-3" />
251
267
  </button>
252
268
  </Tooltip>
253
269
  )}
@@ -257,9 +273,10 @@ export const replaceTracebackFilenames = (domNode: DOMNode) => {
257
273
  }
258
274
  if (info?.kind === "file") {
259
275
  return (
260
- <div
276
+ <button
277
+ type="button"
261
278
  className="inline-block cursor-pointer text-destructive hover:underline"
262
- onClick={(_) => {
279
+ onClick={() => {
263
280
  getRequestClient().openFile({
264
281
  path: info.filePath,
265
282
  lineNumber: info.lineNumber,
@@ -267,7 +284,7 @@ export const replaceTracebackFilenames = (domNode: DOMNode) => {
267
284
  }}
268
285
  >
269
286
  <span className="nb">"{info.filePath}"</span>
270
- </div>
287
+ </button>
271
288
  );
272
289
  }
273
290
  };
@@ -24,6 +24,14 @@
24
24
  max-width: 100%;
25
25
  }
26
26
 
27
+ .output audio,
28
+ .output-area audio,
29
+ .media audio {
30
+ width: 100%;
31
+ max-width: 100%;
32
+ transform: translateZ(0);
33
+ }
34
+
27
35
  .output {
28
36
  position: relative;
29
37
 
@@ -7,6 +7,24 @@ import {
7
7
  TerminalBuffer,
8
8
  } from "../ansi-reduce";
9
9
 
10
+ test("preserves source evidence through stateful output and serialization", () => {
11
+ const output = StatefulOutputMessage.create({
12
+ channel: "stderr",
13
+ mimetype: "application/vnd.marimo+traceback",
14
+ timestamp: 1,
15
+ data: "<pre>ValueError:",
16
+ code: "raise ValueError('failed code')",
17
+ }).appendData(" failed code</pre>");
18
+ expect(output.code).toBe("raise ValueError('failed code')");
19
+ expect(output.toJSON()).toEqual({
20
+ channel: "stderr",
21
+ mimetype: "application/vnd.marimo+traceback",
22
+ timestamp: 1,
23
+ data: "<pre>ValueError: failed code</pre>",
24
+ code: "raise ValueError('failed code')",
25
+ });
26
+ });
27
+
10
28
  describe("TerminalBuffer", () => {
11
29
  test("writeChar writes single character", () => {
12
30
  const buffer = new TerminalBuffer();
@@ -1,11 +1,12 @@
1
1
  /* Copyright 2026 Marimo. All rights reserved. */
2
2
 
3
- import { render } from "@testing-library/react";
3
+ import { fireEvent, render, screen } from "@testing-library/react";
4
4
  import { Provider } from "jotai";
5
5
  import { beforeAll, beforeEach, describe, expect, test, vi } from "vitest";
6
6
  import { MockRequestClient } from "@/__mocks__/requests";
7
7
  import { Tracebacks } from "@/__mocks__/tracebacks";
8
8
  import { cellId } from "@/__tests__/branded";
9
+ import { toggleBreakpoint } from "@/core/codemirror/cells/debugger-state";
9
10
  import { TooltipProvider } from "@/components/ui/tooltip";
10
11
  import { initialModeAtom } from "@/core/mode";
11
12
  import { requestClientAtom } from "@/core/network/requests";
@@ -19,7 +20,32 @@ import {
19
20
 
20
21
  const cid = cellId("1");
21
22
 
23
+ vi.mock("@/core/config/feature-flag", async (importOriginal) => ({
24
+ ...(await importOriginal<typeof import("@/core/config/feature-flag")>()),
25
+ getFeatureFlag: (flag: string) => flag === "debugger",
26
+ }));
27
+ vi.mock("@/core/codemirror/cells/debugger-state", async (importOriginal) => ({
28
+ ...(await importOriginal<
29
+ typeof import("@/core/codemirror/cells/debugger-state")
30
+ >()),
31
+ toggleBreakpoint: vi.fn(),
32
+ }));
33
+
22
34
  describe("traceback component", () => {
35
+ test("activates the breakpoint from the named button itself", () => {
36
+ render(
37
+ <Provider store={store}>
38
+ <TooltipProvider>
39
+ <MarimoTracebackOutput traceback={Tracebacks.raw} cellId={cid} />
40
+ </TooltipProvider>
41
+ </Provider>,
42
+ );
43
+ const buttons = screen.getAllByRole("button", {
44
+ name: "Toggle breakpoint",
45
+ });
46
+ fireEvent.click(buttons[0]);
47
+ expect(toggleBreakpoint).toHaveBeenCalledOnce();
48
+ });
23
49
  beforeEach(() => {
24
50
  vi.resetAllMocks();
25
51
  store.set(initialModeAtom, "edit");
@@ -358,6 +358,7 @@ export class AnsiReducer {
358
358
 
359
359
  export type StringOutputMessage = Omit<OutputMessage, "data"> & {
360
360
  data: string;
361
+ id?: number;
361
362
  };
362
363
 
363
364
  /**
@@ -368,6 +369,8 @@ export class StatefulOutputMessage implements OutputMessage {
368
369
  public readonly mimetype: OutputMessage["mimetype"];
369
370
  public readonly channel: OutputMessage["channel"];
370
371
  public readonly timestamp: OutputMessage["timestamp"];
372
+ public readonly code: OutputMessage["code"];
373
+ public readonly id: StringOutputMessage["id"];
371
374
  private ansiReducer = new AnsiReducer();
372
375
  private _data: string;
373
376
 
@@ -378,35 +381,50 @@ export class StatefulOutputMessage implements OutputMessage {
378
381
  public static create(message: StringOutputMessage): StatefulOutputMessage {
379
382
  const ansiReducer = new AnsiReducer();
380
383
  ansiReducer.append(message.data);
381
- return new StatefulOutputMessage(
382
- message.mimetype,
383
- message.channel,
384
- message.timestamp,
384
+ return new StatefulOutputMessage({
385
+ mimetype: message.mimetype,
386
+ channel: message.channel,
387
+ timestamp: message.timestamp,
385
388
  ansiReducer,
386
- );
389
+ code: message.code,
390
+ id: message.id,
391
+ });
387
392
  }
388
393
 
389
- private constructor(
390
- mimetype: OutputMessage["mimetype"],
391
- channel: OutputMessage["channel"],
392
- timestamp: OutputMessage["timestamp"],
393
- ansiReducer: AnsiReducer,
394
- ) {
394
+ private constructor({
395
+ mimetype,
396
+ channel,
397
+ timestamp,
398
+ ansiReducer,
399
+ code,
400
+ id,
401
+ }: {
402
+ mimetype: OutputMessage["mimetype"];
403
+ channel: OutputMessage["channel"];
404
+ timestamp: OutputMessage["timestamp"];
405
+ ansiReducer: AnsiReducer;
406
+ code: OutputMessage["code"];
407
+ id: StringOutputMessage["id"];
408
+ }) {
395
409
  this.mimetype = mimetype;
396
410
  this.channel = channel;
397
411
  this.timestamp = timestamp;
412
+ this.code = code;
413
+ this.id = id;
398
414
  this.ansiReducer = ansiReducer;
399
415
  this._data = this.ansiReducer.render();
400
416
  }
401
417
 
402
418
  public appendData(chunk: string): StatefulOutputMessage {
403
419
  this.ansiReducer.append(chunk);
404
- return new StatefulOutputMessage(
405
- this.mimetype,
406
- this.channel,
407
- this.timestamp,
408
- this.ansiReducer,
409
- );
420
+ return new StatefulOutputMessage({
421
+ mimetype: this.mimetype,
422
+ channel: this.channel,
423
+ timestamp: this.timestamp,
424
+ ansiReducer: this.ansiReducer,
425
+ code: this.code,
426
+ id: this.id,
427
+ });
410
428
  }
411
429
 
412
430
  public toJSON(): StringOutputMessage {
@@ -415,6 +433,7 @@ export class StatefulOutputMessage implements OutputMessage {
415
433
  channel: this.channel,
416
434
  timestamp: this.timestamp,
417
435
  data: this.data,
436
+ ...(this.code === undefined ? {} : { code: this.code }),
418
437
  };
419
438
  }
420
439
  }