@marimo-team/islands 0.24.3-dev83 → 0.24.3-dev88
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.
- package/dist/{ErrorBoundary-Uf_LvjvY.js → ErrorBoundary-B2X1GHu6.js} +1 -1
- package/dist/{code-visibility-DxgQWu1j.js → code-visibility-Crx6UYYV.js} +1 -1
- package/dist/{common-ByAtncLr.js → common-B0G8iLT2.js} +2 -2
- package/dist/{data-grid-overlay-editor-DL_blFyL.js → data-grid-overlay-editor-B41XQBJD.js} +1 -1
- package/dist/{feedback-button-AZcBqfoV.js → feedback-button-Ct6mvQkx.js} +2 -2
- package/dist/{glide-data-editor-BJdZncJk.js → glide-data-editor-Cf3tJ2PH.js} +3 -3
- package/dist/{globals-yWarpyN4.js → globals-FEQwhGbc.js} +1 -1
- package/dist/main.js +19 -9
- package/dist/{number-overlay-editor-BatBVYxr.js → number-overlay-editor-CF9a1VxK.js} +1 -1
- package/dist/{reveal-component-D02jcpiJ.js → reveal-component-BPIsjCXN.js} +2 -2
- package/dist/style.css +1 -1
- package/package.json +1 -1
- package/src/__tests__/fixtures/pair-preview.ts +1 -1
- package/src/components/editor/actions/__tests__/pair-with-agent-commands.test.ts +6 -6
- package/src/components/editor/actions/__tests__/pair-with-agent-modal.test.tsx +1 -1
- package/src/components/editor/output/Outputs.css +0 -1
- package/src/components/ui/table.tsx +1 -1
- package/src/css/app/Cell.css +0 -2
- package/src/plugins/impl/FileBrowserPlugin.tsx +10 -4
- package/src/plugins/impl/__tests__/FileBrowserPlugin.test.tsx +50 -1
package/package.json
CHANGED
|
@@ -6,7 +6,7 @@ import { pairPreviewSchema } from "@/core/config/pair";
|
|
|
6
6
|
|
|
7
7
|
// Read the Python-owned resource only in tests to check the shared contract.
|
|
8
8
|
export const PAIR_PREVIEW = pairPreviewSchema.parse({
|
|
9
|
-
command: "
|
|
9
|
+
command: "uvx marimo@latest",
|
|
10
10
|
templates: JSON.parse(
|
|
11
11
|
readFileSync(
|
|
12
12
|
path.resolve(
|
|
@@ -129,7 +129,7 @@ describe("getTerminalCommand", () => {
|
|
|
129
129
|
PAIR_PREVIEW,
|
|
130
130
|
),
|
|
131
131
|
).toBe(
|
|
132
|
-
String.raw`codex "$(MARIMO_PAIR_NEXT=1
|
|
132
|
+
String.raw`codex "$(MARIMO_PAIR_NEXT=1 uvx marimo@latest pair prompt \
|
|
133
133
|
--url http://localhost:8000)"`,
|
|
134
134
|
);
|
|
135
135
|
} finally {
|
|
@@ -152,7 +152,7 @@ describe("getTerminalCommand", () => {
|
|
|
152
152
|
PAIR_PREVIEW,
|
|
153
153
|
),
|
|
154
154
|
).toBe(
|
|
155
|
-
String.raw`${cli} "$(MARIMO_PAIR_NEXT=1
|
|
155
|
+
String.raw`${cli} "$(MARIMO_PAIR_NEXT=1 uvx marimo@latest pair prompt \
|
|
156
156
|
--url http://localhost:8000 \
|
|
157
157
|
--file notebooks/example.py \
|
|
158
158
|
--session s_ab12cd \
|
|
@@ -264,8 +264,8 @@ describe("getRawPrompt", () => {
|
|
|
264
264
|
expect(getRawPrompt(connection, null, PAIR_PREVIEW)).toBe(
|
|
265
265
|
"Pair with me on this running marimo notebook.\n\n" +
|
|
266
266
|
`URL: http://localhost:8000\n${fields}\n` +
|
|
267
|
-
"Run `
|
|
268
|
-
"Use `
|
|
267
|
+
"Run `uvx marimo@latest pair --help` first.\n" +
|
|
268
|
+
"Use `uvx marimo@latest` for all marimo commands.\n\n" +
|
|
269
269
|
"Once connected, send a fun toast using `mo.status.toast(...)` (`import marimo as mo`).",
|
|
270
270
|
);
|
|
271
271
|
});
|
|
@@ -278,8 +278,8 @@ describe("getRawPrompt", () => {
|
|
|
278
278
|
"URL: http://localhost:8000\n" +
|
|
279
279
|
"File: notebooks/example.py\n" +
|
|
280
280
|
"Session: s_ab12cd\n\n" +
|
|
281
|
-
"Run `
|
|
282
|
-
"Use `
|
|
281
|
+
"Run `uvx marimo@latest pair --help` first.\n" +
|
|
282
|
+
"Use `uvx marimo@latest` for all marimo commands.\n\n" +
|
|
283
283
|
"Once connected, send a fun toast using `mo.status.toast(...)` (`import marimo as mo`).",
|
|
284
284
|
);
|
|
285
285
|
});
|
|
@@ -203,7 +203,7 @@ describe("PairWithAgentModal", () => {
|
|
|
203
203
|
);
|
|
204
204
|
await waitFor(() =>
|
|
205
205
|
expect(copyToClipboard).toHaveBeenCalledWith(
|
|
206
|
-
String.raw`claude "$(MARIMO_PAIR_NEXT=1
|
|
206
|
+
String.raw`claude "$(MARIMO_PAIR_NEXT=1 uvx marimo@latest pair prompt \
|
|
207
207
|
--url http://localhost:8000/ \
|
|
208
208
|
--file notebook.py \
|
|
209
209
|
--session ${getSessionId()} \
|
|
@@ -7,7 +7,7 @@ const Table = React.forwardRef<
|
|
|
7
7
|
HTMLTableElement,
|
|
8
8
|
React.HTMLAttributes<HTMLTableElement>
|
|
9
9
|
>(({ className, ...props }, ref) => (
|
|
10
|
-
<div className="w-full overflow-auto
|
|
10
|
+
<div className="w-full overflow-auto scrollbar-thin flex-1 print:overflow-hidden">
|
|
11
11
|
<table
|
|
12
12
|
ref={ref}
|
|
13
13
|
className={cn("w-full caption-bottom text-sm", className)}
|
package/src/css/app/Cell.css
CHANGED
|
@@ -82,7 +82,6 @@
|
|
|
82
82
|
.console-output-area {
|
|
83
83
|
max-height: 610px;
|
|
84
84
|
overflow: auto;
|
|
85
|
-
overscroll-behavior: contain;
|
|
86
85
|
}
|
|
87
86
|
|
|
88
87
|
/* Special case for particular components */
|
|
@@ -522,7 +521,6 @@
|
|
|
522
521
|
display: flow-root;
|
|
523
522
|
|
|
524
523
|
overflow: auto;
|
|
525
|
-
overscroll-behavior: contain;
|
|
526
524
|
}
|
|
527
525
|
|
|
528
526
|
.marimo-output-stale,
|
|
@@ -218,7 +218,7 @@ export const FileBrowser = ({
|
|
|
218
218
|
|
|
219
219
|
const { data, error, isPending } = useAsyncData(() => {
|
|
220
220
|
return list_directory({ path: path });
|
|
221
|
-
}, [path, randomId]);
|
|
221
|
+
}, [path, randomId, list_directory]);
|
|
222
222
|
|
|
223
223
|
useEffect(() => {
|
|
224
224
|
if (!isPending) {
|
|
@@ -238,9 +238,15 @@ export const FileBrowser = ({
|
|
|
238
238
|
// Reset the roving tabindex whenever the listing reloads (a new path or a
|
|
239
239
|
// same-path refresh) so activeIndex never points past the current rows.
|
|
240
240
|
const listingKey = `${path}::${randomId}`;
|
|
241
|
-
const [
|
|
242
|
-
|
|
243
|
-
|
|
241
|
+
const [prevListing, setPrevListing] = useState({
|
|
242
|
+
listingKey,
|
|
243
|
+
list_directory,
|
|
244
|
+
});
|
|
245
|
+
if (
|
|
246
|
+
prevListing.listingKey !== listingKey ||
|
|
247
|
+
prevListing.list_directory !== list_directory
|
|
248
|
+
) {
|
|
249
|
+
setPrevListing({ listingKey, list_directory });
|
|
244
250
|
setActiveIndex(0);
|
|
245
251
|
}
|
|
246
252
|
|
|
@@ -5,8 +5,9 @@ import { beforeAll, describe, expect, it, vi } from "vitest";
|
|
|
5
5
|
import { SetupMocks } from "@/__mocks__/common";
|
|
6
6
|
import { initialModeAtom } from "@/core/mode";
|
|
7
7
|
import { store } from "@/core/state/jotai";
|
|
8
|
+
import { CellNotInitializedError } from "@/utils/errors";
|
|
8
9
|
import type { IPluginProps } from "../../types";
|
|
9
|
-
import { FileBrowserPlugin } from "../FileBrowserPlugin";
|
|
10
|
+
import { FileBrowser, FileBrowserPlugin } from "../FileBrowserPlugin";
|
|
10
11
|
|
|
11
12
|
interface MockFile {
|
|
12
13
|
id: string;
|
|
@@ -80,6 +81,54 @@ beforeAll(() => {
|
|
|
80
81
|
store.set(initialModeAtom, "edit");
|
|
81
82
|
});
|
|
82
83
|
|
|
84
|
+
describe("FileBrowserPlugin session cache recovery", () => {
|
|
85
|
+
it("retries a failed cached listing when the plugin resets", async () => {
|
|
86
|
+
const host = document.createElement("marimo-file-browser");
|
|
87
|
+
const wrapper = document.createElement("marimo-ui-element");
|
|
88
|
+
wrapper.setAttribute("random-id", "cached-id");
|
|
89
|
+
wrapper.append(host);
|
|
90
|
+
|
|
91
|
+
const props = {
|
|
92
|
+
initialPath: "/home/user",
|
|
93
|
+
filetypes: [],
|
|
94
|
+
selectionMode: "directory",
|
|
95
|
+
multiple: false,
|
|
96
|
+
label: "Pick folder",
|
|
97
|
+
restrictNavigation: false,
|
|
98
|
+
value: [],
|
|
99
|
+
setValue: vi.fn(),
|
|
100
|
+
host,
|
|
101
|
+
};
|
|
102
|
+
const error = new CellNotInitializedError();
|
|
103
|
+
const cachedListDirectory = vi.fn().mockRejectedValue(error);
|
|
104
|
+
const { rerender } = render(
|
|
105
|
+
<FileBrowser {...props} list_directory={cachedListDirectory} />,
|
|
106
|
+
);
|
|
107
|
+
expect(await screen.findByText(error.message)).toBeInTheDocument();
|
|
108
|
+
|
|
109
|
+
// PluginSlot recreates the RPC functions on reset, even when the path
|
|
110
|
+
// and the host's attributes are unchanged.
|
|
111
|
+
const liveListDirectory = mockListDirectory(FILES);
|
|
112
|
+
rerender(<FileBrowser {...props} list_directory={liveListDirectory} />);
|
|
113
|
+
|
|
114
|
+
expect(await screen.findByText("docs")).toBeInTheDocument();
|
|
115
|
+
expect(screen.queryByText(error.message)).not.toBeInTheDocument();
|
|
116
|
+
expect(liveListDirectory.mock.calls).toEqual([[{ path: "/home/user" }]]);
|
|
117
|
+
|
|
118
|
+
fireEvent.click(screen.getByRole("checkbox", { name: "Select docs" }));
|
|
119
|
+
expect(props.setValue).toHaveBeenCalledWith([
|
|
120
|
+
{ ...FILES[0], id: FILES[0].path },
|
|
121
|
+
]);
|
|
122
|
+
|
|
123
|
+
fireEvent.keyDown(screen.getAllByRole("row")[0], { key: "End" });
|
|
124
|
+
rerender(
|
|
125
|
+
<FileBrowser {...props} list_directory={mockListDirectory([FILES[0]])} />,
|
|
126
|
+
);
|
|
127
|
+
await waitFor(() => expect(screen.getAllByRole("row")).toHaveLength(2));
|
|
128
|
+
expect(screen.getAllByRole("row")[0]).toHaveAttribute("tabindex", "0");
|
|
129
|
+
});
|
|
130
|
+
});
|
|
131
|
+
|
|
83
132
|
describe("FileBrowserPlugin keyboard accessibility", () => {
|
|
84
133
|
it("renders a row per file plus the parent row", async () => {
|
|
85
134
|
renderBrowser();
|