@marimo-team/islands 0.25.3-dev173 → 0.25.3-dev175

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 (134) hide show
  1. package/dist/{ErrorBoundary-wT3f3iJ1.js → ErrorBoundary-DNvcAIsP.js} +1 -1
  2. package/dist/{any-language-editor-B92WMzoC.js → any-language-editor-BVFHDDQ3.js} +2 -2
  3. package/dist/{chat-ui-CuORr6fL.js → chat-ui-X-cWrL9u.js} +1222 -1222
  4. package/dist/{code-visibility-ZReaeMaF.js → code-visibility-CH1lmM1h.js} +2 -2
  5. package/dist/{common-DCevHg1m.js → common-DIrS1UR9.js} +1074 -1078
  6. package/dist/{data-grid-overlay-editor-CTC-bJus.js → data-grid-overlay-editor-DFLZvFK0.js} +1 -1
  7. package/dist/{dist-F8Ep36rk.js → dist-B1M0bGO3.js} +1 -1
  8. package/dist/{dist-D6d86eNJ.js → dist-BA13RJj5.js} +1 -1
  9. package/dist/{dist-Bvs24R_E.js → dist-BJtmSgcE.js} +48 -48
  10. package/dist/{dist-CN_BeG2I.js → dist-Ba2VIn1K.js} +53 -53
  11. package/dist/{dist-PXYI_yuP.js → dist-Bj4bmwUm.js} +12 -12
  12. package/dist/{dist-DoE4XJBC.js → dist-BmS-ZGjl.js} +8626 -8626
  13. package/dist/{dist-BorMD-uX.js → dist-Bzogh7CW.js} +87 -87
  14. package/dist/{dist-CN8zI-XC.js → dist-CThPVKaP.js} +1385 -1382
  15. package/dist/{dist-DiDibOYr.js → dist-CTi5FTiV.js} +87 -87
  16. package/dist/{dist-diIx5qJW.js → dist-Ck_C32ye.js} +2 -2
  17. package/dist/{dist-BLfKmR-l.js → dist-D1fnFp1J.js} +1 -1
  18. package/dist/{dist-OR1OnN-y.js → dist-D3x9__Fu.js} +46 -46
  19. package/dist/{dist-BMQf5zIS.js → dist-D7mrh5sO.js} +36 -36
  20. package/dist/{dist-CSJ0MDRw.js → dist-D9Q3xjiP.js} +1 -1
  21. package/dist/{dist-BuaRHxOc.js → dist-DP60Ubh8.js} +2 -2
  22. package/dist/{dist-CSbh1PNP.js → dist-DTv9KkpW.js} +12 -12
  23. package/dist/{dist-D-wwqlzJ.js → dist-DVVwOfrD.js} +109 -109
  24. package/dist/{dist-C8fAKSH1.js → dist-DYXM73-k.js} +36 -36
  25. package/dist/{dist-DBtSl3sf.js → dist-DjeybPOb.js} +1 -1
  26. package/dist/{dist-CrSP_H1M.js → dist-DtGn9N4h.js} +197 -197
  27. package/dist/{dist-CLdpGQVr.js → dist-KN80qWCP.js} +2 -2
  28. package/dist/{dist-Cg7gzw-a.js → dist-O0qFpEJh.js} +56 -56
  29. package/dist/{dist-CkTTIdBe.js → dist-OUle2RT7.js} +207 -207
  30. package/dist/{dist-BK4Oj99o.js → dist-T5rh6JvL.js} +1 -1
  31. package/dist/{error-entries-CmWMEsY_.js → error-entries-mpoD5t79.js} +4939 -4983
  32. package/dist/{esm-D2gTsXEV.js → esm-Bbw_Njjx.js} +575 -575
  33. package/dist/{esm-AMFssoNp.js → esm-mDQNEFe_.js} +354 -354
  34. package/dist/{feedback-button-DwXkmewo.js → feedback-button-DL0DJ-LB.js} +21 -21
  35. package/dist/{glide-data-editor-BlmcP-lw.js → glide-data-editor-n4wnx19S.js} +3 -3
  36. package/dist/{globals-BdRitZ4p.js → globals-NCsYyjpB.js} +1 -1
  37. package/dist/{html-to-image-bpiQh7ND.js → html-to-image-BoZthB4P.js} +454 -445
  38. package/dist/main.js +3587 -3587
  39. package/dist/{number-overlay-editor-DQG-hFHT.js → number-overlay-editor-rlvo4mo3.js} +1 -1
  40. package/dist/{process-output-BzloOI7F.js → process-output-DLS4Mqg_.js} +2 -2
  41. package/dist/{reveal-component-D3r3vSTK.js → reveal-component-BJfmRUzb.js} +3 -3
  42. package/package.json +1 -1
  43. package/src/__mocks__/document.tsx +54 -0
  44. package/src/__mocks__/notebook.ts +2 -1
  45. package/src/__mocks__/requests.ts +0 -2
  46. package/src/components/chat/chat-panel.tsx +3 -3
  47. package/src/components/datasources/__tests__/column-preview.test.tsx +6 -8
  48. package/src/components/datasources/column-preview.tsx +4 -8
  49. package/src/components/datasources/datasources.tsx +4 -3
  50. package/src/components/dependency-graph/minimap-content.tsx +2 -6
  51. package/src/components/dependency-graph/panels.tsx +2 -1
  52. package/src/components/editor/__tests__/Output.test.tsx +50 -32
  53. package/src/components/editor/__tests__/data-attributes.test.tsx +22 -11
  54. package/src/components/editor/__tests__/output-persistence.test.tsx +6 -1
  55. package/src/components/editor/actions/__tests__/name-cell-input.test.tsx +69 -0
  56. package/src/components/editor/actions/name-cell-input.tsx +4 -3
  57. package/src/components/editor/actions/useCellActionButton.tsx +20 -26
  58. package/src/components/editor/actions/useNotebookActions.tsx +13 -18
  59. package/src/components/editor/actions/useSetCodeVisibility.ts +10 -11
  60. package/src/components/editor/actions/useSetOutputsExpanded.ts +13 -18
  61. package/src/components/editor/cell/CreateCellButton.tsx +5 -9
  62. package/src/components/editor/cell/__tests__/StagedAICell.test.tsx +3 -1
  63. package/src/components/editor/cell/code/cell-editor.tsx +13 -20
  64. package/src/components/editor/cell/useAddCell.ts +4 -8
  65. package/src/components/editor/cell/useDeleteCell.tsx +10 -36
  66. package/src/components/editor/cell/useRunCells.ts +2 -5
  67. package/src/components/editor/cell/useSplitCell.tsx +2 -1
  68. package/src/components/editor/chrome/panels/logs-panel.tsx +2 -1
  69. package/src/components/editor/chrome/panels/snippets-panel.tsx +5 -11
  70. package/src/components/editor/chrome/wrapper/__tests__/pending-ai-cells.test.tsx +3 -1
  71. package/src/components/editor/columns/sortable-column.tsx +1 -1
  72. package/src/components/editor/connections/components.tsx +4 -9
  73. package/src/components/editor/controls/Controls.tsx +1 -1
  74. package/src/components/editor/controls/__tests__/notebook-menu-dropdown.test.tsx +9 -3
  75. package/src/components/editor/documentation.css +34 -11
  76. package/src/components/editor/errors/auto-fix.tsx +4 -8
  77. package/src/components/editor/file-tree/file-explorer.tsx +3 -7
  78. package/src/components/editor/links/__tests__/cell-link.test.tsx +3 -1
  79. package/src/components/editor/links/cell-link.tsx +2 -1
  80. package/src/components/editor/navigation/__tests__/clipboard.test.ts +60 -38
  81. package/src/components/editor/navigation/__tests__/navigation.test.ts +73 -64
  82. package/src/components/editor/navigation/clipboard.ts +12 -11
  83. package/src/components/editor/navigation/multi-cell-action-toolbar.tsx +11 -20
  84. package/src/components/editor/navigation/navigation.ts +20 -28
  85. package/src/components/editor/notebook-cell.tsx +7 -10
  86. package/src/components/editor/output/console/__tests__/ConsoleOutput.test.tsx +125 -69
  87. package/src/components/editor/renderers/cell-array.tsx +10 -17
  88. package/src/components/markdown/markdown-renderer.tsx +4 -8
  89. package/src/components/pages/edit-page.tsx +32 -17
  90. package/src/components/scratchpad/scratchpad.test.tsx +3 -1
  91. package/src/components/scratchpad/scratchpad.tsx +4 -7
  92. package/src/components/slides/__tests__/minimap-actions.test.tsx +9 -25
  93. package/src/components/slides/minimap.tsx +7 -3
  94. package/src/components/slides/slide-cell-view.tsx +3 -3
  95. package/src/components/sort/SortableCellsProvider.tsx +2 -1
  96. package/src/core/ai/__tests__/staged-cells.test.ts +18 -20
  97. package/src/core/ai/staged-cells.ts +8 -16
  98. package/src/core/ai/tools/__tests__/edit-notebook-tool.test.ts +2 -2
  99. package/src/core/ai/tools/__tests__/run-cells-tool.test.ts +2 -2
  100. package/src/core/ai/tools/base.ts +2 -2
  101. package/src/core/ai/tools/edit-notebook-tool.ts +13 -21
  102. package/src/core/cells/__tests__/actions.test.ts +474 -34
  103. package/src/core/cells/__tests__/add-missing-import.test.ts +7 -8
  104. package/src/core/cells/__tests__/cells.test.ts +171 -813
  105. package/src/core/cells/__tests__/document.test.ts +5 -35
  106. package/src/core/cells/__tests__/notebook-outline.test.ts +7 -1
  107. package/src/core/cells/__tests__/outputs.test.tsx +71 -53
  108. package/src/core/cells/actions.ts +391 -3
  109. package/src/core/cells/add-missing-import.ts +46 -42
  110. package/src/core/cells/cells.ts +38 -413
  111. package/src/core/cells/document.ts +7 -4
  112. package/src/core/cells/outputs.ts +12 -28
  113. package/src/core/codemirror/cells/extensions.ts +6 -6
  114. package/src/core/codemirror/cells/state.ts +1 -1
  115. package/src/core/codemirror/keymaps/vim.ts +2 -2
  116. package/src/core/edit-app.tsx +19 -27
  117. package/src/core/islands/bridge.ts +0 -2
  118. package/src/core/kernel/handlers.ts +3 -3
  119. package/src/core/network/__tests__/requests-lazy.test.ts +1 -3
  120. package/src/core/network/requests-lazy.ts +0 -2
  121. package/src/core/network/requests-network.ts +0 -16
  122. package/src/core/network/requests-static.ts +0 -2
  123. package/src/core/network/requests-toasting.tsx +0 -2
  124. package/src/core/network/types.ts +0 -7
  125. package/src/core/notebook/document/__tests__/codemirror.test.ts +5 -0
  126. package/src/core/notebook/document/__tests__/draft.test.ts +41 -0
  127. package/src/core/notebook/document/__tests__/state.test.ts +21 -0
  128. package/src/core/notebook/document/draft.ts +35 -5
  129. package/src/core/notebook/document/index.ts +1 -0
  130. package/src/core/notebook/document/state.ts +6 -2
  131. package/src/core/session/useNotebookSession.tsx +6 -2
  132. package/src/core/wasm/bridge.ts +0 -16
  133. package/src/css/globals.css +56 -22
  134. package/src/stories/runtime-story.tsx +22 -15
