@marimo-team/islands 0.23.16-dev45 → 0.23.16-dev48
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/{chat-ui-BhycUrBk.js → chat-ui-1e7PcW56.js} +19 -22
- package/dist/{common-CWszsqAm.js → common-iyiGAJwl.js} +1 -1
- package/dist/main.js +4 -4
- package/dist/{process-output-YXcQTd1Y.js → process-output-BRwR4QGs.js} +30 -26
- package/dist/{reveal-component-C1UBr2Io.js → reveal-component-BL7inNNa.js} +1 -1
- package/package.json +1 -1
- package/src/components/editor/file-tree/__tests__/renderers.test.ts +31 -0
- package/src/components/editor/file-tree/file-viewer.tsx +11 -7
- package/src/components/editor/file-tree/renderers.tsx +21 -0
- package/src/core/ai/context/providers/file.ts +8 -29
- package/src/utils/__tests__/blob.test.ts +27 -1
- package/src/utils/blob.ts +24 -1
|
@@ -6,13 +6,13 @@ import { c as useEventListener, g as Logger, h as cn, t as Button } from "./butt
|
|
|
6
6
|
import { t as require_react } from "./react-DA-nE2FX.js";
|
|
7
7
|
import { t as require_compiler_runtime } from "./compiler-runtime-CEbnTgxf.js";
|
|
8
8
|
import { r as toast } from "./copy-DNq8q3zw.js";
|
|
9
|
-
import { Bn as Info, Bt as PluralWord, C as Accordion, E as AccordionTrigger, En as Anchor2,
|
|
9
|
+
import { Bn as Info, Bt as PluralWord, C as Accordion, E as AccordionTrigger, En as Anchor2, Ft as variablesAtom, Gt as allTablesAtom, H as renderHTML, Kn as CircleX, Kt as dataSourceConnectionsAtom, Mn as Wrench, Nn as Trash2, O as ChatBubbleIcon, Pt as jotaiJsonStorage, Q as notebookAtom, Rn as LoaderCircle, S as AIContextRegistry, T as AccordionItem, Un as ExternalLink, Vn as FileText, Yt as getRequestClient, b as contextToXml, c as Popover, d as PopoverTrigger, f as isOutputEmpty, g as formatDatasourceContextForCell, h as DatasourceContextProvider, ht as displayCellName, in as singleFacet, jt as generateUUID, kt as moveToEndOfEditor, ln as ZodLocalStorage, mn as CellOutputId, n as Spinner, nn as isMarimoErrorsMime, qt as getTableType, r as MarkdownRenderer, rn as isTracebackMime, st as parseHtmlContent, t as toPng, tn as isErrorMime, u as PopoverContent, v as Boosts, w as AccordionContent, wn as atomWithStorage, wt as createVariableInfoElement, x as AIContextProvider, y as Sections } from "./html-to-image-3w0AakWW.js";
|
|
10
10
|
import "./chunk-5FQGJX7Z-B9WoXK1R.js";
|
|
11
11
|
import { u as createLucideIcon } from "./dist-DIlxLFXG.js";
|
|
12
12
|
import { C as logNever, I as X, R as ChevronDown, t as Strings } from "./strings-DIy9NAmg.js";
|
|
13
13
|
import { C as DropdownMenuTrigger, a as NumberField, f as DropdownMenu, h as DropdownMenuItem, p as DropdownMenuContent, r as Input } from "./input-C5K4VBvB.js";
|
|
14
14
|
import { p as isUrl, w as CircleQuestionMark } from "./toDate-CqhBWjvO.js";
|
|
15
|
-
import { a as MarimoIncomingMessageEvent, d as
|
|
15
|
+
import { a as MarimoIncomingMessageEvent, d as fileDetailsToBlob, f as Square, n as blobToString, p as File$1, t as processOutput } from "./process-output-BRwR4QGs.js";
|
|
16
16
|
import "./react-dom-BTJzcVJ9.js";
|
|
17
17
|
import { t as require_jsx_runtime } from "./jsx-runtime-DebpN0FN.js";
|
|
18
18
|
import { A as looseObject, B as union, C as any, D as discriminatedUnion, E as custom, H as safeParseAsync, I as record, L as strictObject, M as never, N as number, O as lazy, P as object$1, R as string, S as _null, T as boolean, V as unknown, W as toJSONSchema, b as _enum, k as literal, w as array$1, x as _instanceof } from "./zod-BUcyXSdR.js";
|
|
@@ -6328,14 +6328,11 @@ var DEFAULT_FILE_SEARCH_CONFIG = {
|
|
|
6328
6328
|
description: e20.message
|
|
6329
6329
|
}), null));
|
|
6330
6330
|
if (!C) return;
|
|
6331
|
-
let w = C.mimeType || "text/plain", T
|
|
6332
|
-
|
|
6333
|
-
|
|
6334
|
-
|
|
6335
|
-
}
|
|
6336
|
-
T = new Blob([C.contents], { type: w });
|
|
6337
|
-
}
|
|
6338
|
-
else T = new Blob([""], { type: w });
|
|
6331
|
+
let w = C.mimeType || "text/plain", T = fileDetailsToBlob({
|
|
6332
|
+
contents: C.contents ?? "",
|
|
6333
|
+
mimeType: w,
|
|
6334
|
+
isBase64: C.isBase64 ?? false
|
|
6335
|
+
});
|
|
6339
6336
|
x(new File([T], g, { type: w })), e19.dispatch({ changes: {
|
|
6340
6337
|
from: y,
|
|
6341
6338
|
to: b,
|
|
@@ -6760,20 +6757,20 @@ const ToolErrorCard = (e18) => {
|
|
|
6760
6757
|
className: "font-semibold",
|
|
6761
6758
|
children: "Failed:"
|
|
6762
6759
|
}), h[7] = A) : A = h[7];
|
|
6763
|
-
let
|
|
6764
|
-
h[8] === g ?
|
|
6760
|
+
let M;
|
|
6761
|
+
h[8] === g ? M = h[9] : (M = formatToolName(g), h[8] = g, h[9] = M);
|
|
6765
6762
|
let N;
|
|
6766
|
-
h[10] ===
|
|
6763
|
+
h[10] === M ? N = h[11] : (N = /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("span", {
|
|
6767
6764
|
className: "flex-1 text-left",
|
|
6768
6765
|
children: [
|
|
6769
6766
|
A,
|
|
6770
6767
|
" ",
|
|
6771
6768
|
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("code", {
|
|
6772
6769
|
className: "font-mono",
|
|
6773
|
-
children:
|
|
6770
|
+
children: M
|
|
6774
6771
|
})
|
|
6775
6772
|
]
|
|
6776
|
-
}), h[10] =
|
|
6773
|
+
}), h[10] = M, h[11] = N);
|
|
6777
6774
|
let P = S && "rotate-180", F;
|
|
6778
6775
|
h[12] === P ? F = h[13] : (F = cn("h-3.5 w-3.5 shrink-0 transition-transform", P), h[12] = P, h[13] = F);
|
|
6779
6776
|
let I;
|
|
@@ -6983,8 +6980,8 @@ const ToolHistoryRow = (e18) => {
|
|
|
6983
6980
|
className: N,
|
|
6984
6981
|
children: R
|
|
6985
6982
|
}), h[19] = R, h[20] = N, h[21] = z) : z = h[21];
|
|
6986
|
-
let
|
|
6987
|
-
h[22] !== x || h[23] !== y || h[24] !== b || h[25] !== _ ? (
|
|
6983
|
+
let V;
|
|
6984
|
+
h[22] !== x || h[23] !== y || h[24] !== b || h[25] !== _ ? (V = /* @__PURE__ */ (0, import_jsx_runtime.jsx)(AccordionContent, {
|
|
6988
6985
|
className: "py-2 px-2",
|
|
6989
6986
|
children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(HistoryContent, {
|
|
6990
6987
|
state: _,
|
|
@@ -6992,13 +6989,13 @@ const ToolHistoryRow = (e18) => {
|
|
|
6992
6989
|
result: b,
|
|
6993
6990
|
approval: x
|
|
6994
6991
|
})
|
|
6995
|
-
}), h[22] = x, h[23] = y, h[24] = b, h[25] = _, h[26] =
|
|
6992
|
+
}), h[22] = x, h[23] = y, h[24] = b, h[25] = _, h[26] = V) : V = h[26];
|
|
6996
6993
|
let H;
|
|
6997
|
-
h[27] !== z || h[28] !==
|
|
6994
|
+
h[27] !== z || h[28] !== V ? (H = /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(AccordionItem, {
|
|
6998
6995
|
value: "tool-call",
|
|
6999
6996
|
className: "border-0",
|
|
7000
|
-
children: [z,
|
|
7001
|
-
}), h[27] = z, h[28] =
|
|
6997
|
+
children: [z, V]
|
|
6998
|
+
}), h[27] = z, h[28] = V, h[29] = H) : H = h[29];
|
|
7002
6999
|
let U;
|
|
7003
7000
|
return h[30] !== H || h[31] !== j || h[32] !== M ? (U = /* @__PURE__ */ (0, import_jsx_runtime.jsx)(Accordion, {
|
|
7004
7001
|
type: "single",
|
|
@@ -7826,7 +7823,7 @@ const Chatbot = (e18) => {
|
|
|
7826
7823
|
Object.keys(e18.config).some((h2) => e18.config[h2] !== C[h2]) && (S(e18.config), w(e18.config));
|
|
7827
7824
|
let j = (0, import_react.useRef)(x);
|
|
7828
7825
|
j.current = x;
|
|
7829
|
-
let M = (0, import_react.useRef)(null), N = (0, import_react.useRef)(null), { data:
|
|
7826
|
+
let M = (0, import_react.useRef)(null), N = (0, import_react.useRef)(null), { data: F } = useAsyncData(async () => (await e18.get_chat_history({})).messages, []), I = e18.value.length > 0 ? e18.value : F, { messages: L, sendMessage: R, setMessages: z, status: B, stop: V, error: H, regenerate: U, clearError: W, addToolApprovalResponse: G } = useChat({
|
|
7830
7827
|
sendAutomaticallyWhen: ({ messages: e19 }) => hasPendingToolCalls(e19),
|
|
7831
7828
|
transport: new DefaultChatTransport({ fetch: async (h2, g) => {
|
|
7832
7829
|
var _a2;
|
|
@@ -36338,7 +36338,7 @@ ${d}`,
|
|
|
36338
36338
|
return Logger.warn("Failed to get version from mount config"), null;
|
|
36339
36339
|
}
|
|
36340
36340
|
}
|
|
36341
|
-
marimoVersionAtom = atom(getVersionFromMountConfig() || "0.23.16-
|
|
36341
|
+
marimoVersionAtom = atom(getVersionFromMountConfig() || "0.23.16-dev48");
|
|
36342
36342
|
showCodeInRunModeAtom = atom(true);
|
|
36343
36343
|
atom(null);
|
|
36344
36344
|
var import_compiler_runtime = require_compiler_runtime();
|
package/dist/main.js
CHANGED
|
@@ -26,13 +26,13 @@ import { $ as notebookOutline, $t as publishedCellClasses, A as ChevronDownIcon,
|
|
|
26
26
|
import { __tla as __tla_1 } from "./chunk-5FQGJX7Z-B9WoXK1R.js";
|
|
27
27
|
import { o as useSize, s as Root$1, u as createLucideIcon } from "./dist-DIlxLFXG.js";
|
|
28
28
|
import { A as SquareFunction, C as DEFAULT_COLOR_SCHEME, D as SCALE_TYPE_DESCRIPTIONS, E as EMPTY_VALUE$1, O as TIME_UNIT_DESCRIPTIONS, S as DEFAULT_AGGREGATION, T as DEFAULT_TIME_UNIT, _ as AGGREGATION_TYPE_DESCRIPTIONS, a as AGGREGATION_FNS$1, b as COLOR_SCHEMES, c as COLOR_BY_FIELDS, d as NONE_VALUE, f as SELECTABLE_DATA_TYPES, g as TIME_UNITS, h as STRING_AGGREGATION_FNS, i as convertDataTypeToSelectable, j as ChartColumn, k as escapeFieldName, l as COMBINED_TIME_UNITS, m as SORT_TYPES, n as createSpecWithoutData, o as BIN_AGGREGATION, p as SINGLE_TIME_UNITS, r as isFieldSet, s as CHART_TYPES, t as augmentSpecWithData, u as ChartType, v as AGGREGATION_TYPE_ICON, w as DEFAULT_MAX_BINS_FACET, x as COUNT_FIELD, y as CHART_TYPE_ICON } from "./spec-CQKL_D3i.js";
|
|
29
|
-
import { $ as CommandSeparator, $t as Kbd, A as ErrorState, At as getPageIndexForRow, B as ContextMenuTrigger, Bt as dateToLocalISODate, C as downloadHTMLAsImage, Ct as inferFieldTypes, D as ColumnName, Dt as DelayMount, E as downloadSizeLimitAtom, Et as ColumnChartSpecModel, F as getUserColumnVisibilityCounts, Ft as TOO_MANY_ROWS, G as DateRangePicker, Gt as TabsList, H as useSelectList, Ht as dateToLocalISOTime, I as ContextMenu, It as toFieldTypes, J as Command, Jt as ChartInfoState, K as Combobox, Kt as TabsTrigger, L as ContextMenuContent, Lt as getMimeValues, M as prettifyRowColumnCount, Mt as loadTableData, N as prettifyRowCount, Nt as INDEX_COLUMN_NAME, O as ColumnPreviewContainer, Ot as useIntersectionObserver, P as getColumnCountForDisplay, Pt as SELECT_COLUMN_ID, Q as CommandList, Qt as RenderTextWithLinks, R as ContextMenuItem, Rt as isNullishFilter, S as downloadExportedFile, St as generateColumns, T as Filenames, Tt as ColumnChartContext, U as CompactChipRow, Ut as Tabs, V as useInternalStateWithSync, Vt as dateToLocalISODateTime, W as DatePicker, Wt as TabsContent, X as CommandInput, Xt as LazyVegaEmbed, Y as CommandEmpty, Yt as ChartLoadingState, Z as CommandItem, Zt as useOverflowDetection, _ as DataTable, _n as ChevronLeft, _t as TableCell, an as TextWrap, at as contextAwarePanelType, b as downloadBlob, bt as TableRow, c as SLIDE_TYPE_OPTIONS_BY_VALUE, cn as EyeOff, ct as slotsController, d as Switch, dn as Download, en as HtmlOutput, et as smartMatch, f as RadioGroup, fn as Code, g as OutputRenderer, gn as ChevronsDownUp, gt as TableBody, h as OutputArea, hn as ChevronsLeft, ht as Table, i as showCodeInRunModeAtom, in as $fae977aafc393c5c$export$6b862160d295c8e, it as contextAwarePanelOwner, j as LoadingState, jt as loadTableAndRawData, k as EmptyState, kt as usePrevious$1, lt as Toggle, m as JsonOutput, mn as ChevronsRight, mt as Provider$1, n as useNotebookCodeAvailable, nn as safeLocale, nt as PANEL_TYPES, on as GripHorizontal, ot as isCellAwareAtom, p as RadioGroupItem, pn as ChevronsUpDown, pt as Fill, q as ComboboxItem, qt as ChartErrorState, r as marimoVersionAtom, rn as $fae977aafc393c5c$export$588937bcd60ade55, rt as contextAwarePanelOpen, sn as Funnel, st as SlotNames, t as cellDomProps, tn as EmotionCacheProvider, tt as ContextAwarePanelItem, u as Slide, un as Ellipsis, v as InstallPackageButton, vn as ArrowDownWideNarrow, vt as TableHead, w as Progress, wt as renderCellValue, x as downloadByURL, xt as NAMELESS_COLUMN_PREFIX, y as ADD_PRINTING_CLASS, yt as TableHeader, z as ContextMenuSeparator, zt as Maps, __tla as __tla_2 } from "./common-
|
|
29
|
+
import { $ as CommandSeparator, $t as Kbd, A as ErrorState, At as getPageIndexForRow, B as ContextMenuTrigger, Bt as dateToLocalISODate, C as downloadHTMLAsImage, Ct as inferFieldTypes, D as ColumnName, Dt as DelayMount, E as downloadSizeLimitAtom, Et as ColumnChartSpecModel, F as getUserColumnVisibilityCounts, Ft as TOO_MANY_ROWS, G as DateRangePicker, Gt as TabsList, H as useSelectList, Ht as dateToLocalISOTime, I as ContextMenu, It as toFieldTypes, J as Command, Jt as ChartInfoState, K as Combobox, Kt as TabsTrigger, L as ContextMenuContent, Lt as getMimeValues, M as prettifyRowColumnCount, Mt as loadTableData, N as prettifyRowCount, Nt as INDEX_COLUMN_NAME, O as ColumnPreviewContainer, Ot as useIntersectionObserver, P as getColumnCountForDisplay, Pt as SELECT_COLUMN_ID, Q as CommandList, Qt as RenderTextWithLinks, R as ContextMenuItem, Rt as isNullishFilter, S as downloadExportedFile, St as generateColumns, T as Filenames, Tt as ColumnChartContext, U as CompactChipRow, Ut as Tabs, V as useInternalStateWithSync, Vt as dateToLocalISODateTime, W as DatePicker, Wt as TabsContent, X as CommandInput, Xt as LazyVegaEmbed, Y as CommandEmpty, Yt as ChartLoadingState, Z as CommandItem, Zt as useOverflowDetection, _ as DataTable, _n as ChevronLeft, _t as TableCell, an as TextWrap, at as contextAwarePanelType, b as downloadBlob, bt as TableRow, c as SLIDE_TYPE_OPTIONS_BY_VALUE, cn as EyeOff, ct as slotsController, d as Switch, dn as Download, en as HtmlOutput, et as smartMatch, f as RadioGroup, fn as Code, g as OutputRenderer, gn as ChevronsDownUp, gt as TableBody, h as OutputArea, hn as ChevronsLeft, ht as Table, i as showCodeInRunModeAtom, in as $fae977aafc393c5c$export$6b862160d295c8e, it as contextAwarePanelOwner, j as LoadingState, jt as loadTableAndRawData, k as EmptyState, kt as usePrevious$1, lt as Toggle, m as JsonOutput, mn as ChevronsRight, mt as Provider$1, n as useNotebookCodeAvailable, nn as safeLocale, nt as PANEL_TYPES, on as GripHorizontal, ot as isCellAwareAtom, p as RadioGroupItem, pn as ChevronsUpDown, pt as Fill, q as ComboboxItem, qt as ChartErrorState, r as marimoVersionAtom, rn as $fae977aafc393c5c$export$588937bcd60ade55, rt as contextAwarePanelOpen, sn as Funnel, st as SlotNames, t as cellDomProps, tn as EmotionCacheProvider, tt as ContextAwarePanelItem, u as Slide, un as Ellipsis, v as InstallPackageButton, vn as ArrowDownWideNarrow, vt as TableHead, w as Progress, wt as renderCellValue, x as downloadByURL, xt as NAMELESS_COLUMN_PREFIX, y as ADD_PRINTING_CLASS, yt as TableHeader, z as ContextMenuSeparator, zt as Maps, __tla as __tla_2 } from "./common-iyiGAJwl.js";
|
|
30
30
|
import { c as Calendar, i as createReducerAndAtoms, n as useOnUnmount, o as ToggleLeft, t as useOnMount } from "./useLifecycle-CMJGqBaY.js";
|
|
31
31
|
import { t as Check } from "./check-DP7U0H0G.js";
|
|
32
32
|
import { A as Icon, C as logNever, D as $18f2051aff69b9bf$export$a54013f0d02a8f82, E as $18f2051aff69b9bf$export$43bb16f9c6d9e3f7, F as createCollection, I as X, M as clamp$2, N as usePrevious$2, P as useDirection, R as ChevronDown, S as assertNever, a as SelectGroup, c as SelectSeparator, d as NativeSelect, i as SelectContent, j as Trigger$1, l as SelectTrigger, n as capitalize, o as SelectItem, r as Select, s as SelectLabel, t as Strings, u as SelectValue, w as $a916eb452884faea$export$b7a616150fdb9f44 } from "./strings-DIy9NAmg.js";
|
|
33
33
|
import { B as $64fa3d84918910a7$export$4d86445c2cf5e3, C as DropdownMenuTrigger, Ft as $65484d02dcb7eb3e$export$457c3d6518dd4c6f, It as $3ef42575df84b30b$export$9d1611c77c2fe928, W as $64fa3d84918910a7$export$df3a06d6289f983e, Wt as $ff5963eb1fccf552$export$e08e3b67e392101e, X as useDebouncedCallback, Y as useDebounceControlledState, a as NumberField, d as roundToFractionDigits, f as DropdownMenu, g as DropdownMenuLabel, gn as ChevronRight, h as DropdownMenuItem, hn as Circle, i as OnBlurredInput, l as prettyNumber, m as DropdownMenuGroup, n as DebouncedNumberInput, o as maxFractionDigitsForSteps, ot as $f7dceffc5ad7768b$export$4e328f61c538687f, p as DropdownMenuContent, pt as $6179b936705e76d3$export$ae780daf29e6d456, r as Input, st as $701a24aa0da5b062$export$ea18c227d4417cc3, t as DebouncedInput, u as prettyScientificNumber, v as DropdownMenuSeparator, xt as $458b0a5536c1a7cf$export$40bfa8c7b0832715, y as DropdownMenuShortcut, z as $64fa3d84918910a7$export$29f1550f4b0d4415 } from "./input-C5K4VBvB.js";
|
|
34
34
|
import { S as isWasm, _ as initialModeAtom, b as viewStateAtom, c as asRemoteURL, d as isStaticNotebook, f as appendQueryParams, g as getInitialAppMode, m as require_cuid2, u as getStaticVirtualFiles, v as kioskModeAtom, w as CircleQuestionMark, x as Deferred } from "./toDate-CqhBWjvO.js";
|
|
35
|
-
import { a as MarimoIncomingMessageEvent, c as MarimoValueUpdateEvent,
|
|
35
|
+
import { a as MarimoIncomingMessageEvent, c as MarimoValueUpdateEvent, f as Square, i as PythonIcon, l as createInputEvent, n as blobToString, o as MarimoValueInputEvent, p as File, r as filesToBase64, s as MarimoValueReadyEvent, t as processOutput, u as deserializeBlob } from "./process-output-BRwR4QGs.js";
|
|
36
36
|
import { n as Trash, r as Pencil, t as BulkEdit } from "./types-DicH9Oi0.js";
|
|
37
37
|
import { n as require_prop_types, r as Plus, t as ErrorBoundary } from "./ErrorBoundary-DhLqwSWA.js";
|
|
38
38
|
import { t as require_react_dom } from "./react-dom-BTJzcVJ9.js";
|
|
@@ -9009,7 +9009,7 @@ let __tla = Promise.all([
|
|
|
9009
9009
|
};
|
|
9010
9010
|
}
|
|
9011
9011
|
};
|
|
9012
|
-
var LazyChatbot = import_react.lazy(() => import("./chat-ui-
|
|
9012
|
+
var LazyChatbot = import_react.lazy(() => import("./chat-ui-1e7PcW56.js").then((e) => ({
|
|
9013
9013
|
default: e.Chatbot
|
|
9014
9014
|
}))), messageSchema = array(object({
|
|
9015
9015
|
id: string(),
|
|
@@ -38147,7 +38147,7 @@ ${c}
|
|
|
38147
38147
|
function _temp2$2(e) {
|
|
38148
38148
|
e.target === e.currentTarget && e.key === "Enter" && (e.preventDefault(), e.stopPropagation(), e.currentTarget.click());
|
|
38149
38149
|
}
|
|
38150
|
-
var LazySlidesComponent = import_react.lazy(() => import("./reveal-component-
|
|
38150
|
+
var LazySlidesComponent = import_react.lazy(() => import("./reveal-component-BL7inNNa.js"));
|
|
38151
38151
|
const SlidesLayoutRenderer = ({ layout: e, setLayout: r, cells: c, mode: l }) => {
|
|
38152
38152
|
var _a5;
|
|
38153
38153
|
let u = useAtomValue(kioskModeAtom), d = l === "read" || u, f = useAtomValue(numColumnsAtom) > 1, [p, m] = (0, import_react.useState)(null), { slideCells: h, skippedIds: g, noOutputIds: _, slideTypes: v, startCellIndex: y } = (0, import_react.useMemo)(() => computeSlideCellsInfo(c, e), [
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { s as __toESM } from "./chunk-BNovOVIE.js";
|
|
2
2
|
import { t as require_compiler_runtime } from "./compiler-runtime-CEbnTgxf.js";
|
|
3
|
-
import { ot as ansiToPlainText, st as parseHtmlContent } from "./html-to-image-3w0AakWW.js";
|
|
3
|
+
import { F as base64ToDataURL, ot as ansiToPlainText, st as parseHtmlContent } from "./html-to-image-3w0AakWW.js";
|
|
4
4
|
import { u as createLucideIcon } from "./dist-DIlxLFXG.js";
|
|
5
5
|
import { t as Strings } from "./strings-DIy9NAmg.js";
|
|
6
6
|
import { t as require_jsx_runtime } from "./jsx-runtime-DebpN0FN.js";
|
|
@@ -21,64 +21,67 @@ var File = createLucideIcon("file", [["path", {
|
|
|
21
21
|
}]]);
|
|
22
22
|
function deserializeBlob(e) {
|
|
23
23
|
var _a;
|
|
24
|
-
let [
|
|
25
|
-
for (let e2 = 0; e2 <
|
|
26
|
-
return new Blob([
|
|
24
|
+
let [b, x] = e.split(",", 2), S = (_a = /^data:(.+);base64$/.exec(b)) == null ? void 0 : _a[1], C = atob(x), w = C.length, T = new Uint8Array(w);
|
|
25
|
+
for (let e2 = 0; e2 < w; e2++) T[e2] = C.charCodeAt(e2);
|
|
26
|
+
return new Blob([T], { type: S });
|
|
27
|
+
}
|
|
28
|
+
function fileDetailsToBlob({ contents: e, mimeType: b, isBase64: S }) {
|
|
29
|
+
return S ? deserializeBlob(base64ToDataURL(e, b)) : new Blob([e], { type: b });
|
|
27
30
|
}
|
|
28
31
|
function defineCustomEvent(e) {
|
|
29
32
|
return () => ({
|
|
30
33
|
TYPE: e,
|
|
31
|
-
is(
|
|
32
|
-
return
|
|
34
|
+
is(b) {
|
|
35
|
+
return b.type === e;
|
|
33
36
|
},
|
|
34
|
-
create(
|
|
35
|
-
return new CustomEvent(e,
|
|
37
|
+
create(b) {
|
|
38
|
+
return new CustomEvent(e, b);
|
|
36
39
|
}
|
|
37
40
|
});
|
|
38
41
|
}
|
|
39
42
|
const MarimoValueInputEvent = defineCustomEvent("marimo-value-input")(), MarimoValueUpdateEvent = defineCustomEvent("marimo-value-update")(), MarimoValueReadyEvent = defineCustomEvent("marimo-value-ready")(), MarimoIncomingMessageEvent = defineCustomEvent("marimo-incoming-message")();
|
|
40
|
-
function createInputEvent(e,
|
|
43
|
+
function createInputEvent(e, b) {
|
|
41
44
|
return MarimoValueInputEvent.create({
|
|
42
45
|
bubbles: true,
|
|
43
46
|
composed: true,
|
|
44
47
|
detail: {
|
|
45
48
|
value: e,
|
|
46
|
-
element:
|
|
49
|
+
element: b
|
|
47
50
|
}
|
|
48
51
|
});
|
|
49
52
|
}
|
|
50
53
|
var import_compiler_runtime = require_compiler_runtime(), import_jsx_runtime = /* @__PURE__ */ __toESM(require_jsx_runtime(), 1);
|
|
51
54
|
const PythonIcon = (e) => {
|
|
52
|
-
let
|
|
53
|
-
|
|
54
|
-
let
|
|
55
|
-
return
|
|
55
|
+
let b = (0, import_compiler_runtime.c)(4), x, S;
|
|
56
|
+
b[0] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (x = /* @__PURE__ */ (0, import_jsx_runtime.jsx)("title", { children: "Python Logo" }), S = /* @__PURE__ */ (0, import_jsx_runtime.jsx)("path", { d: "M439.8 200.5c-7.7-30.9-22.3-54.2-53.4-54.2h-40.1v47.4c0 36.8-31.2 67.8-66.8 67.8H172.7c-29.2 0-53.4 25-53.4 54.3v101.8c0 29 25.2 46 53.4 54.3 33.8 9.9 66.3 11.7 106.8 0 26.9-7.8 53.4-23.5 53.4-54.3v-40.7H226.2v-13.6h160.2c31.1 0 42.6-21.7 53.4-54.2 11.2-33.5 10.7-65.7 0-108.6zM286.2 404c11.1 0 20.1 9.1 20.1 20.3 0 11.3-9 20.4-20.1 20.4-11 0-20.1-9.2-20.1-20.4.1-11.3 9.1-20.3 20.1-20.3zM167.8 248.1h106.8c29.7 0 53.4-24.5 53.4-54.3V91.9c0-29-24.4-50.7-53.4-55.6-35.8-5.9-74.7-5.6-106.8.1-45.2 8-53.4 24.7-53.4 55.6v40.7h106.9v13.6h-147c-31.1 0-58.3 18.7-66.8 54.2-9.8 40.7-10.2 66.1 0 108.6 7.6 31.6 25.7 54.2 56.8 54.2H101v-48.8c0-35.3 30.5-66.4 66.8-66.4zm-6.7-142.6c-11.1 0-20.1-9.1-20.1-20.3.1-11.3 9-20.4 20.1-20.4 11 0 20.1 9.2 20.1 20.4s-9 20.3-20.1 20.3z" }), b[0] = x, b[1] = S) : (x = b[0], S = b[1]);
|
|
57
|
+
let C;
|
|
58
|
+
return b[2] === e ? C = b[3] : (C = /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("svg", {
|
|
56
59
|
xmlns: "http://www.w3.org/2000/svg",
|
|
57
60
|
width: "1em",
|
|
58
61
|
height: "1em",
|
|
59
62
|
fill: "currentColor",
|
|
60
63
|
viewBox: "0 0 448 512",
|
|
61
64
|
...e,
|
|
62
|
-
children: [
|
|
63
|
-
}),
|
|
65
|
+
children: [x, S]
|
|
66
|
+
}), b[2] = e, b[3] = C), C;
|
|
64
67
|
};
|
|
65
68
|
var FILE_READ_CONCURRENCY = 5;
|
|
66
|
-
function blobToString(e,
|
|
67
|
-
return new Promise((
|
|
68
|
-
let
|
|
69
|
-
|
|
69
|
+
function blobToString(e, b) {
|
|
70
|
+
return new Promise((x) => {
|
|
71
|
+
let S = new FileReader();
|
|
72
|
+
S.readAsDataURL(e), S.onload = (e2) => {
|
|
70
73
|
var _a;
|
|
71
74
|
if ((_a = e2.target) == null ? void 0 : _a.result) {
|
|
72
|
-
let
|
|
73
|
-
|
|
75
|
+
let S2 = e2.target.result;
|
|
76
|
+
x(b === "base64" ? S2.slice(S2.indexOf(",") + 1) : S2);
|
|
74
77
|
}
|
|
75
78
|
};
|
|
76
79
|
});
|
|
77
80
|
}
|
|
78
81
|
function filesToBase64(e) {
|
|
79
82
|
return mapWithConcurrency(e, FILE_READ_CONCURRENCY, async (e2) => {
|
|
80
|
-
let
|
|
81
|
-
return [e2.name,
|
|
83
|
+
let b = await blobToString(e2, "base64");
|
|
84
|
+
return [e2.name, b];
|
|
82
85
|
});
|
|
83
86
|
}
|
|
84
87
|
function processOutput(e) {
|
|
@@ -87,12 +90,13 @@ function processOutput(e) {
|
|
|
87
90
|
export {
|
|
88
91
|
MarimoIncomingMessageEvent as a,
|
|
89
92
|
MarimoValueUpdateEvent as c,
|
|
90
|
-
|
|
91
|
-
|
|
93
|
+
fileDetailsToBlob as d,
|
|
94
|
+
Square as f,
|
|
92
95
|
PythonIcon as i,
|
|
93
96
|
createInputEvent as l,
|
|
94
97
|
blobToString as n,
|
|
95
98
|
MarimoValueInputEvent as o,
|
|
99
|
+
File as p,
|
|
96
100
|
filesToBase64 as r,
|
|
97
101
|
MarimoValueReadyEvent as s,
|
|
98
102
|
processOutput as t,
|
|
@@ -9,7 +9,7 @@ import { t as require_compiler_runtime } from "./compiler-runtime-CEbnTgxf.js";
|
|
|
9
9
|
import { ut as outputIsStale } from "./html-to-image-3w0AakWW.js";
|
|
10
10
|
import "./chunk-5FQGJX7Z-B9WoXK1R.js";
|
|
11
11
|
import { u as createLucideIcon } from "./dist-DIlxLFXG.js";
|
|
12
|
-
import { a as DEFAULT_DECK_TRANSITION, cn as EyeOff, dt as PanelGroup, fn as Code, ft as PanelResizeHandle, l as SlideSidebar, ln as Expand, n as useNotebookCodeAvailable, o as DEFAULT_DECK_VERTICAL_ALIGN, s as DEFAULT_SLIDE_TYPE, t as cellDomProps, u as Slide, ut as Panel } from "./common-
|
|
12
|
+
import { a as DEFAULT_DECK_TRANSITION, cn as EyeOff, dt as PanelGroup, fn as Code, ft as PanelResizeHandle, l as SlideSidebar, ln as Expand, n as useNotebookCodeAvailable, o as DEFAULT_DECK_VERTICAL_ALIGN, s as DEFAULT_SLIDE_TYPE, t as cellDomProps, u as Slide, ut as Panel } from "./common-iyiGAJwl.js";
|
|
13
13
|
import { R as ChevronDown } from "./strings-DIy9NAmg.js";
|
|
14
14
|
import { X as useDebouncedCallback } from "./input-C5K4VBvB.js";
|
|
15
15
|
import { v as kioskModeAtom } from "./toDate-CqhBWjvO.js";
|
package/package.json
CHANGED
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/* Copyright 2026 Marimo. All rights reserved. */
|
|
2
|
+
import { describe, expect, it } from "vitest";
|
|
3
|
+
import { buildMediaSource } from "../renderers";
|
|
4
|
+
|
|
5
|
+
describe("buildMediaSource", () => {
|
|
6
|
+
it("returns base64 source for binary media", () => {
|
|
7
|
+
expect(
|
|
8
|
+
buildMediaSource({
|
|
9
|
+
contents: "aGVsbG8=",
|
|
10
|
+
mimeType: "image/png",
|
|
11
|
+
isBase64: true,
|
|
12
|
+
}),
|
|
13
|
+
).toEqual({
|
|
14
|
+
base64: "aGVsbG8=",
|
|
15
|
+
mime: "image/png",
|
|
16
|
+
});
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
it("returns UTF-8 data URL for text-based media", () => {
|
|
20
|
+
const svg = '<svg xmlns="http://www.w3.org/2000/svg"></svg>';
|
|
21
|
+
expect(
|
|
22
|
+
buildMediaSource({
|
|
23
|
+
contents: svg,
|
|
24
|
+
mimeType: "image/svg+xml",
|
|
25
|
+
isBase64: false,
|
|
26
|
+
}),
|
|
27
|
+
).toEqual({
|
|
28
|
+
url: `data:image/svg+xml;charset=utf-8,${encodeURIComponent(svg)}`,
|
|
29
|
+
});
|
|
30
|
+
});
|
|
31
|
+
});
|
|
@@ -22,12 +22,11 @@ import { isWasm } from "@/core/wasm/utils";
|
|
|
22
22
|
import { useAsyncData } from "@/hooks/useAsyncData";
|
|
23
23
|
import { ErrorBanner } from "@/plugins/impl/common/error-banner";
|
|
24
24
|
import { copyToClipboard } from "@/utils/copy";
|
|
25
|
-
import type { Base64String } from "@/utils/json/base64";
|
|
26
25
|
import { downloadFile } from "./download";
|
|
27
26
|
import { FilePreviewHeader } from "./file-header";
|
|
28
27
|
import { FilePreviewMetadata } from "./file-preview-metadata";
|
|
29
28
|
import { getFileRenderMode } from "./file-render-mode";
|
|
30
|
-
import { FileContentRenderer } from "./renderers";
|
|
29
|
+
import { buildMediaSource, FileContentRenderer } from "./renderers";
|
|
31
30
|
|
|
32
31
|
export const MAX_FILE_PREVIEW_BYTES = 10 * 1024 * 1024;
|
|
33
32
|
|
|
@@ -226,6 +225,15 @@ export const FileViewer: React.FC<Props> = ({ file, onOpenNotebook }) => {
|
|
|
226
225
|
</Alert>
|
|
227
226
|
);
|
|
228
227
|
|
|
228
|
+
const mediaSource =
|
|
229
|
+
isMedia && data.contents
|
|
230
|
+
? buildMediaSource({
|
|
231
|
+
contents: data.contents,
|
|
232
|
+
mimeType,
|
|
233
|
+
isBase64: data.isBase64 ?? false,
|
|
234
|
+
})
|
|
235
|
+
: undefined;
|
|
236
|
+
|
|
229
237
|
return (
|
|
230
238
|
<>
|
|
231
239
|
{header}
|
|
@@ -239,11 +247,7 @@ export const FileViewer: React.FC<Props> = ({ file, onOpenNotebook }) => {
|
|
|
239
247
|
? (data.contents ?? undefined)
|
|
240
248
|
: undefined
|
|
241
249
|
}
|
|
242
|
-
mediaSource={
|
|
243
|
-
isMedia && data.contents
|
|
244
|
-
? { base64: data.contents as Base64String, mime: mimeType }
|
|
245
|
-
: undefined
|
|
246
|
-
}
|
|
250
|
+
mediaSource={mediaSource}
|
|
247
251
|
readOnly={!isText}
|
|
248
252
|
onChange={isText ? setInternalValue : undefined}
|
|
249
253
|
extensions={isText ? [saveKeymapExtension] : []}
|
|
@@ -60,6 +60,27 @@ function resolveMediaSrc(source: MediaSource): string {
|
|
|
60
60
|
return base64ToDataURL(source.base64, source.mime);
|
|
61
61
|
}
|
|
62
62
|
|
|
63
|
+
/**
|
|
64
|
+
* Build a {@link MediaSource} from file details.
|
|
65
|
+
* Binary media is base64-encoded; text-based media (e.g. SVG) uses a UTF-8 data URL.
|
|
66
|
+
*/
|
|
67
|
+
export function buildMediaSource({
|
|
68
|
+
contents,
|
|
69
|
+
mimeType,
|
|
70
|
+
isBase64,
|
|
71
|
+
}: {
|
|
72
|
+
contents: string;
|
|
73
|
+
mimeType: string;
|
|
74
|
+
isBase64: boolean;
|
|
75
|
+
}): MediaSource {
|
|
76
|
+
if (isBase64) {
|
|
77
|
+
return { base64: contents as Base64String, mime: mimeType };
|
|
78
|
+
}
|
|
79
|
+
return {
|
|
80
|
+
url: `data:${mimeType};charset=utf-8,${encodeURIComponent(contents)}`,
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
|
|
63
84
|
export const CsvViewer: React.FC<{ contents: string }> = ({ contents }) => {
|
|
64
85
|
const data = useMemo(() => parseCsvData(contents), [contents]);
|
|
65
86
|
const [pagination, setPagination] = useState<PaginationState>({
|
|
@@ -10,8 +10,7 @@ import {
|
|
|
10
10
|
import { toast } from "@/components/ui/use-toast";
|
|
11
11
|
import { contextCallbacks } from "@/core/codemirror/ai/state";
|
|
12
12
|
import type { EditRequests, FileInfo, RunRequests } from "@/core/network/types";
|
|
13
|
-
import {
|
|
14
|
-
import { type Base64String, base64ToDataURL } from "@/utils/json/base64";
|
|
13
|
+
import { fileDetailsToBlob } from "@/utils/blob";
|
|
15
14
|
import { Logger } from "@/utils/Logger";
|
|
16
15
|
import { type AIContextItem, AIContextProvider } from "../registry";
|
|
17
16
|
import { contextToXml } from "../utils";
|
|
@@ -219,33 +218,13 @@ export class FileContextProvider extends AIContextProvider<FileContextItem> {
|
|
|
219
218
|
|
|
220
219
|
const mimeType = fileDetails.mimeType || "text/plain";
|
|
221
220
|
|
|
222
|
-
//
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
mimeType
|
|
227
|
-
|
|
228
|
-
)
|
|
229
|
-
// Text files - create blob directly from contents
|
|
230
|
-
blob = new Blob([fileDetails.contents || ""], { type: mimeType });
|
|
231
|
-
} else {
|
|
232
|
-
// Binary files - use blob utility to decode base64
|
|
233
|
-
if (fileDetails.contents) {
|
|
234
|
-
try {
|
|
235
|
-
// Create data URL using utility and deserialize blob
|
|
236
|
-
const dataURL = base64ToDataURL(
|
|
237
|
-
fileDetails.contents as Base64String,
|
|
238
|
-
mimeType,
|
|
239
|
-
);
|
|
240
|
-
blob = deserializeBlob(dataURL);
|
|
241
|
-
} catch {
|
|
242
|
-
// Fallback to treating as text
|
|
243
|
-
blob = new Blob([fileDetails.contents], { type: mimeType });
|
|
244
|
-
}
|
|
245
|
-
} else {
|
|
246
|
-
blob = new Blob([""], { type: mimeType });
|
|
247
|
-
}
|
|
248
|
-
}
|
|
221
|
+
// The backend's `isBase64` flag authoritatively distinguishes binary
|
|
222
|
+
// (base64-encoded) from UTF-8 text contents.
|
|
223
|
+
const blob = fileDetailsToBlob({
|
|
224
|
+
contents: fileDetails.contents ?? "",
|
|
225
|
+
mimeType,
|
|
226
|
+
isBase64: fileDetails.isBase64 ?? false,
|
|
227
|
+
});
|
|
249
228
|
|
|
250
229
|
const file = new File([blob], name, { type: mimeType });
|
|
251
230
|
addAttachment(file);
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
/* Copyright 2026 Marimo. All rights reserved. */
|
|
2
2
|
import { beforeEach, describe, expect, test } from "vitest";
|
|
3
|
-
import { deserializeBlob, serializeBlob } from "../blob";
|
|
3
|
+
import { deserializeBlob, fileDetailsToBlob, serializeBlob } from "../blob";
|
|
4
4
|
import { blobToString } from "../fileToBase64";
|
|
5
5
|
|
|
6
6
|
describe("Blob serialization and deserialization", () => {
|
|
@@ -52,6 +52,32 @@ describe("Blob serialization and deserialization", () => {
|
|
|
52
52
|
});
|
|
53
53
|
});
|
|
54
54
|
|
|
55
|
+
describe("fileDetailsToBlob", () => {
|
|
56
|
+
test("decodes base64 contents into a binary blob", async () => {
|
|
57
|
+
const bytes = new Uint8Array([0, 1, 2, 3, 255]);
|
|
58
|
+
const base64 = btoa(String.fromCharCode(...bytes));
|
|
59
|
+
const blob = fileDetailsToBlob({
|
|
60
|
+
contents: base64,
|
|
61
|
+
mimeType: "image/png",
|
|
62
|
+
isBase64: true,
|
|
63
|
+
});
|
|
64
|
+
expect(blob.type).toBe("image/png");
|
|
65
|
+
const roundTripped = new Uint8Array(await blob.arrayBuffer());
|
|
66
|
+
expect(roundTripped).toEqual(bytes);
|
|
67
|
+
});
|
|
68
|
+
|
|
69
|
+
test("treats non-base64 contents as UTF-8 text", async () => {
|
|
70
|
+
const svg = '<svg xmlns="http://www.w3.org/2000/svg"></svg>';
|
|
71
|
+
const blob = fileDetailsToBlob({
|
|
72
|
+
contents: svg,
|
|
73
|
+
mimeType: "image/svg+xml",
|
|
74
|
+
isBase64: false,
|
|
75
|
+
});
|
|
76
|
+
expect(blob.type).toBe("image/svg+xml");
|
|
77
|
+
expect(await blob.text()).toBe(svg);
|
|
78
|
+
});
|
|
79
|
+
});
|
|
80
|
+
|
|
55
81
|
describe("blobToString", () => {
|
|
56
82
|
const testString = "Hello, world!";
|
|
57
83
|
const mimeType = "text/plain";
|
package/src/utils/blob.ts
CHANGED
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
/* Copyright 2026 Marimo. All rights reserved. */
|
|
2
|
-
import
|
|
2
|
+
import {
|
|
3
|
+
type Base64String,
|
|
4
|
+
base64ToDataURL,
|
|
5
|
+
type DataURLString,
|
|
6
|
+
} from "./json/base64";
|
|
3
7
|
|
|
4
8
|
export function serializeBlob<T>(blob: Blob): Promise<DataURLString> {
|
|
5
9
|
return new Promise<DataURLString>((resolve, reject) => {
|
|
@@ -30,3 +34,22 @@ export function deserializeBlob(serializedBlob: DataURLString): Blob {
|
|
|
30
34
|
const blob = new Blob([bytes], { type: mimeType });
|
|
31
35
|
return blob;
|
|
32
36
|
}
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* Convert file details into a `Blob`, using the authoritative `isBase64` flag
|
|
40
|
+
* to decide between decoding base64 bytes and treating contents as UTF-8 text.
|
|
41
|
+
*/
|
|
42
|
+
export function fileDetailsToBlob({
|
|
43
|
+
contents,
|
|
44
|
+
mimeType,
|
|
45
|
+
isBase64,
|
|
46
|
+
}: {
|
|
47
|
+
contents: string;
|
|
48
|
+
mimeType: string;
|
|
49
|
+
isBase64: boolean;
|
|
50
|
+
}): Blob {
|
|
51
|
+
if (isBase64) {
|
|
52
|
+
return deserializeBlob(base64ToDataURL(contents as Base64String, mimeType));
|
|
53
|
+
}
|
|
54
|
+
return new Blob([contents], { type: mimeType });
|
|
55
|
+
}
|