@@ -15,8 +15,10 @@ vi.mock("@/components/editor/cell/useDeleteCell", () => ({
15
15
 
16
16
  vi.mock("@/core/cells/cells", () => ({
17
17
  getCellEditorView: vi.fn(),
18
+ }));
19
+ vi.mock("@/core/cells/actions", () => ({
18
20
  useCellActions: () => ({
19
- createNewCell: vi.fn(),
21
+ createCell: vi.fn(),
20
22
  updateCellCode: vi.fn(),
21
23
  }),
22
24
  }));
@@ -19,7 +19,7 @@ import {
19
19
  DropdownMenuTrigger,
20
20
  } from "@/components/ui/dropdown-menu";
21
21
  import { Tooltip } from "@/components/ui/tooltip";
22
- import { useCellActions } from "@/core/cells/cells";
22
+ import { useCellActions } from "@/core/cells/actions";
23
23
  import { cn } from "@/utils/cn";
24
24
  import type { CellColumnId } from "@/utils/id-tree";
25
25
  import { mergeRefs } from "../../../utils/mergeRefs";
@@ -18,7 +18,7 @@ import {
18
18
  SelectValue,
19
19
  } from "@/components/ui/select";
20
20
  import { maybeAddMarimoImport } from "@/core/cells/add-missing-import";
21
- import { useCellActions } from "@/core/cells/cells";
21
+ import { useCellActions } from "@/core/cells/actions";
22
22
  import { useLastFocusedCellId } from "@/core/cells/focus";
23
23
  import { autoInstantiateAtom } from "@/core/config/config";
24
24
  import type { DetectedDataSource } from "@/core/datasets/data-source-discovery";
@@ -112,7 +112,7 @@ export const ConnectionFormFooter = <L extends string>({
112
112
  * Returns a callback that inserts code into a new cell after the last focused cell.
113
113
  */
114
114
  export function useInsertCode() {
115
- const { createNewCell } = useCellActions();
115
+ const { createCell } = useCellActions();
116
116
  const lastFocusedCellId = useLastFocusedCellId();
117
117
  const autoInstantiate = useAtomValue(autoInstantiateAtom);
118
118
 
@@ -121,17 +121,12 @@ export function useInsertCode() {
121
121
  if (/\bmo\./.test(code)) {
122
122
  maybeAddMarimoImport({
123
123
  autoInstantiate,
124
- createNewCell,
124
+ createCell,
125
125
  fromCellId: lastFocusedCellId,
126
126
  });
127
127
  }
128
128
 
129
- createNewCell({
130
- code,
131
- before: false,
132
- cellId: lastFocusedCellId ?? "__end__",
133
- skipIfCodeExists: true,
134
- });
129
+ createCell({ after: lastFocusedCellId, code, skipIfCodeExists: true });
135
130
  };
136
131
  }
137
132
 
@@ -28,8 +28,8 @@ import {
28
28
  canUndoDeletesAtom,
29
29
  needsRunAtom,
30
30
  undoLabelAtom,
31
- useCellActions,
32
31
  } from "../../../core/cells/cells";
32
+ import { useCellActions } from "../../../core/cells/actions";
33
33
  import { ConfigButton } from "../../app-config/app-config-button";
34
34
  import { renderShortcut } from "../../shortcuts/renderShortcut";
35
35
  import { Tooltip } from "../../ui/tooltip";
@@ -11,6 +11,7 @@ import { Provider } from "jotai";
11
11
  import type React from "react";
12
12
  import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
13
13
  import { requestId } from "@/__tests__/branded";
14
+ import { mockDocumentModel } from "@/__mocks__/document";
14
15
  import { MockRequestClient } from "@/__mocks__/requests";
15
16
  import { ModalProvider } from "@/components/modal/ImperativeModal";
16
17
  import { TooltipProvider } from "@/components/ui/tooltip";
@@ -19,6 +20,7 @@ import {
19
20
  invalidateDataSourceDiscovery,
20
21
  } from "@/core/datasets/data-source-discovery";
21
22
  import { DiscoverDataSources } from "@/core/datasets/request-registry";
23
+ import { DocumentProvider } from "@/core/notebook/document";
22
24
  import { layoutStateAtom } from "@/core/layout/state";
23
25
  import { kioskModeAtom, viewStateAtom } from "@/core/mode";
24
26
  import { connectionAtom } from "@/core/network/connection";
@@ -73,12 +75,16 @@ global.HTMLElement.prototype.scrollIntoView = () => {
73
75
  // jsdom does not implement scrollIntoView; cmdk calls it on selection.
74
76
  };
75
77
 
78
+ const { model } = mockDocumentModel(store, null);
79
+
76
80
  function wrapper({ children }: { children: React.ReactNode }) {
77
81
  return (
78
82
  <Provider store={store}>
79
- <TooltipProvider>
80
- <ModalProvider>{children}</ModalProvider>
81
- </TooltipProvider>
83
+ <DocumentProvider model={model}>
84
+ <TooltipProvider>
85
+ <ModalProvider>{children}</ModalProvider>
86
+ </TooltipProvider>
87
+ </DocumentProvider>
82
88
  </Provider>
83
89
  );
84
90
  }
@@ -157,18 +157,41 @@
157
157
  /* Syntax highlighting for LSP hover code blocks (lezer classHighlighter tok-* classes) */
158
158
  .docs-documentation,
159
159
  .cm-tooltip .documentation {
160
- .tok-keyword { color: light-dark(#708, #c678dd); font-weight: 500; }
160
+ .tok-keyword {
161
+ color: light-dark(#708, #c678dd);
162
+ font-weight: 500;
163
+ }
161
164
  .tok-string,
162
- .tok-string2 { color: light-dark(#a11, #98c379); }
163
- .tok-number { color: light-dark(#164, #d19a66); }
165
+ .tok-string2 {
166
+ color: light-dark(#a11, #98c379);
167
+ }
168
+ .tok-number {
169
+ color: light-dark(#164, #d19a66);
170
+ }
164
171
  .tok-bool,
165
- .tok-atom { color: light-dark(#219, #d19a66); }
166
- .tok-comment { color: var(--cm-comment); }
167
- .tok-className { color: light-dark(#00f, #61afef); }
172
+ .tok-atom {
173
+ color: light-dark(#219, #d19a66);
174
+ }
175
+ .tok-comment {
176
+ color: var(--cm-comment);
177
+ }
178
+ .tok-className {
179
+ color: light-dark(#00f, #61afef);
180
+ }
168
181
  .tok-typeName,
169
- .tok-namespace { color: light-dark(#085, #56b6c2); }
170
- .tok-operator { color: light-dark(#a2f, #56b6c2); }
171
- .tok-propertyName { color: light-dark(#05a, #e5c07b); }
172
- .tok-variableName { color: light-dark(#000, #abb2bf); }
173
- .tok-punctuation { color: light-dark(#000, #abb2bf); }
182
+ .tok-namespace {
183
+ color: light-dark(#085, #56b6c2);
184
+ }
185
+ .tok-operator {
186
+ color: light-dark(#a2f, #56b6c2);
187
+ }
188
+ .tok-propertyName {
189
+ color: light-dark(#05a, #e5c07b);
190
+ }
191
+ .tok-variableName {
192
+ color: light-dark(#000, #abb2bf);
193
+ }
194
+ .tok-punctuation {
195
+ color: light-dark(#000, #abb2bf);
196
+ }
174
197
  }
@@ -18,7 +18,8 @@ import {
18
18
  } from "@/components/ui/dropdown-menu";
19
19
  import { Tooltip } from "@/components/ui/tooltip";
20
20
  import { aiCompletionCellAtom } from "@/core/ai/state";
21
- import { notebookAtom, useCellActions } from "@/core/cells/cells";
21
+ import { notebookAtom } from "@/core/cells/cells";
22
+ import { useCellActions } from "@/core/cells/actions";
22
23
  import type { CellId } from "@/core/cells/ids";
23
24
  import { aiFeaturesEnabledAtom } from "@/core/config/config";
24
25
  import { getAutoFixes } from "@/core/errors/errors";
@@ -51,7 +52,7 @@ export const AutoFixButton = ({
51
52
  className?: string;
52
53
  }) => {
53
54
  const store = useStore();
54
- const { createNewCell } = useCellActions();
55
+ const { createCell } = useCellActions();
55
56
  const aiFeaturesEnabled = useAtomValue(aiFeaturesEnabledAtom);
56
57
  const autoFixes = errors.flatMap((error) =>
57
58
  getAutoFixes(error, { aiEnabled: aiFeaturesEnabled }),
@@ -72,12 +73,7 @@ export const AutoFixButton = ({
72
73
  store.get(notebookAtom).cellHandles[cellId].current?.editorView;
73
74
  firstFix.onFix({
74
75
  addCodeBelow: (code: string) => {
75
- createNewCell({
76
- cellId: cellId,
77
- autoFocus: false,
78
- before: false,
79
- code: code,
80
- });
76
+ createCell({ after: cellId, code, focus: false });
81
77
  },
82
78
  editor: editorView,
83
79
  cellId: cellId,
@@ -59,7 +59,7 @@ import {
59
59
  import { Tooltip } from "@/components/ui/tooltip";
60
60
  import { SearchInput } from "@/components/ui/input";
61
61
  import { toast } from "@/components/ui/use-toast";
62
- import { useCellActions } from "@/core/cells/cells";
62
+ import { useCellActions } from "@/core/cells/actions";
63
63
  import { useLastFocusedCellId } from "@/core/cells/focus";
64
64
  import { disableFileDownloadsAtom } from "@/core/config/config";
65
65
  import { useRequestClient } from "@/core/network/requests";
@@ -697,15 +697,11 @@ const Node = ({ node, style, dragHandle }: NodeRendererProps<FileTreeNode>) => {
697
697
 
698
698
  const Icon = FILE_ICON[fileType];
699
699
  const { openPrompt } = useImperativeModal();
700
- const { createNewCell } = useCellActions();
700
+ const { createCell } = useCellActions();
701
701
  const lastFocusedCellId = useLastFocusedCellId();
702
702
 
703
703
  const handleInsertCode = (code: string) => {
704
- createNewCell({
705
- code,
706
- before: false,
707
- cellId: lastFocusedCellId ?? "__end__",
708
- });
704
+ createCell({ after: lastFocusedCellId, code });
709
705
  };
710
706
 
711
707
  const fileExplorer = use(RequestingTreeContext);
@@ -11,8 +11,10 @@ import { CellLink, CellLinkTraceback } from "../cell-link";
11
11
  const showCellIfHidden = vi.hoisted(() => vi.fn());
12
12
  const targetId = cellId("target");
13
13
 
14
- vi.mock("@/core/cells/cells", () => ({
14
+ vi.mock("@/core/cells/actions", () => ({
15
15
  useCellActions: () => ({ showCellIfHidden }),
16
+ }));
17
+ vi.mock("@/core/cells/cells", () => ({
16
18
  useCellIds: () => ({ inOrderIds: [targetId] }),
17
19
  useCellNames: () => ({ [targetId]: "Target" }),
18
20
  }));
@@ -1,7 +1,8 @@
1
1
  /* Copyright 2026 Marimo. All rights reserved. */
2
2
 
3
3
  import type { JSX } from "react"; /* Copyright 2026 Marimo. All rights reserved. */
4
- import { useCellActions, useCellIds, useCellNames } from "@/core/cells/cells";
4
+ import { useCellIds, useCellNames } from "@/core/cells/cells";
5
+ import { useCellActions } from "@/core/cells/actions";
5
6
  import { type CellId, HTMLCellId, SCRATCH_CELL_ID } from "@/core/cells/ids";
6
7
  import { displayCellName } from "@/core/cells/names";
7
8
  import { goToCellLine } from "@/core/codemirror/go-to-definition/utils";
@@ -5,15 +5,18 @@ import { act, renderHook } from "@testing-library/react";
5
5
  import { beforeEach, describe, expect, it, vi } from "vitest";
6
6
  import { asMock, MockModules, Mocks, SetupMocks } from "@/__mocks__/common";
7
7
  import { cellId } from "@/__tests__/branded";
8
- import type { CellActions, NotebookState } from "@/core/cells/cells";
8
+ import type { CellActions } from "@/core/cells/actions";
9
+ import type { NotebookState } from "@/core/cells/cells";
9
10
  import { useCellClipboard } from "../clipboard";
10
11
 
11
12
  // Mock dependencies
12
13
  vi.mock("@/components/ui/use-toast", () => MockModules.toast());
13
14
 
15
+ vi.mock("@/core/cells/actions", () => ({
16
+ useCellActions: vi.fn(),
17
+ }));
14
18
  vi.mock("@/core/cells/cells", () => ({
15
19
  getNotebook: vi.fn(),
16
- useCellActions: vi.fn(),
17
20
  }));
18
21
 
19
22
  vi.mock("@/utils/Logger", () => ({
@@ -33,14 +36,15 @@ vi.mock("@/core/cells/pending-cut-service", () => ({
33
36
 
34
37
  import { MockNotebook } from "@/__mocks__/notebook";
35
38
  import { toast } from "@/components/ui/use-toast";
36
- import { getNotebook, useCellActions } from "@/core/cells/cells";
39
+ import { useCellActions } from "@/core/cells/actions";
40
+ import { getNotebook } from "@/core/cells/cells";
37
41
  import { Logger } from "@/utils/Logger";
38
42
 
39
43
  describe("useCellClipboard", () => {
40
44
  const [mockCellId1, mockCellId2] = MockNotebook.cellIds();
41
45
  const mockCellCode1 = "print('hello world')";
42
46
  const mockCellCode2 = "x = 42";
43
- const mockCreateNewCell = vi.fn();
47
+ const mockCreateCell = vi.fn();
44
48
 
45
49
  const mockClipboard = Mocks.clipboard();
46
50
 
@@ -70,7 +74,7 @@ describe("useCellClipboard", () => {
70
74
  } as NotebookState);
71
75
 
72
76
  asMock(useCellActions).mockReturnValue({
73
- createNewCell: mockCreateNewCell,
77
+ createCell: mockCreateCell,
74
78
  } as unknown as CellActions);
75
79
  });
76
80
 
@@ -330,11 +334,40 @@ describe("useCellClipboard", () => {
330
334
  await result.current.pasteAtCell(mockCellId1);
331
335
  });
332
336
 
333
- expect(mockCreateNewCell).toHaveBeenCalledWith({
334
- cellId: mockCellId1,
335
- before: false,
337
+ expect(mockCreateCell).toHaveBeenCalledWith({
338
+ after: mockCellId1,
339
+ code: "x = 42",
340
+ config: {},
341
+ });
342
+ });
343
+
344
+ it("drops the copied column so the cell joins the column it is pasted into", async () => {
345
+ const clipboardData = {
346
+ cells: [{ code: "x = 42", config: { column: 1, hide_code: true } }],
347
+ version: "1.0",
348
+ };
349
+
350
+ const mockItem = {
351
+ types: ["web application/x-marimo-cell"],
352
+ getType: vi.fn().mockResolvedValue(
353
+ new Blob([JSON.stringify(clipboardData)], {
354
+ type: "web application/x-marimo-cell",
355
+ }),
356
+ ),
357
+ };
358
+
359
+ mockClipboard.read.mockResolvedValue([mockItem]);
360
+
361
+ const { result } = renderHook(() => useCellClipboard());
362
+
363
+ await act(async () => {
364
+ await result.current.pasteAtCell(mockCellId1);
365
+ });
366
+
367
+ expect(mockCreateCell).toHaveBeenCalledWith({
368
+ after: mockCellId1,
336
369
  code: "x = 42",
337
- autoFocus: true,
370
+ config: { hide_code: true },
338
371
  });
339
372
  });
340
373
 
@@ -365,24 +398,21 @@ describe("useCellClipboard", () => {
365
398
  await result.current.pasteAtCell(mockCellId1);
366
399
  });
367
400
 
368
- expect(mockCreateNewCell).toHaveBeenCalledTimes(3);
369
- expect(mockCreateNewCell).toHaveBeenNthCalledWith(3, {
370
- cellId: mockCellId1,
371
- before: false,
401
+ expect(mockCreateCell).toHaveBeenCalledTimes(3);
402
+ expect(mockCreateCell).toHaveBeenNthCalledWith(3, {
403
+ after: mockCellId1,
372
404
  code: "x = 42",
373
- autoFocus: true,
405
+ config: {},
374
406
  });
375
- expect(mockCreateNewCell).toHaveBeenNthCalledWith(2, {
376
- cellId: mockCellId1,
377
- before: false,
407
+ expect(mockCreateCell).toHaveBeenNthCalledWith(2, {
408
+ after: mockCellId1,
378
409
  code: "y = x * 2",
379
- autoFocus: true,
410
+ config: {},
380
411
  });
381
- expect(mockCreateNewCell).toHaveBeenNthCalledWith(1, {
382
- cellId: mockCellId1,
383
- before: false,
412
+ expect(mockCreateCell).toHaveBeenNthCalledWith(1, {
413
+ after: mockCellId1,
384
414
  code: "print(y)",
385
- autoFocus: true,
415
+ config: {},
386
416
  });
387
417
  });
388
418
 
@@ -401,11 +431,9 @@ describe("useCellClipboard", () => {
401
431
  await result.current.pasteAtCell(mockCellId1);
402
432
  });
403
433
 
404
- expect(mockCreateNewCell).toHaveBeenCalledWith({
405
- cellId: mockCellId1,
406
- before: false,
434
+ expect(mockCreateCell).toHaveBeenCalledWith({
435
+ after: mockCellId1,
407
436
  code: "plain text code",
408
- autoFocus: true,
409
437
  });
410
438
  });
411
439
 
@@ -432,11 +460,9 @@ describe("useCellClipboard", () => {
432
460
  "Failed to parse clipboard cell data",
433
461
  expect.any(Error),
434
462
  );
435
- expect(mockCreateNewCell).toHaveBeenCalledWith({
436
- cellId: mockCellId1,
437
- before: false,
463
+ expect(mockCreateCell).toHaveBeenCalledWith({
464
+ after: mockCellId1,
438
465
  code: "fallback text",
439
- autoFocus: true,
440
466
  });
441
467
  });
442
468
 
@@ -522,11 +548,9 @@ describe("useCellClipboard", () => {
522
548
  "Failed to parse clipboard cell data",
523
549
  expect.any(Error),
524
550
  );
525
- expect(mockCreateNewCell).toHaveBeenCalledWith({
526
- cellId: mockCellId1,
527
- before: false,
551
+ expect(mockCreateCell).toHaveBeenCalledWith({
552
+ after: mockCellId1,
528
553
  code: "fallback text",
529
- autoFocus: true,
530
554
  });
531
555
  });
532
556
 
@@ -554,11 +578,9 @@ describe("useCellClipboard", () => {
554
578
  await result.current.pasteAtCell(mockCellId1);
555
579
  });
556
580
 
557
- expect(mockCreateNewCell).toHaveBeenCalledWith({
558
- cellId: mockCellId1,
559
- before: false,
581
+ expect(mockCreateCell).toHaveBeenCalledWith({
582
+ after: mockCellId1,
560
583
  code: "fallback text",
561
- autoFocus: true,
562
584
  });
563
585
  });
564
586
  });