@rebasepro/studio 0.0.1-canary.eae7889 → 0.1.0
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/{ApiExplorer-gMJt5JrS.js → ApiExplorer-DHVmWYfK.js} +13 -13
- package/dist/ApiExplorer-DHVmWYfK.js.map +1 -0
- package/dist/AuthSimulationSelector-CM488Eei.js +106 -0
- package/dist/AuthSimulationSelector-CM488Eei.js.map +1 -0
- package/dist/{JSEditor-D8nVp3Lp.js → JSEditor-CSHA0t_O.js} +2 -2
- package/dist/{JSEditor-D8nVp3Lp.js.map → JSEditor-CSHA0t_O.js.map} +1 -1
- package/dist/{RLSEditor-DBH09u9v.js → RLSEditor-BzDjqo6w.js} +46 -5
- package/dist/RLSEditor-BzDjqo6w.js.map +1 -0
- package/dist/{SQLEditor-CkVx9vgr.js → SQLEditor-Cr9Kg_Qg.js} +63 -75
- package/dist/SQLEditor-Cr9Kg_Qg.js.map +1 -0
- package/dist/{SchemaVisualizer-BgD5Zb77.js → SchemaVisualizer-BGpmzyXT.js} +5 -5
- package/dist/SchemaVisualizer-BGpmzyXT.js.map +1 -0
- package/dist/StorageView-BYoslzBR.js +870 -0
- package/dist/StorageView-BYoslzBR.js.map +1 -0
- package/dist/core/src/components/BootstrapAdminBanner.d.ts +4 -0
- package/dist/core/src/components/LoginView/LoginView.d.ts +22 -0
- package/dist/core/src/components/common/useDataTableController.d.ts +3 -3
- package/dist/core/src/components/index.d.ts +1 -0
- package/dist/core/src/hooks/data/useRelationSelector.d.ts +2 -2
- package/dist/core/src/hooks/index.d.ts +1 -0
- package/dist/core/src/hooks/useCollapsedGroups.d.ts +16 -1
- package/dist/core/src/hooks/useResolvedComponent.d.ts +47 -0
- package/dist/index.es.js +79 -71
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +821 -834
- package/dist/index.umd.js.map +1 -1
- package/dist/types/src/controllers/auth.d.ts +8 -2
- package/dist/types/src/controllers/client.d.ts +13 -0
- package/dist/types/src/controllers/collection_registry.d.ts +2 -1
- package/dist/types/src/controllers/data_driver.d.ts +36 -1
- package/dist/types/src/controllers/navigation.d.ts +18 -6
- package/dist/types/src/controllers/registry.d.ts +9 -1
- package/dist/types/src/controllers/side_entity_controller.d.ts +7 -0
- package/dist/types/src/rebase_context.d.ts +17 -0
- package/dist/types/src/types/backend_hooks.d.ts +187 -0
- package/dist/types/src/types/collections.d.ts +31 -11
- package/dist/types/src/types/component_ref.d.ts +47 -0
- package/dist/types/src/types/cron.d.ts +1 -1
- package/dist/types/src/types/entity_views.d.ts +6 -7
- package/dist/types/src/types/formex.d.ts +40 -0
- package/dist/types/src/types/index.d.ts +3 -0
- package/dist/types/src/types/plugins.d.ts +6 -3
- package/dist/types/src/types/properties.d.ts +72 -88
- package/dist/types/src/types/slots.d.ts +20 -10
- package/dist/types/src/types/translations.d.ts +6 -0
- package/dist/ui/src/components/FileUpload.d.ts +1 -1
- package/dist/ui/src/components/SearchBar.d.ts +5 -1
- package/dist/ui/src/styles.d.ts +2 -2
- package/package.json +10 -10
- package/src/components/ApiExplorer/ApiExplorer.tsx +7 -5
- package/src/components/ApiExplorer/TryItPanel.tsx +29 -53
- package/src/components/AuthSimulationSelector.tsx +13 -17
- package/src/components/RLSEditor/RLSEditor.tsx +82 -3
- package/src/components/SQLEditor/SQLEditor.tsx +16 -18
- package/src/components/SQLEditor/SchemaBrowser.tsx +6 -8
- package/src/components/SchemaVisualizer/SchemaVisualizer.tsx +20 -22
- package/src/components/StorageView/StorageView.tsx +719 -304
- package/src/components/StudioHomePage.tsx +4 -1
- package/dist/ApiExplorer-gMJt5JrS.js.map +0 -1
- package/dist/AuthSimulationSelector-BF4rkRGp.js +0 -118
- package/dist/AuthSimulationSelector-BF4rkRGp.js.map +0 -1
- package/dist/RLSEditor-DBH09u9v.js.map +0 -1
- package/dist/SQLEditor-CkVx9vgr.js.map +0 -1
- package/dist/SchemaVisualizer-BgD5Zb77.js.map +0 -1
- package/dist/StorageView-CTqGFhY9.js +0 -907
- package/dist/StorageView-CTqGFhY9.js.map +0 -1
package/dist/index.umd.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
(function(global, factory) {
|
|
2
|
-
typeof exports === "object" && typeof module !== "undefined" ? factory(exports, require("@rebasepro/core"), require("react/jsx-runtime"), require("react"), require("@rebasepro/ui"), require("react-compiler-runtime"), require("lucide-react"), require("react-router-dom"), require("react-dom"), require("pgsql-ast-parser"), require("@rebasepro/utils"), require("prism-react-renderer"), require("@rebasepro/client"), require("@monaco-editor/react"), require("@rebasepro/types"), require("@xyflow/react"), require("@xyflow/react/dist/style.css"), require("@rebasepro/common"), require("dagre")) : typeof define === "function" && define.amd ? define(["exports", "@rebasepro/core", "react/jsx-runtime", "react", "@rebasepro/ui", "react-compiler-runtime", "lucide-react", "react-router-dom", "react-dom", "pgsql-ast-parser", "@rebasepro/utils", "prism-react-renderer", "@rebasepro/client", "@monaco-editor/react", "@rebasepro/types", "@xyflow/react", "@xyflow/react/dist/style.css", "@rebasepro/common", "dagre"], factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, factory(global["Rebase collection editor"] = {}, global.core, global.jsxRuntime, global.React, global.ui, global.reactCompilerRuntime, global.lucideReact, global.reactRouterDom, global.reactDom, global.pgsqlAstParser, global.utils, global.prismReactRenderer, global.client, global.Editor, global.types, global.react, null, global.common, global.dagre));
|
|
3
|
-
})(this, (function(exports2, core, jsxRuntime, React, ui, reactCompilerRuntime, lucideReact, reactRouterDom, reactDom, pgsqlAstParser, utils, prismReactRenderer, client, Editor, types, react, style_css, common, dagre) {
|
|
2
|
+
typeof exports === "object" && typeof module !== "undefined" ? factory(exports, require("@rebasepro/core"), require("react/jsx-runtime"), require("react"), require("@rebasepro/ui"), require("react-compiler-runtime"), require("lucide-react"), require("react-router-dom"), require("react-dom"), require("pgsql-ast-parser"), require("@rebasepro/utils"), require("prism-react-renderer"), require("@rebasepro/client"), require("@monaco-editor/react"), require("@rebasepro/types"), require("react-dropzone"), require("@xyflow/react"), require("@xyflow/react/dist/style.css"), require("@rebasepro/common"), require("dagre")) : typeof define === "function" && define.amd ? define(["exports", "@rebasepro/core", "react/jsx-runtime", "react", "@rebasepro/ui", "react-compiler-runtime", "lucide-react", "react-router-dom", "react-dom", "pgsql-ast-parser", "@rebasepro/utils", "prism-react-renderer", "@rebasepro/client", "@monaco-editor/react", "@rebasepro/types", "react-dropzone", "@xyflow/react", "@xyflow/react/dist/style.css", "@rebasepro/common", "dagre"], factory) : (global = typeof globalThis !== "undefined" ? globalThis : global || self, factory(global["Rebase collection editor"] = {}, global.core, global.jsxRuntime, global.React, global.ui, global.reactCompilerRuntime, global.lucideReact, global.reactRouterDom, global.reactDom, global.pgsqlAstParser, global.utils, global.prismReactRenderer, global.client, global.Editor, global.types, global.reactDropzone, global.react, null, global.common, global.dagre));
|
|
3
|
+
})(this, (function(exports2, core, jsxRuntime, React, ui, reactCompilerRuntime, lucideReact, reactRouterDom, reactDom, pgsqlAstParser, utils, prismReactRenderer, client, Editor, types, reactDropzone, react, style_css, common, dagre) {
|
|
4
4
|
"use strict";
|
|
5
5
|
const SECTIONS = [{
|
|
6
6
|
label: "Database",
|
|
@@ -84,7 +84,7 @@
|
|
|
84
84
|
}]
|
|
85
85
|
}];
|
|
86
86
|
function StudioHomePage(t0) {
|
|
87
|
-
const $ = reactCompilerRuntime.c(
|
|
87
|
+
const $ = reactCompilerRuntime.c(30);
|
|
88
88
|
const {
|
|
89
89
|
additionalActions,
|
|
90
90
|
additionalChildrenStart,
|
|
@@ -131,20 +131,27 @@
|
|
|
131
131
|
const sectionProps = t3;
|
|
132
132
|
const pluginActions = core.useSlot("home.actions", sectionProps);
|
|
133
133
|
let t4;
|
|
134
|
-
if ($[6]
|
|
135
|
-
t4 =
|
|
134
|
+
if ($[6] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
135
|
+
t4 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "mb-4", children: /* @__PURE__ */ jsxRuntime.jsx(core.BootstrapAdminBanner, {}) });
|
|
136
|
+
$[6] = t4;
|
|
137
|
+
} else {
|
|
138
|
+
t4 = $[6];
|
|
139
|
+
}
|
|
140
|
+
let t5;
|
|
141
|
+
if ($[7] !== additionalActions || $[8] !== pluginActions) {
|
|
142
|
+
t5 = (additionalActions || pluginActions) && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "w-full sticky py-4 transition-all duration-400 ease-in-out top-0 z-10 flex flex-row gap-4 justify-end", children: [
|
|
136
143
|
additionalActions,
|
|
137
144
|
pluginActions
|
|
138
145
|
] });
|
|
139
|
-
$[
|
|
140
|
-
$[
|
|
141
|
-
$[
|
|
146
|
+
$[7] = additionalActions;
|
|
147
|
+
$[8] = pluginActions;
|
|
148
|
+
$[9] = t5;
|
|
142
149
|
} else {
|
|
143
|
-
|
|
150
|
+
t5 = $[9];
|
|
144
151
|
}
|
|
145
|
-
let
|
|
146
|
-
if ($[
|
|
147
|
-
|
|
152
|
+
let t6;
|
|
153
|
+
if ($[10] !== context || $[11] !== navigate) {
|
|
154
|
+
t6 = SECTIONS.map((section) => /* @__PURE__ */ jsxRuntime.jsxs("section", { "aria-label": section.label, children: [
|
|
148
155
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", component: "h2", color: "secondary", className: "py-2 font-medium uppercase text-sm text-surface-600 dark:text-surface-400", children: section.label }),
|
|
149
156
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-3 mt-2", children: section.tools.map((tool) => /* @__PURE__ */ jsxRuntime.jsx(ui.Card, { onClick: () => {
|
|
150
157
|
navigate(tool.path);
|
|
@@ -166,43 +173,43 @@
|
|
|
166
173
|
}, children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "p-2", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ArrowRightIcon, { className: "text-primary", size: ui.iconSize.small }) }) })
|
|
167
174
|
] }) }, tool.path)) })
|
|
168
175
|
] }, section.label));
|
|
169
|
-
$[
|
|
170
|
-
$[
|
|
171
|
-
$[
|
|
172
|
-
} else {
|
|
173
|
-
t5 = $[11];
|
|
174
|
-
}
|
|
175
|
-
let t6;
|
|
176
|
-
if ($[12] !== t5) {
|
|
177
|
-
t6 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-col gap-8 pt-2", children: t5 });
|
|
178
|
-
$[12] = t5;
|
|
179
|
-
$[13] = t6;
|
|
176
|
+
$[10] = context;
|
|
177
|
+
$[11] = navigate;
|
|
178
|
+
$[12] = t6;
|
|
180
179
|
} else {
|
|
181
|
-
t6 = $[
|
|
180
|
+
t6 = $[12];
|
|
182
181
|
}
|
|
183
182
|
let t7;
|
|
184
|
-
if ($[
|
|
185
|
-
t7 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex
|
|
183
|
+
if ($[13] !== t6) {
|
|
184
|
+
t7 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-col gap-8 pt-2", children: t6 });
|
|
185
|
+
$[13] = t6;
|
|
186
186
|
$[14] = t7;
|
|
187
187
|
} else {
|
|
188
188
|
t7 = $[14];
|
|
189
189
|
}
|
|
190
190
|
let t8;
|
|
191
191
|
if ($[15] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
192
|
-
t8 = /* @__PURE__ */ jsxRuntime.
|
|
192
|
+
t8 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center mb-1", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", component: "h2", color: "secondary", className: "py-2 font-medium uppercase text-sm text-surface-600 dark:text-surface-400", children: "Quick Start" }) });
|
|
193
|
+
$[15] = t8;
|
|
194
|
+
} else {
|
|
195
|
+
t8 = $[15];
|
|
196
|
+
}
|
|
197
|
+
let t9;
|
|
198
|
+
if ($[16] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
199
|
+
t9 = /* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "body2", color: "secondary", className: "mb-4 max-w-2xl", children: [
|
|
193
200
|
"Generate a fully-typed SDK from your collections with",
|
|
194
201
|
" ",
|
|
195
202
|
/* @__PURE__ */ jsxRuntime.jsx("code", { className: "text-emerald-400 font-mono text-xs bg-emerald-400/10 px-1.5 py-0.5 rounded", children: "npx rebase generate-sdk" }),
|
|
196
203
|
" ",
|
|
197
204
|
"and start querying your data with full TypeScript autocompletion."
|
|
198
205
|
] });
|
|
199
|
-
$[
|
|
206
|
+
$[16] = t9;
|
|
200
207
|
} else {
|
|
201
|
-
|
|
208
|
+
t9 = $[16];
|
|
202
209
|
}
|
|
203
|
-
let
|
|
204
|
-
if ($[
|
|
205
|
-
|
|
210
|
+
let t10;
|
|
211
|
+
if ($[17] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
212
|
+
t10 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center justify-between px-4 py-2.5 border-b border-surface-200/40 dark:border-surface-700/40 bg-surface-50 dark:bg-surface-900/80", children: [
|
|
206
213
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2.5", children: [
|
|
207
214
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex gap-1.5", children: [
|
|
208
215
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "w-2.5 h-2.5 rounded-full bg-red-400/60" }),
|
|
@@ -213,63 +220,64 @@
|
|
|
213
220
|
] }),
|
|
214
221
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs font-mono text-surface-400 dark:text-surface-500", children: "TypeScript" })
|
|
215
222
|
] });
|
|
216
|
-
$[
|
|
223
|
+
$[17] = t10;
|
|
217
224
|
} else {
|
|
218
|
-
|
|
225
|
+
t10 = $[17];
|
|
219
226
|
}
|
|
220
|
-
let
|
|
221
|
-
if ($[
|
|
222
|
-
|
|
223
|
-
t7,
|
|
227
|
+
let t11;
|
|
228
|
+
if ($[18] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
229
|
+
t11 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "mt-10 mb-6", children: [
|
|
224
230
|
t8,
|
|
231
|
+
t9,
|
|
225
232
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "rounded-lg border border-surface-200/40 dark:border-surface-700/40 bg-white dark:bg-surface-950 overflow-hidden", children: [
|
|
226
|
-
|
|
233
|
+
t10,
|
|
227
234
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "px-5 py-4 overflow-x-auto text-[13px] leading-6 font-mono", children: /* @__PURE__ */ jsxRuntime.jsx(SyntaxHighlightedSnippet, {}) })
|
|
228
235
|
] })
|
|
229
236
|
] });
|
|
230
|
-
$[
|
|
237
|
+
$[18] = t11;
|
|
231
238
|
} else {
|
|
232
|
-
|
|
239
|
+
t11 = $[18];
|
|
233
240
|
}
|
|
234
|
-
let
|
|
235
|
-
if ($[
|
|
236
|
-
|
|
237
|
-
$[
|
|
238
|
-
$[
|
|
241
|
+
let t12;
|
|
242
|
+
if ($[19] !== sections) {
|
|
243
|
+
t12 = sections?.map(_temp$7);
|
|
244
|
+
$[19] = sections;
|
|
245
|
+
$[20] = t12;
|
|
239
246
|
} else {
|
|
240
|
-
|
|
247
|
+
t12 = $[20];
|
|
241
248
|
}
|
|
242
|
-
let
|
|
243
|
-
if ($[
|
|
244
|
-
|
|
249
|
+
let t13;
|
|
250
|
+
if ($[21] !== additionalChildrenEnd || $[22] !== additionalChildrenStart || $[23] !== t12 || $[24] !== t5 || $[25] !== t7) {
|
|
251
|
+
t13 = /* @__PURE__ */ jsxRuntime.jsxs(ui.Container, { maxWidth: "6xl", children: [
|
|
245
252
|
t4,
|
|
253
|
+
t5,
|
|
246
254
|
additionalChildrenStart,
|
|
247
|
-
|
|
248
|
-
t10,
|
|
255
|
+
t7,
|
|
249
256
|
t11,
|
|
257
|
+
t12,
|
|
250
258
|
additionalChildrenEnd
|
|
251
259
|
] });
|
|
252
|
-
$[
|
|
253
|
-
$[
|
|
254
|
-
$[
|
|
255
|
-
$[
|
|
256
|
-
$[
|
|
257
|
-
$[
|
|
260
|
+
$[21] = additionalChildrenEnd;
|
|
261
|
+
$[22] = additionalChildrenStart;
|
|
262
|
+
$[23] = t12;
|
|
263
|
+
$[24] = t5;
|
|
264
|
+
$[25] = t7;
|
|
265
|
+
$[26] = t13;
|
|
258
266
|
} else {
|
|
259
|
-
|
|
267
|
+
t13 = $[26];
|
|
260
268
|
}
|
|
261
|
-
let
|
|
262
|
-
if ($[
|
|
263
|
-
|
|
264
|
-
$[
|
|
265
|
-
$[27] = t12;
|
|
269
|
+
let t14;
|
|
270
|
+
if ($[27] !== containerRef || $[28] !== t13) {
|
|
271
|
+
t14 = /* @__PURE__ */ jsxRuntime.jsx("div", { ref: containerRef, className: "py-2 overflow-auto h-full w-full", children: t13 });
|
|
272
|
+
$[27] = containerRef;
|
|
266
273
|
$[28] = t13;
|
|
274
|
+
$[29] = t14;
|
|
267
275
|
} else {
|
|
268
|
-
|
|
276
|
+
t14 = $[29];
|
|
269
277
|
}
|
|
270
|
-
return
|
|
278
|
+
return t14;
|
|
271
279
|
}
|
|
272
|
-
function _temp$
|
|
280
|
+
function _temp$7(s) {
|
|
273
281
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "my-10", children: [
|
|
274
282
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", component: "h2", color: "secondary", className: "p-4 py-2 rounded font-medium uppercase text-sm text-surface-600 dark:text-surface-400", children: s.title }),
|
|
275
283
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "mt-4", children: s.children })
|
|
@@ -897,12 +905,12 @@
|
|
|
897
905
|
/* @__PURE__ */ jsxRuntime.jsx("svg", { className: ui.cls("w-3 h-3 mr-1 transition-transform shrink-0", expandedTables[`${schemaName}.${table.tableName}`] ? "rotate-90" : ""), fill: "currentColor", viewBox: "0 0 20 20", children: /* @__PURE__ */ jsxRuntime.jsx("path", { d: "M7.293 14.707a1 1 0 010-1.414L10.586 10 7.293 6.707a1 1 0 011.414-1.414l4 4a1 1 0 010 1.414l-4 4a1 1 0 01-1.414 0z" }) }),
|
|
898
906
|
/* @__PURE__ */ jsxRuntime.jsx("svg", { className: "w-3.5 h-3.5 mr-1 shrink-0 text-text-disabled dark:text-text-disabled-dark", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ jsxRuntime.jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M3 10h18M3 14h18m-9-4v8m-7 0h14a2 2 0 002-2V8a2 2 0 00-2-2H5a2 2 0 00-2 2v10a2 2 0 002 2z" }) }),
|
|
899
907
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-text-secondary dark:text-text-secondary-dark text-xs truncate flex-1 min-w-0", children: table.tableName }),
|
|
900
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex opacity-0 group-hover:opacity-100 focus-within:opacity-100 absolute right-1 items-center bg-surface-100 dark:bg-surface-
|
|
901
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "
|
|
908
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex opacity-0 group-hover:opacity-100 focus-within:opacity-100 absolute right-1 items-center bg-surface-100 dark:bg-surface-800 px-1 gap-1 rounded transition-opacity", children: [
|
|
909
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: (e) => {
|
|
902
910
|
e.stopPropagation();
|
|
903
911
|
navigator.clipboard.writeText(table.tableName);
|
|
904
|
-
}, title: "CopyIcon table name", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CopyIcon, { size: ui.iconSize.
|
|
905
|
-
/* @__PURE__ */ jsxRuntime.jsxs(ui.Menu, { trigger: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "
|
|
912
|
+
}, title: "CopyIcon table name", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CopyIcon, { size: ui.iconSize.small }) }),
|
|
913
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Menu, { trigger: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: (e_0) => e_0.stopPropagation(), title: "Generate SQL templates", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MoreVerticalIcon, { size: ui.iconSize.small }) }), children: [
|
|
906
914
|
/* @__PURE__ */ jsxRuntime.jsx(ui.MenuItem, { dense: true, className: "text-xs", onClick: (e_1) => {
|
|
907
915
|
e_1.stopPropagation();
|
|
908
916
|
onTableClick?.(`SELECT * FROM ${schemaName !== "public" ? `${schemaName}.` : ""}${table.tableName} LIMIT 100;`);
|
|
@@ -939,7 +947,7 @@ WHERE id = ?;`);
|
|
|
939
947
|
/* @__PURE__ */ jsxRuntime.jsx("svg", { className: "w-3 h-3 mr-1.5 text-text-disabled dark:text-text-disabled-dark shrink-0", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ jsxRuntime.jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 1.5, d: "M9 4.5v15m6-15v15m-10.5-1.5h15c.621 0 1.125-.504 1.125-1.125V5.625c0-.621-.504-1.125-1.125-1.125h-15c-.621 0-1.125.504-1.125 1.125v12.75c0 .621.504 1.125 1.125 1.125Z" }) }),
|
|
940
948
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-primary dark:text-text-primary-dark text-[11px] truncate flex-grow mr-2", children: col.name }),
|
|
941
949
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark text-[9px] truncate mr-1 uppercase shrink-0", title: col.dataType, children: col.dataType }),
|
|
942
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "smallest", className: "opacity-0 group-hover:opacity-100 absolute right-1 bg-surface-50 dark:bg-surface-
|
|
950
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "smallest", className: "opacity-0 group-hover:opacity-100 absolute right-1 bg-surface-50 dark:bg-surface-800 transition-colors pointer-events-auto", onClick: (e_6) => {
|
|
943
951
|
e_6.stopPropagation();
|
|
944
952
|
navigator.clipboard.writeText(col.name);
|
|
945
953
|
}, title: "CopyIcon column name", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CopyIcon, { size: ui.iconSize.smallest }) })
|
|
@@ -1520,7 +1528,7 @@ WHERE id = ?;`);
|
|
|
1520
1528
|
}
|
|
1521
1529
|
let t37;
|
|
1522
1530
|
if ($[67] !== expanded || $[68] !== hasChildren || $[69] !== plan.Plans) {
|
|
1523
|
-
t37 = expanded && hasChildren && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-col space-y-2 mt-[-4px]", children: plan.Plans.map(_temp$
|
|
1531
|
+
t37 = expanded && hasChildren && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-col space-y-2 mt-[-4px]", children: plan.Plans.map(_temp$6) });
|
|
1524
1532
|
$[67] = expanded;
|
|
1525
1533
|
$[68] = hasChildren;
|
|
1526
1534
|
$[69] = plan.Plans;
|
|
@@ -1547,7 +1555,7 @@ WHERE id = ?;`);
|
|
|
1547
1555
|
}
|
|
1548
1556
|
return t38;
|
|
1549
1557
|
};
|
|
1550
|
-
function _temp$
|
|
1558
|
+
function _temp$6(childPlan, idx) {
|
|
1551
1559
|
return /* @__PURE__ */ jsxRuntime.jsx(ExplainVisualizer, { plan: childPlan, isRoot: false }, idx);
|
|
1552
1560
|
}
|
|
1553
1561
|
let VirtualTableInput = null;
|
|
@@ -1559,7 +1567,7 @@ WHERE id = ?;`);
|
|
|
1559
1567
|
const STORAGE_KEY_TABS = "rebase_sql_tabs";
|
|
1560
1568
|
const STORAGE_KEY_ACTIVE_TAB = "rebase_sql_active_tab";
|
|
1561
1569
|
const FixedEditorOverlay = (t0) => {
|
|
1562
|
-
const $ = reactCompilerRuntime.c(
|
|
1570
|
+
const $ = reactCompilerRuntime.c(26);
|
|
1563
1571
|
const {
|
|
1564
1572
|
displayValue,
|
|
1565
1573
|
onSave,
|
|
@@ -1650,90 +1658,70 @@ WHERE id = ?;`);
|
|
|
1650
1658
|
t7 = $[9];
|
|
1651
1659
|
}
|
|
1652
1660
|
let t8;
|
|
1653
|
-
if ($[10]
|
|
1661
|
+
if ($[10] !== resolvedMaxHeight) {
|
|
1654
1662
|
t8 = {
|
|
1655
|
-
minHeight: "32px"
|
|
1663
|
+
minHeight: "32px",
|
|
1664
|
+
maxHeight: resolvedMaxHeight
|
|
1656
1665
|
};
|
|
1657
|
-
$[10] =
|
|
1666
|
+
$[10] = resolvedMaxHeight;
|
|
1667
|
+
$[11] = t8;
|
|
1658
1668
|
} else {
|
|
1659
|
-
t8 = $[
|
|
1669
|
+
t8 = $[11];
|
|
1660
1670
|
}
|
|
1661
1671
|
let t10;
|
|
1662
1672
|
let t9;
|
|
1663
|
-
if ($[
|
|
1664
|
-
t9 = (
|
|
1665
|
-
|
|
1666
|
-
e.target.value = "";
|
|
1667
|
-
e.target.value = val;
|
|
1668
|
-
e.target.style.height = "auto";
|
|
1669
|
-
e.target.style.height = `${Math.min(e.target.scrollHeight, resolvedMaxHeight)}px`;
|
|
1670
|
-
};
|
|
1671
|
-
t10 = (e_0) => {
|
|
1672
|
-
e_0.target.style.height = "auto";
|
|
1673
|
-
e_0.target.style.height = `${Math.min(e_0.target.scrollHeight, resolvedMaxHeight)}px`;
|
|
1674
|
-
};
|
|
1675
|
-
$[11] = resolvedMaxHeight;
|
|
1676
|
-
$[12] = t10;
|
|
1677
|
-
$[13] = t9;
|
|
1678
|
-
} else {
|
|
1679
|
-
t10 = $[12];
|
|
1680
|
-
t9 = $[13];
|
|
1681
|
-
}
|
|
1682
|
-
let t11;
|
|
1683
|
-
let t12;
|
|
1684
|
-
if ($[14] !== onCancel || $[15] !== onSave) {
|
|
1685
|
-
t11 = (e_1) => {
|
|
1686
|
-
onSave(e_1.target.value || null);
|
|
1673
|
+
if ($[12] !== onCancel || $[13] !== onSave) {
|
|
1674
|
+
t9 = (e_0) => {
|
|
1675
|
+
onSave(e_0.target.value || null);
|
|
1687
1676
|
onCancel();
|
|
1688
1677
|
};
|
|
1689
|
-
|
|
1690
|
-
if (
|
|
1691
|
-
|
|
1692
|
-
onSave(
|
|
1678
|
+
t10 = (e_1) => {
|
|
1679
|
+
if (e_1.key === "Enter" && !e_1.shiftKey) {
|
|
1680
|
+
e_1.preventDefault();
|
|
1681
|
+
onSave(e_1.currentTarget.value || null);
|
|
1693
1682
|
onCancel();
|
|
1694
1683
|
}
|
|
1695
|
-
if (
|
|
1684
|
+
if (e_1.key === "Escape") {
|
|
1696
1685
|
onCancel();
|
|
1697
1686
|
}
|
|
1698
1687
|
};
|
|
1699
|
-
$[
|
|
1700
|
-
$[
|
|
1701
|
-
$[
|
|
1702
|
-
$[
|
|
1688
|
+
$[12] = onCancel;
|
|
1689
|
+
$[13] = onSave;
|
|
1690
|
+
$[14] = t10;
|
|
1691
|
+
$[15] = t9;
|
|
1703
1692
|
} else {
|
|
1704
|
-
|
|
1705
|
-
|
|
1693
|
+
t10 = $[14];
|
|
1694
|
+
t9 = $[15];
|
|
1706
1695
|
}
|
|
1707
|
-
let
|
|
1708
|
-
if ($[
|
|
1709
|
-
|
|
1710
|
-
$[
|
|
1711
|
-
$[
|
|
1696
|
+
let t11;
|
|
1697
|
+
if ($[16] !== displayValue || $[17] !== t10 || $[18] !== t8 || $[19] !== t9) {
|
|
1698
|
+
t11 = /* @__PURE__ */ jsxRuntime.jsx(ui.TextareaAutosize, { className: "w-full h-full bg-transparent outline-none border-none ring-0 font-mono text-[13px] text-text-primary dark:text-text-primary-dark px-4 py-1.5 resize-none overflow-y-auto", defaultValue: displayValue, autoFocus: true, style: t8, onFocus: _temp$5, onBlur: t9, onKeyDown: t10 });
|
|
1699
|
+
$[16] = displayValue;
|
|
1700
|
+
$[17] = t10;
|
|
1701
|
+
$[18] = t8;
|
|
1702
|
+
$[19] = t9;
|
|
1712
1703
|
$[20] = t11;
|
|
1713
|
-
$[21] = t12;
|
|
1714
|
-
$[22] = t9;
|
|
1715
|
-
$[23] = t13;
|
|
1716
1704
|
} else {
|
|
1717
|
-
|
|
1705
|
+
t11 = $[20];
|
|
1718
1706
|
}
|
|
1719
|
-
let
|
|
1720
|
-
if ($[
|
|
1721
|
-
|
|
1722
|
-
$[
|
|
1723
|
-
$[
|
|
1724
|
-
$[
|
|
1707
|
+
let t12;
|
|
1708
|
+
if ($[21] !== t11 || $[22] !== t7) {
|
|
1709
|
+
t12 = reactDom.createPortal(/* @__PURE__ */ jsxRuntime.jsx("div", { className: "fixed z-[9999] bg-surface-50 dark:bg-surface-900 border-2 border-primary dark:border-primary-dark shadow-xl flex flex-col", style: t7, children: t11 }), document.body);
|
|
1710
|
+
$[21] = t11;
|
|
1711
|
+
$[22] = t7;
|
|
1712
|
+
$[23] = t12;
|
|
1725
1713
|
} else {
|
|
1726
|
-
|
|
1714
|
+
t12 = $[23];
|
|
1727
1715
|
}
|
|
1728
|
-
let
|
|
1729
|
-
if ($[
|
|
1730
|
-
|
|
1731
|
-
$[
|
|
1732
|
-
$[
|
|
1716
|
+
let t13;
|
|
1717
|
+
if ($[24] !== t12) {
|
|
1718
|
+
t13 = /* @__PURE__ */ jsxRuntime.jsx("div", { ref: anchorRef, className: "w-full h-full min-h-[20px]", children: t12 });
|
|
1719
|
+
$[24] = t12;
|
|
1720
|
+
$[25] = t13;
|
|
1733
1721
|
} else {
|
|
1734
|
-
|
|
1722
|
+
t13 = $[25];
|
|
1735
1723
|
}
|
|
1736
|
-
return
|
|
1724
|
+
return t13;
|
|
1737
1725
|
};
|
|
1738
1726
|
const SQLEditor = () => {
|
|
1739
1727
|
const {
|
|
@@ -2568,12 +2556,15 @@ WHERE id = ?;`);
|
|
|
2568
2556
|
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: handleAddTab, className: "ml-2 flex-shrink-0", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.PlusIcon, { size: ui.iconSize.smallest }) })
|
|
2569
2557
|
] }) }),
|
|
2570
2558
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex shrink-0 items-center justify-end pr-2 gap-1.5", children: [
|
|
2571
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: t("studio_sql_format_sql"), children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: handlePrettify,
|
|
2559
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: t("studio_sql_format_sql"), children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: handlePrettify, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MenuIcon, { size: ui.iconSize.smallest }) }) }),
|
|
2572
2560
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", size: "small", onClick: handleExplain, disabled: loading, children: t("studio_sql_explain") }),
|
|
2573
2561
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-4 w-px bg-surface-200 dark:bg-surface-950 mx-1" }),
|
|
2574
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center space-x-2 px-2
|
|
2562
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center space-x-2 px-2", onClick: (e_14) => {
|
|
2563
|
+
setAutoLimit(!autoLimit);
|
|
2564
|
+
e_14.stopPropagation();
|
|
2565
|
+
}, children: [
|
|
2575
2566
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-[11px] text-text-secondary cursor-pointer select-none", children: t("studio_sql_limit_1000") }),
|
|
2576
|
-
/* @__PURE__ */ jsxRuntime.jsx("
|
|
2567
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { onClick: (e_15) => e_15.stopPropagation(), children: /* @__PURE__ */ jsxRuntime.jsx(ui.Checkbox, { checked: autoLimit, onCheckedChange: setAutoLimit, size: "smallest", padding: false }) })
|
|
2577
2568
|
] }),
|
|
2578
2569
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-4 w-px bg-surface-200 dark:bg-surface-950 mx-1" }),
|
|
2579
2570
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: isFavorite ? t("studio_sql_remove_from_favorites") : t("studio_sql_add_to_favorites"), children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => {
|
|
@@ -2638,6 +2629,11 @@ WHERE id = ?;`);
|
|
|
2638
2629
|
} })
|
|
2639
2630
|
] });
|
|
2640
2631
|
};
|
|
2632
|
+
function _temp$5(e) {
|
|
2633
|
+
const val = e.target.value;
|
|
2634
|
+
e.target.value = "";
|
|
2635
|
+
e.target.value = val;
|
|
2636
|
+
}
|
|
2641
2637
|
const SQLEditor$1 = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2642
2638
|
__proto__: null,
|
|
2643
2639
|
SQLEditor
|
|
@@ -3269,7 +3265,7 @@ return result;`);
|
|
|
3269
3265
|
return t8;
|
|
3270
3266
|
}
|
|
3271
3267
|
function AuthSimulationSelector(t0) {
|
|
3272
|
-
const $ = reactCompilerRuntime.c(
|
|
3268
|
+
const $ = reactCompilerRuntime.c(25);
|
|
3273
3269
|
const {
|
|
3274
3270
|
authMode,
|
|
3275
3271
|
setAuthMode,
|
|
@@ -3290,77 +3286,65 @@ return result;`);
|
|
|
3290
3286
|
t1 = $[0];
|
|
3291
3287
|
t2 = $[1];
|
|
3292
3288
|
}
|
|
3293
|
-
|
|
3289
|
+
const t3 = authMode === "jwt" ? "outlined" : "outlined";
|
|
3290
|
+
const t4 = authMode === "jwt" ? "primary" : "neutral";
|
|
3291
|
+
let t5;
|
|
3294
3292
|
if ($[2] !== setAuthMode) {
|
|
3295
|
-
|
|
3293
|
+
t5 = () => setAuthMode("jwt");
|
|
3296
3294
|
$[2] = setAuthMode;
|
|
3297
|
-
$[3] =
|
|
3295
|
+
$[3] = t5;
|
|
3298
3296
|
} else {
|
|
3299
|
-
|
|
3300
|
-
}
|
|
3301
|
-
const t4 = authMode === "jwt" ? "bg-primary/15 text-primary dark:text-primary-dark border-primary/30 font-medium" : "border-surface-300 dark:border-surface-600 text-text-secondary dark:text-text-secondary-dark hover:border-primary/30";
|
|
3302
|
-
let t5;
|
|
3303
|
-
if ($[4] !== t4) {
|
|
3304
|
-
t5 = ui.cls("px-3 py-1 text-xs rounded-full border transition-all", t4);
|
|
3305
|
-
$[4] = t4;
|
|
3306
|
-
$[5] = t5;
|
|
3307
|
-
} else {
|
|
3308
|
-
t5 = $[5];
|
|
3297
|
+
t5 = $[3];
|
|
3309
3298
|
}
|
|
3310
3299
|
let t6;
|
|
3311
|
-
if ($[
|
|
3312
|
-
t6 = /* @__PURE__ */ jsxRuntime.jsx("
|
|
3313
|
-
$[
|
|
3314
|
-
$[
|
|
3315
|
-
$[
|
|
3316
|
-
|
|
3317
|
-
t6 = $[8];
|
|
3318
|
-
}
|
|
3319
|
-
let t7;
|
|
3320
|
-
if ($[9] !== setAuthMode) {
|
|
3321
|
-
t7 = () => setAuthMode("none");
|
|
3322
|
-
$[9] = setAuthMode;
|
|
3323
|
-
$[10] = t7;
|
|
3300
|
+
if ($[4] !== t3 || $[5] !== t4 || $[6] !== t5) {
|
|
3301
|
+
t6 = /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "small", variant: t3, color: t4, onClick: t5, className: "rounded-full !px-3 !py-1 !text-xs", children: "JWT Token" });
|
|
3302
|
+
$[4] = t3;
|
|
3303
|
+
$[5] = t4;
|
|
3304
|
+
$[6] = t5;
|
|
3305
|
+
$[7] = t6;
|
|
3324
3306
|
} else {
|
|
3325
|
-
|
|
3307
|
+
t6 = $[7];
|
|
3326
3308
|
}
|
|
3327
|
-
const
|
|
3309
|
+
const t7 = authMode === "none" ? "outlined" : "outlined";
|
|
3310
|
+
const t8 = authMode === "none" ? "error" : "neutral";
|
|
3328
3311
|
let t9;
|
|
3329
|
-
if ($[
|
|
3330
|
-
t9 =
|
|
3331
|
-
$[
|
|
3332
|
-
$[
|
|
3312
|
+
if ($[8] !== setAuthMode) {
|
|
3313
|
+
t9 = () => setAuthMode("none");
|
|
3314
|
+
$[8] = setAuthMode;
|
|
3315
|
+
$[9] = t9;
|
|
3333
3316
|
} else {
|
|
3334
|
-
t9 = $[
|
|
3317
|
+
t9 = $[9];
|
|
3335
3318
|
}
|
|
3336
3319
|
let t10;
|
|
3337
|
-
if ($[
|
|
3338
|
-
t10 = /* @__PURE__ */ jsxRuntime.jsx("
|
|
3339
|
-
$[
|
|
3340
|
-
$[
|
|
3341
|
-
$[
|
|
3320
|
+
if ($[10] !== t7 || $[11] !== t8 || $[12] !== t9) {
|
|
3321
|
+
t10 = /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "small", variant: t7, color: t8, onClick: t9, className: "rounded-full !px-3 !py-1 !text-xs", children: "No Auth" });
|
|
3322
|
+
$[10] = t7;
|
|
3323
|
+
$[11] = t8;
|
|
3324
|
+
$[12] = t9;
|
|
3325
|
+
$[13] = t10;
|
|
3342
3326
|
} else {
|
|
3343
|
-
t10 = $[
|
|
3327
|
+
t10 = $[13];
|
|
3344
3328
|
}
|
|
3345
3329
|
let t11;
|
|
3346
|
-
if ($[
|
|
3330
|
+
if ($[14] !== authMode || $[15] !== currentUser || $[16] !== loading || $[17] !== selectedUser || $[18] !== setSelectedUser || $[19] !== users) {
|
|
3347
3331
|
t11 = authMode === "jwt" && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
3348
3332
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-px h-4 bg-surface-300 dark:bg-surface-600 mx-1" }),
|
|
3349
3333
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark text-xs font-medium", children: "Run as:" }),
|
|
3350
3334
|
/* @__PURE__ */ jsxRuntime.jsx(core.UserSelectPopover, { selectedUser, onUserSelected: setSelectedUser, users, loading, currentUser })
|
|
3351
3335
|
] });
|
|
3352
|
-
$[
|
|
3353
|
-
$[
|
|
3354
|
-
$[
|
|
3355
|
-
$[
|
|
3356
|
-
$[
|
|
3357
|
-
$[
|
|
3358
|
-
$[
|
|
3336
|
+
$[14] = authMode;
|
|
3337
|
+
$[15] = currentUser;
|
|
3338
|
+
$[16] = loading;
|
|
3339
|
+
$[17] = selectedUser;
|
|
3340
|
+
$[18] = setSelectedUser;
|
|
3341
|
+
$[19] = users;
|
|
3342
|
+
$[20] = t11;
|
|
3359
3343
|
} else {
|
|
3360
|
-
t11 = $[
|
|
3344
|
+
t11 = $[20];
|
|
3361
3345
|
}
|
|
3362
3346
|
let t12;
|
|
3363
|
-
if ($[
|
|
3347
|
+
if ($[21] !== t10 || $[22] !== t11 || $[23] !== t6) {
|
|
3364
3348
|
t12 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center gap-3", children: [
|
|
3365
3349
|
t1,
|
|
3366
3350
|
t2,
|
|
@@ -3368,12 +3352,12 @@ return result;`);
|
|
|
3368
3352
|
t10,
|
|
3369
3353
|
t11
|
|
3370
3354
|
] });
|
|
3371
|
-
$[
|
|
3372
|
-
$[
|
|
3373
|
-
$[
|
|
3374
|
-
$[
|
|
3355
|
+
$[21] = t10;
|
|
3356
|
+
$[22] = t11;
|
|
3357
|
+
$[23] = t6;
|
|
3358
|
+
$[24] = t12;
|
|
3375
3359
|
} else {
|
|
3376
|
-
t12 = $[
|
|
3360
|
+
t12 = $[24];
|
|
3377
3361
|
}
|
|
3378
3362
|
return t12;
|
|
3379
3363
|
}
|
|
@@ -5419,6 +5403,12 @@ return result;
|
|
|
5419
5403
|
function _temp2$2(role) {
|
|
5420
5404
|
return /* @__PURE__ */ jsxRuntime.jsx(ui.MultiSelectItem, { value: role, children: role }, role);
|
|
5421
5405
|
}
|
|
5406
|
+
function sanitizeSqlIdentifier(name) {
|
|
5407
|
+
if (!/^[a-zA-Z_][a-zA-Z0-9_]*$/.test(name)) {
|
|
5408
|
+
throw new Error(`Invalid SQL identifier: "${name}". Only letters, digits, and underscores are allowed.`);
|
|
5409
|
+
}
|
|
5410
|
+
return `"${name}"`;
|
|
5411
|
+
}
|
|
5422
5412
|
const RLSEditor = ({
|
|
5423
5413
|
apiUrl = ""
|
|
5424
5414
|
}) => {
|
|
@@ -5694,6 +5684,30 @@ return result;
|
|
|
5694
5684
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark text-[11px]", children: "Total policies" }),
|
|
5695
5685
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "font-mono text-[13px] font-medium", children: rlsStats.totalPolicies })
|
|
5696
5686
|
] })
|
|
5687
|
+
] }),
|
|
5688
|
+
rlsStats.total - rlsStats.enabled > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("p-2.5 rounded border border-yellow-200 dark:border-yellow-900/50 bg-yellow-50 dark:bg-yellow-900/20 flex items-start gap-2", ui.defaultBorderMixin), children: [
|
|
5689
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.AlertTriangleIcon, { size: 14, className: "text-yellow-600 dark:text-yellow-500 mt-0.5 shrink-0" }),
|
|
5690
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
5691
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", className: "text-yellow-800 dark:text-yellow-400 text-[11px] font-semibold block", children: [
|
|
5692
|
+
rlsStats.total - rlsStats.enabled,
|
|
5693
|
+
" table",
|
|
5694
|
+
rlsStats.total - rlsStats.enabled > 1 ? "s" : "",
|
|
5695
|
+
" without RLS"
|
|
5696
|
+
] }),
|
|
5697
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-yellow-700 dark:text-yellow-600 text-[10px] block mt-0.5", children: "These tables have no row-level access control. If auth enforcement is disabled, data may be publicly accessible." })
|
|
5698
|
+
] })
|
|
5699
|
+
] }),
|
|
5700
|
+
rlsStats.enabled > 0 && rlsStats.enabled - rlsStats.withPolicies > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("p-2.5 rounded border border-blue-200 dark:border-blue-900/50 bg-blue-50 dark:bg-blue-900/20 flex items-start gap-2", ui.defaultBorderMixin), children: [
|
|
5701
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ShieldIcon, { size: 14, className: "text-blue-600 dark:text-blue-400 mt-0.5 shrink-0" }),
|
|
5702
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
5703
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", className: "text-blue-800 dark:text-blue-300 text-[11px] font-semibold block", children: [
|
|
5704
|
+
rlsStats.enabled - rlsStats.withPolicies,
|
|
5705
|
+
" table",
|
|
5706
|
+
rlsStats.enabled - rlsStats.withPolicies > 1 ? "s" : "",
|
|
5707
|
+
" with RLS but no policies"
|
|
5708
|
+
] }),
|
|
5709
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-blue-700 dark:text-blue-500 text-[10px] block mt-0.5", children: "RLS is enabled but no permissive policies exist. All access is denied by default (Postgres deny-all)." })
|
|
5710
|
+
] })
|
|
5697
5711
|
] })
|
|
5698
5712
|
] })
|
|
5699
5713
|
] })
|
|
@@ -5710,7 +5724,7 @@ return result;
|
|
|
5710
5724
|
const action = activeTableData.rlsEnabled ? "DISABLE" : "ENABLE";
|
|
5711
5725
|
if (!confirm(`Are you sure you want to ${action.toLowerCase()} Row Level Security on "${table_3}"?`)) return;
|
|
5712
5726
|
try {
|
|
5713
|
-
await databaseAdmin.executeSql(`ALTER TABLE
|
|
5727
|
+
await databaseAdmin.executeSql(`ALTER TABLE ${sanitizeSqlIdentifier(table_3)} ${action} ROW LEVEL SECURITY`);
|
|
5714
5728
|
snackbarController.open({
|
|
5715
5729
|
type: "success",
|
|
5716
5730
|
message: `RLS ${action.toLowerCase()}d on ${table_3}`
|
|
@@ -5729,7 +5743,7 @@ return result;
|
|
|
5729
5743
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "small", color: "primary", disabled: !activeCollection, onClick: () => setEditingPolicy("new"), children: t("studio_rls_create_policy") })
|
|
5730
5744
|
] }) })
|
|
5731
5745
|
] }),
|
|
5732
|
-
error ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "p-6 h-full flex items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(core.ErrorView, { title: t("studio_rls_error"), error, onRetry: fetchRLSData }) }) : !activeTableData ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow flex items-center justify-center text-text-disabled h-full", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "text-center", children: [
|
|
5746
|
+
isLoading && !activeTableData ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow flex items-center justify-center h-full", children: /* @__PURE__ */ jsxRuntime.jsx(ui.CircularProgress, { size: "small" }) }) : error ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "p-6 h-full flex items-center justify-center", children: /* @__PURE__ */ jsxRuntime.jsx(core.ErrorView, { title: t("studio_rls_error"), error, onRetry: fetchRLSData }) }) : !activeTableData ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow flex items-center justify-center text-text-disabled h-full", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "text-center", children: [
|
|
5733
5747
|
/* @__PURE__ */ jsxRuntime.jsx("svg", { className: "w-12 h-12 mx-auto mb-4 opacity-50", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ jsxRuntime.jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 1, d: "M12 15v2m-6 4h12a2 2 0 002-2v-6a2 2 0 00-2-2H6a2 2 0 00-2 2v6a2 2 0 002 2zm10-10V7a4 4 0 00-8 0v4h8z" }) }),
|
|
5734
5748
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", children: t("studio_rls_select_table") })
|
|
5735
5749
|
] }) }) : editingPolicy ? /* @__PURE__ */ jsxRuntime.jsx(PolicyEditor, { policy: editingPolicy === "new" ? void 0 : editingPolicy, schema: activeTableData.schemaName, table: activeTableData.tableName, onSave: async (newPolicy) => {
|
|
@@ -5848,7 +5862,7 @@ return result;
|
|
|
5848
5862
|
const table_4 = activeTableData.tableName;
|
|
5849
5863
|
if (!confirm(`Drop policy "${policy.policyname}" from table "${table_4}"?`)) return;
|
|
5850
5864
|
try {
|
|
5851
|
-
await databaseAdmin.executeSql(`DROP POLICY
|
|
5865
|
+
await databaseAdmin.executeSql(`DROP POLICY ${sanitizeSqlIdentifier(policy.policyname)} ON ${sanitizeSqlIdentifier(table_4)}`);
|
|
5852
5866
|
snackbarController.open({
|
|
5853
5867
|
type: "success",
|
|
5854
5868
|
message: `Policy "${policy.policyname}" dropped`
|
|
@@ -5863,6 +5877,17 @@ return result;
|
|
|
5863
5877
|
}, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2Icon, { size: ui.iconSize.smallest }) }) })
|
|
5864
5878
|
] })
|
|
5865
5879
|
] }, policy.policyname))
|
|
5880
|
+
] }),
|
|
5881
|
+
activeTableData && mergedPolicies.length === 0 && activeTableData.rlsEnabled && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center py-12 text-center", children: [
|
|
5882
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ShieldIcon, { size: 40, className: "text-surface-300 dark:text-surface-600 mb-4" }),
|
|
5883
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle2", className: "text-text-secondary dark:text-text-secondary-dark mb-2", children: "No policies defined" }),
|
|
5884
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark max-w-sm mb-4", children: "RLS is enabled on this table but no policies exist. All access is denied by default (Postgres deny-all). Create a policy to allow specific access." }),
|
|
5885
|
+
activeCollection && /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "small", variant: "filled", color: "primary", onClick: () => setEditingPolicy("new"), children: t("studio_rls_create_policy") })
|
|
5886
|
+
] }),
|
|
5887
|
+
activeTableData && mergedPolicies.length === 0 && !activeTableData.rlsEnabled && activeCollection && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center py-12 text-center", children: [
|
|
5888
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.AlertTriangleIcon, { size: 40, className: "text-yellow-400 dark:text-yellow-600 mb-4" }),
|
|
5889
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle2", className: "text-text-secondary dark:text-text-secondary-dark mb-2", children: "No access control" }),
|
|
5890
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark max-w-sm", children: "This table has neither RLS nor policies. Enable RLS and create policies to restrict row-level access." })
|
|
5866
5891
|
] })
|
|
5867
5892
|
] }) }) })
|
|
5868
5893
|
] }) }) });
|
|
@@ -5945,570 +5970,157 @@ return result;
|
|
|
5945
5970
|
}
|
|
5946
5971
|
}, [uploading, onClose]);
|
|
5947
5972
|
return /* @__PURE__ */ jsxRuntime.jsxs(ui.Dialog, { open, onOpenChange: (o) => !o && handleClose(), maxWidth: "md", children: [
|
|
5948
|
-
/* @__PURE__ */ jsxRuntime.jsxs(ui.
|
|
5949
|
-
|
|
5950
|
-
|
|
5951
|
-
|
|
5952
|
-
|
|
5953
|
-
|
|
5954
|
-
|
|
5955
|
-
currentPath || "root"
|
|
5956
|
-
] })
|
|
5973
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogTitle, { children: [
|
|
5974
|
+
"Upload Files",
|
|
5975
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark mt-0.5 block", children: [
|
|
5976
|
+
"to ",
|
|
5977
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "font-mono text-primary", children: [
|
|
5978
|
+
"/",
|
|
5979
|
+
currentPath || "root"
|
|
5957
5980
|
] })
|
|
5958
|
-
] })
|
|
5959
|
-
|
|
5960
|
-
|
|
5961
|
-
|
|
5962
|
-
|
|
5963
|
-
|
|
5964
|
-
|
|
5965
|
-
|
|
5966
|
-
|
|
5967
|
-
|
|
5968
|
-
|
|
5969
|
-
|
|
5970
|
-
|
|
5981
|
+
] })
|
|
5982
|
+
] }),
|
|
5983
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { className: "space-y-4", children: [
|
|
5984
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.FileUpload, { onFilesAdded: handleFilesAdded, size: "large", uploadDescription: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center justify-center pointer-events-none", children: [
|
|
5985
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.UploadCloudIcon, { className: "text-surface-accent-400 mb-2 w-8 h-8" }),
|
|
5986
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "label", children: "Drop files here or click to browse" }),
|
|
5987
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", color: "secondary", children: "Any file type supported" })
|
|
5988
|
+
] }) }),
|
|
5989
|
+
error && /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-red-500 block whitespace-pre-line", children: error }),
|
|
5990
|
+
selectedFiles.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-2", children: [
|
|
5991
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", color: "secondary", children: [
|
|
5992
|
+
"Selected files (",
|
|
5993
|
+
selectedFiles.length,
|
|
5994
|
+
")"
|
|
5995
|
+
] }),
|
|
5996
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "max-h-40 overflow-auto space-y-1", children: selectedFiles.map((file, index_0) => /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center justify-between p-2 rounded bg-surface-100 dark:bg-surface-800", children: [
|
|
5997
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-1 min-w-0 mr-2", children: [
|
|
5998
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "truncate", children: file.name }),
|
|
5999
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", color: "secondary", children: formatFileSize(file.size) })
|
|
5971
6000
|
] }),
|
|
5972
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5973
|
-
|
|
5974
|
-
|
|
5975
|
-
|
|
5976
|
-
|
|
5977
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", size: "small", onClick: (e) => {
|
|
5978
|
-
e.stopPropagation();
|
|
5979
|
-
handleRemoveFile(index_0);
|
|
5980
|
-
}, disabled: uploading, children: "Remove" })
|
|
5981
|
-
] }, `${file.name}-${index_0}`)) })
|
|
5982
|
-
] })
|
|
6001
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: (e) => {
|
|
6002
|
+
e.stopPropagation();
|
|
6003
|
+
handleRemoveFile(index_0);
|
|
6004
|
+
}, disabled: uploading, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.XIcon, { size: 14 }) })
|
|
6005
|
+
] }, `${file.name}-${index_0}`)) })
|
|
5983
6006
|
] })
|
|
5984
6007
|
] }),
|
|
5985
6008
|
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogActions, { children: [
|
|
5986
6009
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", onClick: handleClose, disabled: uploading, children: "Cancel" }),
|
|
5987
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "filled", onClick: handleUpload, disabled: selectedFiles.length === 0 || uploading,
|
|
5988
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.CircularProgress, { size: "smallest" }),
|
|
5989
|
-
"Uploading..."
|
|
5990
|
-
] }) : `Upload ${selectedFiles.length > 0 ? `(${selectedFiles.length})` : ""}` })
|
|
6010
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "filled", onClick: handleUpload, disabled: selectedFiles.length === 0 || uploading, startIcon: uploading ? /* @__PURE__ */ jsxRuntime.jsx(ui.CircularProgress, { size: "smallest" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.UploadCloudIcon, { size: 14 }), children: uploading ? "Uploading..." : `Upload${selectedFiles.length > 0 ? ` (${selectedFiles.length})` : ""}` })
|
|
5991
6011
|
] })
|
|
5992
6012
|
] });
|
|
5993
6013
|
}
|
|
5994
|
-
function FilePreviewPanel(
|
|
5995
|
-
|
|
5996
|
-
|
|
5997
|
-
|
|
5998
|
-
|
|
5999
|
-
|
|
6000
|
-
downloadUrl
|
|
6001
|
-
} = t0;
|
|
6014
|
+
function FilePreviewPanel({
|
|
6015
|
+
file,
|
|
6016
|
+
onClose,
|
|
6017
|
+
onDelete,
|
|
6018
|
+
downloadUrl
|
|
6019
|
+
}) {
|
|
6002
6020
|
file.contentType?.startsWith("image/");
|
|
6003
6021
|
file.contentType?.startsWith("video/");
|
|
6004
6022
|
file.contentType?.startsWith("audio/");
|
|
6005
|
-
|
|
6006
|
-
if ($[0] !== file.contentType) {
|
|
6007
|
-
t1 = getFileIcon(file.contentType);
|
|
6008
|
-
$[0] = file.contentType;
|
|
6009
|
-
$[1] = t1;
|
|
6010
|
-
} else {
|
|
6011
|
-
t1 = $[1];
|
|
6012
|
-
}
|
|
6013
|
-
const FileIconComponent = t1;
|
|
6023
|
+
const FileIconComponent = getFileIcon(file.contentType);
|
|
6014
6024
|
const [deleteDialogOpen, setDeleteDialogOpen] = React.useState(false);
|
|
6015
|
-
|
|
6016
|
-
|
|
6017
|
-
|
|
6018
|
-
|
|
6019
|
-
|
|
6020
|
-
|
|
6021
|
-
|
|
6022
|
-
|
|
6023
|
-
|
|
6024
|
-
|
|
6025
|
-
|
|
6026
|
-
|
|
6027
|
-
|
|
6028
|
-
|
|
6029
|
-
|
|
6030
|
-
|
|
6031
|
-
|
|
6032
|
-
|
|
6033
|
-
|
|
6034
|
-
|
|
6035
|
-
|
|
6036
|
-
|
|
6037
|
-
|
|
6038
|
-
|
|
6039
|
-
} else {
|
|
6040
|
-
t5 = $[7];
|
|
6041
|
-
}
|
|
6042
|
-
let t6;
|
|
6043
|
-
if ($[8] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6044
|
-
t6 = () => setDeleteDialogOpen(true);
|
|
6045
|
-
$[8] = t6;
|
|
6046
|
-
} else {
|
|
6047
|
-
t6 = $[8];
|
|
6048
|
-
}
|
|
6049
|
-
let t7;
|
|
6050
|
-
if ($[9] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6051
|
-
t7 = /* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Delete", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: t6, className: "text-red-500 hover:bg-red-50 dark:hover:bg-red-900/20", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2Icon, { size: ui.iconSize.smallest }) }) });
|
|
6052
|
-
$[9] = t7;
|
|
6053
|
-
} else {
|
|
6054
|
-
t7 = $[9];
|
|
6055
|
-
}
|
|
6056
|
-
let t8;
|
|
6057
|
-
if ($[10] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6058
|
-
t8 = /* @__PURE__ */ jsxRuntime.jsx(lucideReact.XIcon, { size: ui.iconSize.smallest });
|
|
6059
|
-
$[10] = t8;
|
|
6060
|
-
} else {
|
|
6061
|
-
t8 = $[10];
|
|
6062
|
-
}
|
|
6063
|
-
let t9;
|
|
6064
|
-
if ($[11] !== onClose) {
|
|
6065
|
-
t9 = /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: onClose, children: t8 });
|
|
6066
|
-
$[11] = onClose;
|
|
6067
|
-
$[12] = t9;
|
|
6068
|
-
} else {
|
|
6069
|
-
t9 = $[12];
|
|
6070
|
-
}
|
|
6071
|
-
let t10;
|
|
6072
|
-
if ($[13] !== t5 || $[14] !== t9) {
|
|
6073
|
-
t10 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-0.5", children: [
|
|
6074
|
-
t5,
|
|
6075
|
-
t7,
|
|
6076
|
-
t9
|
|
6077
|
-
] });
|
|
6078
|
-
$[13] = t5;
|
|
6079
|
-
$[14] = t9;
|
|
6080
|
-
$[15] = t10;
|
|
6081
|
-
} else {
|
|
6082
|
-
t10 = $[15];
|
|
6083
|
-
}
|
|
6084
|
-
let t11;
|
|
6085
|
-
if ($[16] !== t10 || $[17] !== t4) {
|
|
6086
|
-
t11 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: t3, children: [
|
|
6087
|
-
t4,
|
|
6088
|
-
t10
|
|
6089
|
-
] });
|
|
6090
|
-
$[16] = t10;
|
|
6091
|
-
$[17] = t4;
|
|
6092
|
-
$[18] = t11;
|
|
6093
|
-
} else {
|
|
6094
|
-
t11 = $[18];
|
|
6095
|
-
}
|
|
6096
|
-
let t12;
|
|
6097
|
-
const ext = getExtension(file.name)?.toLowerCase() || "";
|
|
6098
|
-
const isImage_0 = file.contentType?.startsWith("image/") || ["jpg", "jpeg", "png", "gif", "webp", "svg"].includes(ext);
|
|
6099
|
-
const isVideo_0 = file.contentType?.startsWith("video/") || ["mp4", "webm", "ogg", "mov"].includes(ext);
|
|
6100
|
-
const isAudio_0 = file.contentType?.startsWith("audio/") || ["mp3", "wav", "ogg", "m4a"].includes(ext);
|
|
6101
|
-
const downloadUrl_0 = file.downloadUrl;
|
|
6102
|
-
if (isImage_0 && downloadUrl_0) {
|
|
6103
|
-
let t132;
|
|
6104
|
-
if ($[19] !== downloadUrl_0 || $[20] !== file.name) {
|
|
6105
|
-
t132 = /* @__PURE__ */ jsxRuntime.jsx("img", { src: downloadUrl_0, alt: file.name, className: "max-w-full max-h-[400px] object-contain rounded-md shadow-sm" });
|
|
6106
|
-
$[19] = downloadUrl_0;
|
|
6107
|
-
$[20] = file.name;
|
|
6108
|
-
$[21] = t132;
|
|
6109
|
-
} else {
|
|
6110
|
-
t132 = $[21];
|
|
6111
|
-
}
|
|
6112
|
-
t12 = t132;
|
|
6113
|
-
} else {
|
|
6114
|
-
if (isVideo_0 && downloadUrl_0) {
|
|
6115
|
-
let t132;
|
|
6116
|
-
if ($[22] !== downloadUrl_0) {
|
|
6117
|
-
t132 = /* @__PURE__ */ jsxRuntime.jsx("video", { src: downloadUrl_0, className: "max-w-full max-h-[400px] rounded-md", controls: true });
|
|
6118
|
-
$[22] = downloadUrl_0;
|
|
6119
|
-
$[23] = t132;
|
|
6120
|
-
} else {
|
|
6121
|
-
t132 = $[23];
|
|
6122
|
-
}
|
|
6123
|
-
t12 = t132;
|
|
6124
|
-
} else {
|
|
6125
|
-
if (isAudio_0 && downloadUrl_0) {
|
|
6126
|
-
let t132;
|
|
6127
|
-
if ($[24] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6128
|
-
t132 = /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Music2Icon, { className: "text-surface-accent-400 w-10 h-10" });
|
|
6129
|
-
$[24] = t132;
|
|
6130
|
-
} else {
|
|
6131
|
-
t132 = $[24];
|
|
6132
|
-
}
|
|
6133
|
-
let t142;
|
|
6134
|
-
if ($[25] !== downloadUrl_0) {
|
|
6135
|
-
t142 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center gap-4", children: [
|
|
6136
|
-
t132,
|
|
6025
|
+
const [urlCopied, setUrlCopied] = React.useState(false);
|
|
6026
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
6027
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex flex-col h-full border-l", ui.defaultBorderMixin, "bg-white dark:bg-surface-800"), children: [
|
|
6028
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex items-center justify-between p-3 border-b shrink-0", ui.defaultBorderMixin), children: [
|
|
6029
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "font-medium truncate flex-1 mr-2", children: file.name }),
|
|
6030
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-0.5", children: [
|
|
6031
|
+
downloadUrl && /* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Download", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => window.open(downloadUrl, "_blank"), children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.DownloadIcon, { size: ui.iconSize.smallest }) }) }),
|
|
6032
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Delete", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => setDeleteDialogOpen(true), className: "text-red-500 hover:bg-red-50 dark:hover:bg-red-900/20", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2Icon, { size: ui.iconSize.smallest }) }) }),
|
|
6033
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: onClose, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.XIcon, { size: ui.iconSize.smallest }) })
|
|
6034
|
+
] })
|
|
6035
|
+
] }),
|
|
6036
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-1 overflow-auto", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: ui.cls("flex flex-col items-center justify-center min-h-[200px] p-4 bg-surface-50 dark:bg-surface-800 border-b", ui.defaultBorderMixin), children: (() => {
|
|
6037
|
+
const ext = getExtension(file.name)?.toLowerCase() || "";
|
|
6038
|
+
const isImage_0 = file.contentType?.startsWith("image/") || ["jpg", "jpeg", "png", "gif", "webp", "svg"].includes(ext);
|
|
6039
|
+
const isVideo_0 = file.contentType?.startsWith("video/") || ["mp4", "webm", "ogg", "mov"].includes(ext);
|
|
6040
|
+
const isAudio_0 = file.contentType?.startsWith("audio/") || ["mp3", "wav", "ogg", "m4a"].includes(ext);
|
|
6041
|
+
const downloadUrl_0 = file.downloadUrl;
|
|
6042
|
+
if (isImage_0 && downloadUrl_0) {
|
|
6043
|
+
return /* @__PURE__ */ jsxRuntime.jsx("img", { src: downloadUrl_0, alt: file.name, className: "max-w-full max-h-[400px] object-contain rounded-md shadow-sm" });
|
|
6044
|
+
} else if (isVideo_0 && downloadUrl_0) {
|
|
6045
|
+
return /* @__PURE__ */ jsxRuntime.jsx("video", { src: downloadUrl_0, className: "max-w-full max-h-[400px] rounded-md", controls: true });
|
|
6046
|
+
} else if (isAudio_0 && downloadUrl_0) {
|
|
6047
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center gap-4", children: [
|
|
6048
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Music2Icon, { className: "text-surface-accent-400 w-10 h-10" }),
|
|
6137
6049
|
/* @__PURE__ */ jsxRuntime.jsx("audio", { src: downloadUrl_0, controls: true, className: "w-full max-w-xs" })
|
|
6138
6050
|
] });
|
|
6139
|
-
$[25] = downloadUrl_0;
|
|
6140
|
-
$[26] = t142;
|
|
6141
|
-
} else {
|
|
6142
|
-
t142 = $[26];
|
|
6143
|
-
}
|
|
6144
|
-
t12 = t142;
|
|
6145
|
-
} else {
|
|
6146
|
-
let t132;
|
|
6147
|
-
if ($[27] !== FileIconComponent) {
|
|
6148
|
-
t132 = /* @__PURE__ */ jsxRuntime.jsx(FileIconComponent, { className: "w-10 h-10" });
|
|
6149
|
-
$[27] = FileIconComponent;
|
|
6150
|
-
$[28] = t132;
|
|
6151
|
-
} else {
|
|
6152
|
-
t132 = $[28];
|
|
6153
|
-
}
|
|
6154
|
-
let t142;
|
|
6155
|
-
if ($[29] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6156
|
-
t142 = /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark", children: "No preview available" });
|
|
6157
|
-
$[29] = t142;
|
|
6158
6051
|
} else {
|
|
6159
|
-
|
|
6160
|
-
|
|
6161
|
-
|
|
6162
|
-
if ($[30] !== t132) {
|
|
6163
|
-
t152 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center gap-3 text-surface-accent-400", children: [
|
|
6164
|
-
t132,
|
|
6165
|
-
t142
|
|
6052
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center gap-3 text-surface-accent-400", children: [
|
|
6053
|
+
/* @__PURE__ */ jsxRuntime.jsx(FileIconComponent, { className: "w-10 h-10" }),
|
|
6054
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark", children: "No preview available" })
|
|
6166
6055
|
] });
|
|
6167
|
-
$[30] = t132;
|
|
6168
|
-
$[31] = t152;
|
|
6169
|
-
} else {
|
|
6170
|
-
t152 = $[31];
|
|
6171
6056
|
}
|
|
6172
|
-
|
|
6173
|
-
|
|
6174
|
-
|
|
6175
|
-
|
|
6176
|
-
|
|
6177
|
-
|
|
6178
|
-
|
|
6179
|
-
|
|
6180
|
-
|
|
6181
|
-
|
|
6182
|
-
|
|
6183
|
-
|
|
6184
|
-
|
|
6185
|
-
|
|
6186
|
-
|
|
6187
|
-
|
|
6188
|
-
|
|
6189
|
-
|
|
6190
|
-
|
|
6191
|
-
|
|
6192
|
-
|
|
6193
|
-
|
|
6194
|
-
|
|
6195
|
-
|
|
6196
|
-
|
|
6197
|
-
|
|
6198
|
-
|
|
6199
|
-
|
|
6200
|
-
|
|
6201
|
-
|
|
6202
|
-
|
|
6203
|
-
|
|
6204
|
-
|
|
6205
|
-
|
|
6206
|
-
|
|
6207
|
-
|
|
6208
|
-
|
|
6209
|
-
|
|
6210
|
-
|
|
6211
|
-
|
|
6212
|
-
|
|
6213
|
-
} else {
|
|
6214
|
-
t17 = $[38];
|
|
6215
|
-
}
|
|
6216
|
-
const t18 = file.contentType || "Unknown";
|
|
6217
|
-
let t19;
|
|
6218
|
-
if ($[39] !== t18) {
|
|
6219
|
-
t19 = /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6220
|
-
t17,
|
|
6221
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px]", children: t18 })
|
|
6222
|
-
] });
|
|
6223
|
-
$[39] = t18;
|
|
6224
|
-
$[40] = t19;
|
|
6225
|
-
} else {
|
|
6226
|
-
t19 = $[40];
|
|
6227
|
-
}
|
|
6228
|
-
let t20;
|
|
6229
|
-
if ($[41] !== file.size) {
|
|
6230
|
-
t20 = file.size !== void 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6231
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Size" }),
|
|
6232
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px]", children: formatFileSize(file.size) })
|
|
6233
|
-
] });
|
|
6234
|
-
$[41] = file.size;
|
|
6235
|
-
$[42] = t20;
|
|
6236
|
-
} else {
|
|
6237
|
-
t20 = $[42];
|
|
6238
|
-
}
|
|
6239
|
-
let t21;
|
|
6240
|
-
if ($[43] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6241
|
-
t21 = /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Extension" });
|
|
6242
|
-
$[43] = t21;
|
|
6243
|
-
} else {
|
|
6244
|
-
t21 = $[43];
|
|
6245
|
-
}
|
|
6246
|
-
let t22;
|
|
6247
|
-
if ($[44] !== file.name) {
|
|
6248
|
-
t22 = getExtension(file.name) || "—";
|
|
6249
|
-
$[44] = file.name;
|
|
6250
|
-
$[45] = t22;
|
|
6251
|
-
} else {
|
|
6252
|
-
t22 = $[45];
|
|
6253
|
-
}
|
|
6254
|
-
let t23;
|
|
6255
|
-
if ($[46] !== t22) {
|
|
6256
|
-
t23 = /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6257
|
-
t21,
|
|
6258
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] font-mono", children: t22 })
|
|
6259
|
-
] });
|
|
6260
|
-
$[46] = t22;
|
|
6261
|
-
$[47] = t23;
|
|
6262
|
-
} else {
|
|
6263
|
-
t23 = $[47];
|
|
6264
|
-
}
|
|
6265
|
-
let t24;
|
|
6266
|
-
if ($[48] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6267
|
-
t24 = /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Path" });
|
|
6268
|
-
$[48] = t24;
|
|
6269
|
-
} else {
|
|
6270
|
-
t24 = $[48];
|
|
6271
|
-
}
|
|
6272
|
-
let t25;
|
|
6273
|
-
if ($[49] !== file.fullPath) {
|
|
6274
|
-
t25 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "col-span-2", children: [
|
|
6275
|
-
t24,
|
|
6276
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] font-mono break-all", children: file.fullPath })
|
|
6277
|
-
] });
|
|
6278
|
-
$[49] = file.fullPath;
|
|
6279
|
-
$[50] = t25;
|
|
6280
|
-
} else {
|
|
6281
|
-
t25 = $[50];
|
|
6282
|
-
}
|
|
6283
|
-
let t26;
|
|
6284
|
-
if ($[51] !== t16 || $[52] !== t19 || $[53] !== t20 || $[54] !== t23 || $[55] !== t25) {
|
|
6285
|
-
t26 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid grid-cols-2 gap-3", children: [
|
|
6286
|
-
t16,
|
|
6287
|
-
t19,
|
|
6288
|
-
t20,
|
|
6289
|
-
t23,
|
|
6290
|
-
t25
|
|
6291
|
-
] });
|
|
6292
|
-
$[51] = t16;
|
|
6293
|
-
$[52] = t19;
|
|
6294
|
-
$[53] = t20;
|
|
6295
|
-
$[54] = t23;
|
|
6296
|
-
$[55] = t25;
|
|
6297
|
-
$[56] = t26;
|
|
6298
|
-
} else {
|
|
6299
|
-
t26 = $[56];
|
|
6300
|
-
}
|
|
6301
|
-
let t27;
|
|
6302
|
-
if ($[57] !== downloadUrl) {
|
|
6303
|
-
t27 = downloadUrl && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "pt-2", children: [
|
|
6304
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px] block mb-1", children: "URL" }),
|
|
6305
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "p-2 rounded bg-surface-100 dark:bg-surface-950 cursor-pointer hover:bg-surface-200 dark:hover:bg-surface-700 transition-colors", onClick: () => {
|
|
6306
|
-
navigator.clipboard.writeText(downloadUrl);
|
|
6307
|
-
}, children: [
|
|
6308
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "font-mono text-[11px] break-all text-primary", children: downloadUrl }),
|
|
6309
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark text-[10px] block mt-1", children: "Click to copy" })
|
|
6310
|
-
] })
|
|
6311
|
-
] });
|
|
6312
|
-
$[57] = downloadUrl;
|
|
6313
|
-
$[58] = t27;
|
|
6314
|
-
} else {
|
|
6315
|
-
t27 = $[58];
|
|
6316
|
-
}
|
|
6317
|
-
let t28;
|
|
6318
|
-
if ($[59] !== t26 || $[60] !== t27) {
|
|
6319
|
-
t28 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "p-4 space-y-3", children: [
|
|
6320
|
-
t14,
|
|
6321
|
-
t26,
|
|
6322
|
-
t27
|
|
6323
|
-
] });
|
|
6324
|
-
$[59] = t26;
|
|
6325
|
-
$[60] = t27;
|
|
6326
|
-
$[61] = t28;
|
|
6327
|
-
} else {
|
|
6328
|
-
t28 = $[61];
|
|
6329
|
-
}
|
|
6330
|
-
let t29;
|
|
6331
|
-
if ($[62] !== t11 || $[63] !== t13 || $[64] !== t28) {
|
|
6332
|
-
t29 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: t2, children: [
|
|
6333
|
-
t11,
|
|
6334
|
-
t13,
|
|
6335
|
-
t28
|
|
6336
|
-
] });
|
|
6337
|
-
$[62] = t11;
|
|
6338
|
-
$[63] = t13;
|
|
6339
|
-
$[64] = t28;
|
|
6340
|
-
$[65] = t29;
|
|
6341
|
-
} else {
|
|
6342
|
-
t29 = $[65];
|
|
6343
|
-
}
|
|
6344
|
-
let t30;
|
|
6345
|
-
if ($[66] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6346
|
-
t30 = /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle1", className: "mb-2", children: "Delete File?" });
|
|
6347
|
-
$[66] = t30;
|
|
6348
|
-
} else {
|
|
6349
|
-
t30 = $[66];
|
|
6350
|
-
}
|
|
6351
|
-
let t31;
|
|
6352
|
-
if ($[67] !== file.name) {
|
|
6353
|
-
t31 = /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { children: [
|
|
6354
|
-
t30,
|
|
6355
|
-
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { className: "text-surface-accent-600 dark:text-surface-accent-400", children: [
|
|
6356
|
-
'Are you sure you want to delete "',
|
|
6357
|
-
file.name,
|
|
6358
|
-
'"? This action cannot be undone.'
|
|
6057
|
+
})() }) }),
|
|
6058
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "p-4 space-y-3", children: [
|
|
6059
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark text-[10px] uppercase tracking-wider font-bold mb-1 block", children: "File Info" }) }),
|
|
6060
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "grid grid-cols-2 gap-3", children: [
|
|
6061
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6062
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Name" }),
|
|
6063
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] break-all", children: file.name })
|
|
6064
|
+
] }),
|
|
6065
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6066
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Type" }),
|
|
6067
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px]", children: file.contentType || "Unknown" })
|
|
6068
|
+
] }),
|
|
6069
|
+
file.size !== void 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6070
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Size" }),
|
|
6071
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px]", children: formatFileSize(file.size) })
|
|
6072
|
+
] }),
|
|
6073
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6074
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Extension" }),
|
|
6075
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] font-mono", children: getExtension(file.name) || "—" })
|
|
6076
|
+
] }),
|
|
6077
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "col-span-2", children: [
|
|
6078
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px]", children: "Path" }),
|
|
6079
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] font-mono break-all", children: file.fullPath })
|
|
6080
|
+
] })
|
|
6081
|
+
] }),
|
|
6082
|
+
downloadUrl && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "pt-2", children: [
|
|
6083
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-surface-accent-500 text-[11px] block mb-1", children: "URL" }),
|
|
6084
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex items-center gap-2 p-2 rounded cursor-pointer transition-colors", "bg-surface-100 dark:bg-surface-800 hover:bg-surface-200 dark:hover:bg-surface-700"), onClick: () => {
|
|
6085
|
+
const fullUrl = downloadUrl.startsWith("http") ? downloadUrl : `${window.location.origin}${downloadUrl.startsWith("/") ? "" : "/"}${downloadUrl}`;
|
|
6086
|
+
navigator.clipboard.writeText(fullUrl).then(() => {
|
|
6087
|
+
setUrlCopied(true);
|
|
6088
|
+
setTimeout(() => setUrlCopied(false), 2e3);
|
|
6089
|
+
});
|
|
6090
|
+
}, children: [
|
|
6091
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "font-mono text-[11px] truncate flex-1 min-w-0 text-primary", children: (() => {
|
|
6092
|
+
const fullUrl_0 = downloadUrl.startsWith("http") ? downloadUrl : `${window.location.origin}${downloadUrl.startsWith("/") ? "" : "/"}${downloadUrl}`;
|
|
6093
|
+
return fullUrl_0;
|
|
6094
|
+
})() }),
|
|
6095
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: urlCopied ? "Copied!" : "Copy URL", children: /* @__PURE__ */ jsxRuntime.jsx("div", { className: "shrink-0", children: urlCopied ? /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckIcon, { size: 14, className: "text-green-500" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CopyIcon, { size: 14, className: "text-surface-accent-400" }) }) })
|
|
6096
|
+
] })
|
|
6097
|
+
] })
|
|
6359
6098
|
] })
|
|
6360
|
-
] })
|
|
6361
|
-
|
|
6362
|
-
|
|
6363
|
-
|
|
6364
|
-
|
|
6365
|
-
|
|
6366
|
-
|
|
6367
|
-
|
|
6368
|
-
|
|
6369
|
-
|
|
6370
|
-
|
|
6371
|
-
|
|
6372
|
-
|
|
6373
|
-
|
|
6374
|
-
|
|
6375
|
-
|
|
6376
|
-
t32,
|
|
6377
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "filled", color: "error", onClick: () => {
|
|
6378
|
-
setDeleteDialogOpen(false);
|
|
6379
|
-
onDelete();
|
|
6380
|
-
}, children: "Delete" })
|
|
6381
|
-
] });
|
|
6382
|
-
$[70] = onDelete;
|
|
6383
|
-
$[71] = t33;
|
|
6384
|
-
} else {
|
|
6385
|
-
t33 = $[71];
|
|
6386
|
-
}
|
|
6387
|
-
let t34;
|
|
6388
|
-
if ($[72] !== deleteDialogOpen || $[73] !== t31 || $[74] !== t33) {
|
|
6389
|
-
t34 = /* @__PURE__ */ jsxRuntime.jsxs(ui.Dialog, { open: deleteDialogOpen, onOpenChange: setDeleteDialogOpen, children: [
|
|
6390
|
-
t31,
|
|
6391
|
-
t33
|
|
6392
|
-
] });
|
|
6393
|
-
$[72] = deleteDialogOpen;
|
|
6394
|
-
$[73] = t31;
|
|
6395
|
-
$[74] = t33;
|
|
6396
|
-
$[75] = t34;
|
|
6397
|
-
} else {
|
|
6398
|
-
t34 = $[75];
|
|
6399
|
-
}
|
|
6400
|
-
let t35;
|
|
6401
|
-
if ($[76] !== t29 || $[77] !== t34) {
|
|
6402
|
-
t35 = /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
6403
|
-
t29,
|
|
6404
|
-
t34
|
|
6405
|
-
] });
|
|
6406
|
-
$[76] = t29;
|
|
6407
|
-
$[77] = t34;
|
|
6408
|
-
$[78] = t35;
|
|
6409
|
-
} else {
|
|
6410
|
-
t35 = $[78];
|
|
6411
|
-
}
|
|
6412
|
-
return t35;
|
|
6413
|
-
}
|
|
6414
|
-
function StorageSidebar(t0) {
|
|
6415
|
-
const $ = reactCompilerRuntime.c(19);
|
|
6416
|
-
const {
|
|
6417
|
-
folders,
|
|
6418
|
-
currentPath,
|
|
6419
|
-
onNavigate,
|
|
6420
|
-
loading
|
|
6421
|
-
} = t0;
|
|
6422
|
-
breadcrumbSegments(currentPath);
|
|
6423
|
-
let t1;
|
|
6424
|
-
let t2;
|
|
6425
|
-
if ($[0] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6426
|
-
t1 = ui.cls("flex flex-col h-full w-full bg-white dark:bg-surface-950 border-r", ui.defaultBorderMixin);
|
|
6427
|
-
t2 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: ui.cls("p-3 border-b flex justify-between items-center bg-surface-50 dark:bg-surface-900 shrink-0", ui.defaultBorderMixin), children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "font-bold uppercase tracking-wider text-text-disabled dark:text-text-disabled-dark", children: "Folders" }) });
|
|
6428
|
-
$[0] = t1;
|
|
6429
|
-
$[1] = t2;
|
|
6430
|
-
} else {
|
|
6431
|
-
t1 = $[0];
|
|
6432
|
-
t2 = $[1];
|
|
6433
|
-
}
|
|
6434
|
-
const t3 = currentPath === "" || !currentPath ? "bg-primary/10 text-primary dark:bg-primary/20 dark:text-primary-light" : "hover:bg-surface-100 dark:hover:bg-surface-950 text-text-secondary dark:text-text-secondary-dark";
|
|
6435
|
-
let t4;
|
|
6436
|
-
if ($[2] !== t3) {
|
|
6437
|
-
t4 = ui.cls("flex items-center p-1.5 cursor-pointer rounded transition-colors", t3);
|
|
6438
|
-
$[2] = t3;
|
|
6439
|
-
$[3] = t4;
|
|
6440
|
-
} else {
|
|
6441
|
-
t4 = $[3];
|
|
6442
|
-
}
|
|
6443
|
-
let t5;
|
|
6444
|
-
if ($[4] !== onNavigate) {
|
|
6445
|
-
t5 = () => onNavigate("");
|
|
6446
|
-
$[4] = onNavigate;
|
|
6447
|
-
$[5] = t5;
|
|
6448
|
-
} else {
|
|
6449
|
-
t5 = $[5];
|
|
6450
|
-
}
|
|
6451
|
-
let t6;
|
|
6452
|
-
let t7;
|
|
6453
|
-
if ($[6] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel")) {
|
|
6454
|
-
t6 = /* @__PURE__ */ jsxRuntime.jsx(lucideReact.HomeIcon, { size: ui.iconSize.smallest, className: "mr-1.5 shrink-0" });
|
|
6455
|
-
t7 = /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-xs truncate", children: "Root" });
|
|
6456
|
-
$[6] = t6;
|
|
6457
|
-
$[7] = t7;
|
|
6458
|
-
} else {
|
|
6459
|
-
t6 = $[6];
|
|
6460
|
-
t7 = $[7];
|
|
6461
|
-
}
|
|
6462
|
-
let t8;
|
|
6463
|
-
if ($[8] !== t4 || $[9] !== t5) {
|
|
6464
|
-
t8 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: t4, onClick: t5, children: [
|
|
6465
|
-
t6,
|
|
6466
|
-
t7
|
|
6467
|
-
] });
|
|
6468
|
-
$[8] = t4;
|
|
6469
|
-
$[9] = t5;
|
|
6470
|
-
$[10] = t8;
|
|
6471
|
-
} else {
|
|
6472
|
-
t8 = $[10];
|
|
6473
|
-
}
|
|
6474
|
-
let t9;
|
|
6475
|
-
if ($[11] !== currentPath || $[12] !== folders || $[13] !== loading || $[14] !== onNavigate) {
|
|
6476
|
-
t9 = loading && folders.length === 0 ? /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex justify-center p-4", children: /* @__PURE__ */ jsxRuntime.jsx(ui.CircularProgress, { size: "small" }) }) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "mt-1 space-y-0.5", children: folders.map((folder) => {
|
|
6477
|
-
const isSelected = currentPath === folder.fullPath;
|
|
6478
|
-
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex items-center p-1.5 cursor-pointer rounded transition-colors group", isSelected ? "bg-primary/10 text-primary dark:bg-primary/20 dark:text-primary-light" : "hover:bg-surface-100 dark:hover:bg-surface-950 text-text-secondary dark:text-text-secondary-dark"), onClick: () => onNavigate(folder.fullPath), children: [
|
|
6479
|
-
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderIcon, { size: ui.iconSize.smallest, className: "mr-1.5 shrink-0 text-amber-500 dark:text-amber-400" }),
|
|
6480
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-xs truncate flex-1 min-w-0", children: folder.name })
|
|
6481
|
-
] }, folder.fullPath);
|
|
6482
|
-
}) });
|
|
6483
|
-
$[11] = currentPath;
|
|
6484
|
-
$[12] = folders;
|
|
6485
|
-
$[13] = loading;
|
|
6486
|
-
$[14] = onNavigate;
|
|
6487
|
-
$[15] = t9;
|
|
6488
|
-
} else {
|
|
6489
|
-
t9 = $[15];
|
|
6490
|
-
}
|
|
6491
|
-
let t10;
|
|
6492
|
-
if ($[16] !== t8 || $[17] !== t9) {
|
|
6493
|
-
t10 = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: t1, children: [
|
|
6494
|
-
t2,
|
|
6495
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-grow overflow-y-auto no-scrollbar p-1", children: [
|
|
6496
|
-
t8,
|
|
6497
|
-
t9
|
|
6099
|
+
] }),
|
|
6100
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Dialog, { open: deleteDialogOpen, onOpenChange: setDeleteDialogOpen, children: [
|
|
6101
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { children: [
|
|
6102
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle1", className: "mb-2", children: "Delete File?" }),
|
|
6103
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { className: "text-surface-accent-600 dark:text-surface-accent-400", children: [
|
|
6104
|
+
'Are you sure you want to delete "',
|
|
6105
|
+
file.name,
|
|
6106
|
+
'"? This action cannot be undone.'
|
|
6107
|
+
] })
|
|
6108
|
+
] }),
|
|
6109
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogActions, { children: [
|
|
6110
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", onClick: () => setDeleteDialogOpen(false), children: "Cancel" }),
|
|
6111
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "filled", color: "error", onClick: () => {
|
|
6112
|
+
setDeleteDialogOpen(false);
|
|
6113
|
+
onDelete();
|
|
6114
|
+
}, children: "Delete" })
|
|
6498
6115
|
] })
|
|
6499
|
-
] })
|
|
6500
|
-
|
|
6501
|
-
$[17] = t9;
|
|
6502
|
-
$[18] = t10;
|
|
6503
|
-
} else {
|
|
6504
|
-
t10 = $[18];
|
|
6505
|
-
}
|
|
6506
|
-
return t10;
|
|
6116
|
+
] })
|
|
6117
|
+
] });
|
|
6507
6118
|
}
|
|
6508
6119
|
const StorageView = () => {
|
|
6509
6120
|
const storageSource = core.useStorageSource();
|
|
6510
6121
|
const snackbarController = core.useSnackbarController();
|
|
6511
|
-
const [
|
|
6122
|
+
const [searchParams, setSearchParams] = reactRouterDom.useSearchParams();
|
|
6123
|
+
const currentPath = searchParams.get("path") || "";
|
|
6512
6124
|
const [loading, setLoading] = React.useState(true);
|
|
6513
6125
|
const [error, setError] = React.useState(null);
|
|
6514
6126
|
const [folders, setFolders] = React.useState([]);
|
|
@@ -6517,25 +6129,24 @@ return result;
|
|
|
6517
6129
|
const [selectedDownloadUrl, setSelectedDownloadUrl] = React.useState(null);
|
|
6518
6130
|
const [uploadDialogOpen, setUploadDialogOpen] = React.useState(false);
|
|
6519
6131
|
const [viewMode, setViewMode] = React.useState("grid");
|
|
6520
|
-
const [
|
|
6521
|
-
|
|
6522
|
-
|
|
6523
|
-
|
|
6524
|
-
|
|
6525
|
-
|
|
6526
|
-
|
|
6527
|
-
|
|
6132
|
+
const [selectedPaths, setSelectedPaths] = React.useState(/* @__PURE__ */ new Set());
|
|
6133
|
+
const lastClickedRef = React.useRef(null);
|
|
6134
|
+
const [deleteDialogOpen, setDeleteDialogOpen] = React.useState(false);
|
|
6135
|
+
const [deleteDialogTarget, setDeleteDialogTarget] = React.useState(null);
|
|
6136
|
+
const [deleting, setDeleting] = React.useState(false);
|
|
6137
|
+
const [newFolderDialogOpen, setNewFolderDialogOpen] = React.useState(false);
|
|
6138
|
+
const [newFolderName, setNewFolderName] = React.useState("");
|
|
6139
|
+
const [creatingFolder, setCreatingFolder] = React.useState(false);
|
|
6140
|
+
const apiConfig = core.useApiConfig();
|
|
6141
|
+
const storageSourceRef = React.useRef(storageSource);
|
|
6528
6142
|
React.useEffect(() => {
|
|
6529
|
-
|
|
6530
|
-
|
|
6531
|
-
} catch {
|
|
6532
|
-
}
|
|
6533
|
-
}, [sidebarSize]);
|
|
6143
|
+
storageSourceRef.current = storageSource;
|
|
6144
|
+
}, [storageSource]);
|
|
6534
6145
|
const fetchContents = React.useCallback(async (path) => {
|
|
6535
6146
|
setLoading(true);
|
|
6536
6147
|
setError(null);
|
|
6537
6148
|
try {
|
|
6538
|
-
const result = await
|
|
6149
|
+
const result = await storageSourceRef.current.listObjects(path);
|
|
6539
6150
|
const folderItems = (result.prefixes ?? []).map((ref) => ({
|
|
6540
6151
|
name: ref.name,
|
|
6541
6152
|
fullPath: ref.fullPath,
|
|
@@ -6543,7 +6154,7 @@ return result;
|
|
|
6543
6154
|
}));
|
|
6544
6155
|
const fileItems = await Promise.all((result.items ?? []).map(async (ref_0) => {
|
|
6545
6156
|
try {
|
|
6546
|
-
const downloadConfig = await
|
|
6157
|
+
const downloadConfig = await storageSourceRef.current.getSignedUrl(ref_0.fullPath);
|
|
6547
6158
|
return {
|
|
6548
6159
|
name: ref_0.name,
|
|
6549
6160
|
fullPath: ref_0.fullPath,
|
|
@@ -6568,38 +6179,84 @@ return result;
|
|
|
6568
6179
|
} finally {
|
|
6569
6180
|
setLoading(false);
|
|
6570
6181
|
}
|
|
6571
|
-
}, [
|
|
6182
|
+
}, []);
|
|
6572
6183
|
React.useEffect(() => {
|
|
6573
6184
|
fetchContents(currentPath);
|
|
6574
6185
|
}, [currentPath, fetchContents]);
|
|
6575
6186
|
const handleNavigate = React.useCallback((path_0) => {
|
|
6576
|
-
|
|
6187
|
+
if (!path_0) {
|
|
6188
|
+
setSearchParams({});
|
|
6189
|
+
} else {
|
|
6190
|
+
setSearchParams({
|
|
6191
|
+
path: path_0
|
|
6192
|
+
});
|
|
6193
|
+
}
|
|
6577
6194
|
setSelectedFile(null);
|
|
6578
6195
|
setSelectedDownloadUrl(null);
|
|
6579
|
-
|
|
6196
|
+
setSelectedPaths(/* @__PURE__ */ new Set());
|
|
6197
|
+
lastClickedRef.current = null;
|
|
6198
|
+
}, [setSearchParams]);
|
|
6580
6199
|
const handleNavigateUp = React.useCallback(() => {
|
|
6581
6200
|
const parts = currentPath.split("/").filter(Boolean);
|
|
6582
6201
|
parts.pop();
|
|
6583
6202
|
handleNavigate(parts.join("/"));
|
|
6584
6203
|
}, [currentPath, handleNavigate]);
|
|
6585
|
-
const
|
|
6586
|
-
|
|
6587
|
-
|
|
6588
|
-
|
|
6204
|
+
const allItems = React.useMemo(() => [...folders, ...files], [folders, files]);
|
|
6205
|
+
const handleItemClick = React.useCallback((item, e_0) => {
|
|
6206
|
+
const path_1 = item.fullPath;
|
|
6207
|
+
if (e_0.metaKey || e_0.ctrlKey) {
|
|
6208
|
+
setSelectedPaths((prev) => {
|
|
6209
|
+
const next = new Set(prev);
|
|
6210
|
+
if (next.has(path_1)) next.delete(path_1);
|
|
6211
|
+
else next.add(path_1);
|
|
6212
|
+
return next;
|
|
6213
|
+
});
|
|
6214
|
+
lastClickedRef.current = path_1;
|
|
6215
|
+
} else if (e_0.shiftKey && lastClickedRef.current) {
|
|
6216
|
+
const allPaths = allItems.map((i) => i.fullPath);
|
|
6217
|
+
const anchorIdx = allPaths.indexOf(lastClickedRef.current);
|
|
6218
|
+
const currentIdx = allPaths.indexOf(path_1);
|
|
6219
|
+
if (anchorIdx >= 0 && currentIdx >= 0) {
|
|
6220
|
+
const [start, end] = anchorIdx < currentIdx ? [anchorIdx, currentIdx] : [currentIdx, anchorIdx];
|
|
6221
|
+
setSelectedPaths((prev_0) => {
|
|
6222
|
+
const next_0 = new Set(prev_0);
|
|
6223
|
+
for (let i_0 = start; i_0 <= end; i_0++) next_0.add(allPaths[i_0]);
|
|
6224
|
+
return next_0;
|
|
6225
|
+
});
|
|
6226
|
+
}
|
|
6589
6227
|
} else {
|
|
6590
|
-
|
|
6591
|
-
|
|
6592
|
-
|
|
6593
|
-
|
|
6228
|
+
setSelectedPaths(/* @__PURE__ */ new Set([path_1]));
|
|
6229
|
+
lastClickedRef.current = path_1;
|
|
6230
|
+
if (!item.isFolder) {
|
|
6231
|
+
setSelectedFile(item);
|
|
6232
|
+
if (item.downloadUrl) {
|
|
6233
|
+
setSelectedDownloadUrl(item.downloadUrl);
|
|
6234
|
+
} else {
|
|
6235
|
+
storageSourceRef.current.getSignedUrl(item.fullPath).then((config) => setSelectedDownloadUrl(config.url)).catch(() => setSelectedDownloadUrl(null));
|
|
6236
|
+
}
|
|
6237
|
+
} else {
|
|
6238
|
+
setSelectedFile(null);
|
|
6594
6239
|
setSelectedDownloadUrl(null);
|
|
6595
6240
|
}
|
|
6596
6241
|
}
|
|
6597
|
-
}, [
|
|
6242
|
+
}, [allItems]);
|
|
6243
|
+
const handleItemDoubleClick = React.useCallback((item_0) => {
|
|
6244
|
+
if (item_0.isFolder) {
|
|
6245
|
+
handleNavigate(item_0.fullPath);
|
|
6246
|
+
} else {
|
|
6247
|
+
setSelectedFile(item_0);
|
|
6248
|
+
if (item_0.downloadUrl) {
|
|
6249
|
+
setSelectedDownloadUrl(item_0.downloadUrl);
|
|
6250
|
+
} else {
|
|
6251
|
+
storageSourceRef.current.getSignedUrl(item_0.fullPath).then((config_0) => setSelectedDownloadUrl(config_0.url)).catch(() => setSelectedDownloadUrl(null));
|
|
6252
|
+
}
|
|
6253
|
+
}
|
|
6254
|
+
}, [handleNavigate]);
|
|
6598
6255
|
const handleUpload = React.useCallback(async (uploadFiles) => {
|
|
6599
|
-
for (const
|
|
6600
|
-
const key = currentPath ? `${currentPath}/${
|
|
6601
|
-
await
|
|
6602
|
-
file
|
|
6256
|
+
for (const file of uploadFiles) {
|
|
6257
|
+
const key = currentPath ? `${currentPath}/${file.name}` : file.name;
|
|
6258
|
+
await storageSourceRef.current.putObject({
|
|
6259
|
+
file,
|
|
6603
6260
|
key
|
|
6604
6261
|
});
|
|
6605
6262
|
}
|
|
@@ -6607,25 +6264,220 @@ return result;
|
|
|
6607
6264
|
type: "success",
|
|
6608
6265
|
message: `${uploadFiles.length} file${uploadFiles.length > 1 ? "s" : ""} uploaded successfully`
|
|
6609
6266
|
});
|
|
6610
|
-
fetchContents(currentPath);
|
|
6611
|
-
}, [
|
|
6267
|
+
await fetchContents(currentPath);
|
|
6268
|
+
}, [currentPath, snackbarController, fetchContents]);
|
|
6269
|
+
const handleCreateFolder = React.useCallback(async () => {
|
|
6270
|
+
if (!newFolderName.trim() || !apiConfig?.apiUrl) return;
|
|
6271
|
+
const name = newFolderName.trim();
|
|
6272
|
+
if (name.includes("/") || name.includes("\\")) {
|
|
6273
|
+
snackbarController.open({
|
|
6274
|
+
type: "error",
|
|
6275
|
+
message: "Folder name cannot contain slashes"
|
|
6276
|
+
});
|
|
6277
|
+
return;
|
|
6278
|
+
}
|
|
6279
|
+
const existingFolder = folders.find((f) => f.name === name);
|
|
6280
|
+
if (existingFolder) {
|
|
6281
|
+
snackbarController.open({
|
|
6282
|
+
type: "error",
|
|
6283
|
+
message: `Folder "${name}" already exists`
|
|
6284
|
+
});
|
|
6285
|
+
return;
|
|
6286
|
+
}
|
|
6287
|
+
setCreatingFolder(true);
|
|
6288
|
+
try {
|
|
6289
|
+
const folderPath = currentPath ? `default/${currentPath}/${name}` : `default/${name}`;
|
|
6290
|
+
const token = apiConfig.getAuthToken ? await apiConfig.getAuthToken() : null;
|
|
6291
|
+
const response = await fetch(`${apiConfig.apiUrl}/api/storage/folder`, {
|
|
6292
|
+
method: "POST",
|
|
6293
|
+
headers: {
|
|
6294
|
+
"Content-Type": "application/json",
|
|
6295
|
+
...token ? {
|
|
6296
|
+
"Authorization": `Bearer ${token}`
|
|
6297
|
+
} : {}
|
|
6298
|
+
},
|
|
6299
|
+
body: JSON.stringify({
|
|
6300
|
+
path: folderPath
|
|
6301
|
+
})
|
|
6302
|
+
});
|
|
6303
|
+
if (!response.ok) {
|
|
6304
|
+
const err = await response.json().catch(() => ({
|
|
6305
|
+
error: "Failed to create folder"
|
|
6306
|
+
}));
|
|
6307
|
+
throw new Error(err.error || "Failed to create folder");
|
|
6308
|
+
}
|
|
6309
|
+
snackbarController.open({
|
|
6310
|
+
type: "success",
|
|
6311
|
+
message: `Folder "${name}" created`
|
|
6312
|
+
});
|
|
6313
|
+
setNewFolderDialogOpen(false);
|
|
6314
|
+
setNewFolderName("");
|
|
6315
|
+
await fetchContents(currentPath);
|
|
6316
|
+
} catch (e_1) {
|
|
6317
|
+
snackbarController.open({
|
|
6318
|
+
type: "error",
|
|
6319
|
+
message: e_1 instanceof Error ? e_1.message : String(e_1)
|
|
6320
|
+
});
|
|
6321
|
+
} finally {
|
|
6322
|
+
setCreatingFolder(false);
|
|
6323
|
+
}
|
|
6324
|
+
}, [newFolderName, currentPath, apiConfig, snackbarController, fetchContents, folders]);
|
|
6325
|
+
const handleDropFiles = React.useCallback(async (droppedFiles) => {
|
|
6326
|
+
if (droppedFiles.length === 0) return;
|
|
6327
|
+
try {
|
|
6328
|
+
for (const file_0 of droppedFiles) {
|
|
6329
|
+
const key_0 = currentPath ? `${currentPath}/${file_0.name}` : file_0.name;
|
|
6330
|
+
await storageSourceRef.current.putObject({
|
|
6331
|
+
file: file_0,
|
|
6332
|
+
key: key_0
|
|
6333
|
+
});
|
|
6334
|
+
}
|
|
6335
|
+
snackbarController.open({
|
|
6336
|
+
type: "success",
|
|
6337
|
+
message: `${droppedFiles.length} file${droppedFiles.length > 1 ? "s" : ""} uploaded successfully`
|
|
6338
|
+
});
|
|
6339
|
+
await fetchContents(currentPath);
|
|
6340
|
+
} catch (e_2) {
|
|
6341
|
+
snackbarController.open({
|
|
6342
|
+
type: "error",
|
|
6343
|
+
message: e_2 instanceof Error ? e_2.message : String(e_2)
|
|
6344
|
+
});
|
|
6345
|
+
}
|
|
6346
|
+
}, [currentPath, snackbarController, fetchContents]);
|
|
6347
|
+
const {
|
|
6348
|
+
getRootProps: getDropRootProps,
|
|
6349
|
+
getInputProps: getDropInputProps,
|
|
6350
|
+
isDragActive
|
|
6351
|
+
} = reactDropzone.useDropzone({
|
|
6352
|
+
onDrop: handleDropFiles,
|
|
6353
|
+
noClick: true,
|
|
6354
|
+
noKeyboard: true,
|
|
6355
|
+
noDragEventsBubbling: true
|
|
6356
|
+
});
|
|
6357
|
+
const deleteFolderRecursive = React.useCallback(async (prefix) => {
|
|
6358
|
+
const result_0 = await storageSourceRef.current.listObjects(prefix);
|
|
6359
|
+
for (const item_1 of result_0.items ?? []) {
|
|
6360
|
+
await storageSourceRef.current.deleteObject(item_1.fullPath);
|
|
6361
|
+
}
|
|
6362
|
+
for (const sub of result_0.prefixes ?? []) {
|
|
6363
|
+
await deleteFolderRecursive(sub.fullPath);
|
|
6364
|
+
}
|
|
6365
|
+
try {
|
|
6366
|
+
await storageSourceRef.current.deleteObject(prefix);
|
|
6367
|
+
} catch {
|
|
6368
|
+
}
|
|
6369
|
+
}, []);
|
|
6612
6370
|
const handleDeleteFile = React.useCallback(async (file_1) => {
|
|
6613
6371
|
try {
|
|
6614
|
-
|
|
6372
|
+
if (file_1.isFolder) {
|
|
6373
|
+
await deleteFolderRecursive(file_1.fullPath);
|
|
6374
|
+
} else {
|
|
6375
|
+
await storageSourceRef.current.deleteObject(file_1.fullPath);
|
|
6376
|
+
}
|
|
6615
6377
|
snackbarController.open({
|
|
6616
6378
|
type: "success",
|
|
6617
6379
|
message: `"${file_1.name}" deleted`
|
|
6618
6380
|
});
|
|
6619
6381
|
setSelectedFile(null);
|
|
6620
6382
|
setSelectedDownloadUrl(null);
|
|
6383
|
+
setSelectedPaths((prev_1) => {
|
|
6384
|
+
const next_1 = new Set(prev_1);
|
|
6385
|
+
next_1.delete(file_1.fullPath);
|
|
6386
|
+
return next_1;
|
|
6387
|
+
});
|
|
6621
6388
|
fetchContents(currentPath);
|
|
6622
|
-
} catch (
|
|
6389
|
+
} catch (e_3) {
|
|
6623
6390
|
snackbarController.open({
|
|
6624
6391
|
type: "error",
|
|
6625
|
-
message:
|
|
6392
|
+
message: e_3 instanceof Error ? e_3.message : String(e_3)
|
|
6626
6393
|
});
|
|
6627
6394
|
}
|
|
6628
|
-
}, [
|
|
6395
|
+
}, [currentPath, snackbarController, fetchContents, deleteFolderRecursive]);
|
|
6396
|
+
const handleBulkDelete = React.useCallback(async () => {
|
|
6397
|
+
setDeleting(true);
|
|
6398
|
+
try {
|
|
6399
|
+
const items = allItems.filter((i_1) => selectedPaths.has(i_1.fullPath));
|
|
6400
|
+
for (const item_2 of items) {
|
|
6401
|
+
if (item_2.isFolder) {
|
|
6402
|
+
await deleteFolderRecursive(item_2.fullPath);
|
|
6403
|
+
} else {
|
|
6404
|
+
await storageSourceRef.current.deleteObject(item_2.fullPath);
|
|
6405
|
+
}
|
|
6406
|
+
}
|
|
6407
|
+
snackbarController.open({
|
|
6408
|
+
type: "success",
|
|
6409
|
+
message: `${items.length} item${items.length !== 1 ? "s" : ""} deleted`
|
|
6410
|
+
});
|
|
6411
|
+
setSelectedPaths(/* @__PURE__ */ new Set());
|
|
6412
|
+
setSelectedFile(null);
|
|
6413
|
+
setSelectedDownloadUrl(null);
|
|
6414
|
+
await fetchContents(currentPath);
|
|
6415
|
+
} catch (e_4) {
|
|
6416
|
+
snackbarController.open({
|
|
6417
|
+
type: "error",
|
|
6418
|
+
message: e_4 instanceof Error ? e_4.message : String(e_4)
|
|
6419
|
+
});
|
|
6420
|
+
} finally {
|
|
6421
|
+
setDeleting(false);
|
|
6422
|
+
setDeleteDialogOpen(false);
|
|
6423
|
+
setDeleteDialogTarget(null);
|
|
6424
|
+
}
|
|
6425
|
+
}, [allItems, selectedPaths, currentPath, snackbarController, fetchContents, deleteFolderRecursive]);
|
|
6426
|
+
const handleConfirmDeleteFolder = React.useCallback(async () => {
|
|
6427
|
+
if (!deleteDialogTarget || deleteDialogTarget === "selection") return;
|
|
6428
|
+
setDeleting(true);
|
|
6429
|
+
try {
|
|
6430
|
+
await deleteFolderRecursive(deleteDialogTarget.fullPath);
|
|
6431
|
+
snackbarController.open({
|
|
6432
|
+
type: "success",
|
|
6433
|
+
message: `Folder "${deleteDialogTarget.name}" deleted`
|
|
6434
|
+
});
|
|
6435
|
+
setSelectedPaths((prev_2) => {
|
|
6436
|
+
const next_2 = new Set(prev_2);
|
|
6437
|
+
next_2.delete(deleteDialogTarget.fullPath);
|
|
6438
|
+
return next_2;
|
|
6439
|
+
});
|
|
6440
|
+
await fetchContents(currentPath);
|
|
6441
|
+
} catch (e_5) {
|
|
6442
|
+
snackbarController.open({
|
|
6443
|
+
type: "error",
|
|
6444
|
+
message: e_5 instanceof Error ? e_5.message : String(e_5)
|
|
6445
|
+
});
|
|
6446
|
+
} finally {
|
|
6447
|
+
setDeleting(false);
|
|
6448
|
+
setDeleteDialogOpen(false);
|
|
6449
|
+
setDeleteDialogTarget(null);
|
|
6450
|
+
}
|
|
6451
|
+
}, [deleteDialogTarget, currentPath, snackbarController, fetchContents, deleteFolderRecursive]);
|
|
6452
|
+
const handleSelectAll = React.useCallback(() => {
|
|
6453
|
+
if (selectedPaths.size === allItems.length) {
|
|
6454
|
+
setSelectedPaths(/* @__PURE__ */ new Set());
|
|
6455
|
+
} else {
|
|
6456
|
+
setSelectedPaths(new Set(allItems.map((i_2) => i_2.fullPath)));
|
|
6457
|
+
}
|
|
6458
|
+
}, [allItems, selectedPaths]);
|
|
6459
|
+
React.useEffect(() => {
|
|
6460
|
+
const handler = (e_6) => {
|
|
6461
|
+
if (deleteDialogOpen || uploadDialogOpen || newFolderDialogOpen) return;
|
|
6462
|
+
if ((e_6.metaKey || e_6.ctrlKey) && e_6.key === "a") {
|
|
6463
|
+
e_6.preventDefault();
|
|
6464
|
+
handleSelectAll();
|
|
6465
|
+
}
|
|
6466
|
+
if (e_6.key === "Escape") {
|
|
6467
|
+
setSelectedPaths(/* @__PURE__ */ new Set());
|
|
6468
|
+
setSelectedFile(null);
|
|
6469
|
+
setSelectedDownloadUrl(null);
|
|
6470
|
+
}
|
|
6471
|
+
if ((e_6.key === "Delete" || e_6.key === "Backspace") && selectedPaths.size > 0 && !e_6.metaKey && !e_6.ctrlKey) {
|
|
6472
|
+
if (e_6.target?.tagName === "INPUT" || e_6.target?.tagName === "TEXTAREA") return;
|
|
6473
|
+
e_6.preventDefault();
|
|
6474
|
+
setDeleteDialogTarget("selection");
|
|
6475
|
+
setDeleteDialogOpen(true);
|
|
6476
|
+
}
|
|
6477
|
+
};
|
|
6478
|
+
window.addEventListener("keydown", handler);
|
|
6479
|
+
return () => window.removeEventListener("keydown", handler);
|
|
6480
|
+
}, [handleSelectAll, selectedPaths, deleteDialogOpen, uploadDialogOpen, newFolderDialogOpen]);
|
|
6629
6481
|
const handleRefresh = React.useCallback(() => {
|
|
6630
6482
|
fetchContents(currentPath);
|
|
6631
6483
|
}, [currentPath, fetchContents]);
|
|
@@ -6640,43 +6492,74 @@ return result;
|
|
|
6640
6492
|
if (error) {
|
|
6641
6493
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow flex items-center justify-center p-6 overflow-auto", children: /* @__PURE__ */ jsxRuntime.jsx(core.ErrorView, { title: "Error loading storage", error, onRetry: handleRefresh }) });
|
|
6642
6494
|
}
|
|
6643
|
-
const allItems = [...folders, ...files];
|
|
6644
6495
|
if (allItems.length === 0) {
|
|
6645
6496
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow flex items-center justify-center text-text-disabled dark:text-text-disabled-dark", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "text-center", children: [
|
|
6646
6497
|
/* @__PURE__ */ jsxRuntime.jsx("svg", { className: "w-12 h-12 mx-auto mb-4 opacity-50", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ jsxRuntime.jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 1, d: "M3 7v10a2 2 0 002 2h14a2 2 0 002-2V9a2 2 0 00-2-2h-6l-2-2H5a2 2 0 00-2 2z" }) }),
|
|
6647
6498
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", children: "This folder is empty" }),
|
|
6648
|
-
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
6649
|
-
/* @__PURE__ */ jsxRuntime.
|
|
6650
|
-
|
|
6499
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2 mt-3", children: [
|
|
6500
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { variant: "text", onClick: () => {
|
|
6501
|
+
setNewFolderName("");
|
|
6502
|
+
setNewFolderDialogOpen(true);
|
|
6503
|
+
}, children: [
|
|
6504
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderPlusIcon, { size: ui.iconSize.smallest }),
|
|
6505
|
+
"New folder"
|
|
6506
|
+
] }),
|
|
6507
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { onClick: () => setUploadDialogOpen(true), children: [
|
|
6508
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.PlusIcon, { size: ui.iconSize.smallest }),
|
|
6509
|
+
"Upload files"
|
|
6510
|
+
] })
|
|
6651
6511
|
] })
|
|
6652
6512
|
] }) });
|
|
6653
6513
|
}
|
|
6654
6514
|
if (viewMode === "list") {
|
|
6655
6515
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow overflow-auto", children: /* @__PURE__ */ jsxRuntime.jsxs("table", { className: "w-full", children: [
|
|
6656
6516
|
/* @__PURE__ */ jsxRuntime.jsx("thead", { children: /* @__PURE__ */ jsxRuntime.jsxs("tr", { className: ui.cls("border-b text-left text-[10px] uppercase tracking-wider text-text-disabled dark:text-text-disabled-dark", ui.defaultBorderMixin), children: [
|
|
6657
|
-
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "
|
|
6517
|
+
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "pl-3 pr-0 py-2 w-8", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Checkbox, { size: "small", checked: allItems.length > 0 && selectedPaths.size === allItems.length, indeterminate: selectedPaths.size > 0 && selectedPaths.size < allItems.length, onCheckedChange: handleSelectAll }) }),
|
|
6518
|
+
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "px-2 py-2 font-bold", children: "Name" }),
|
|
6658
6519
|
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "px-4 py-2 font-bold w-24", children: "Type" }),
|
|
6659
|
-
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "px-4 py-2 font-bold w-24 text-right", children: "Size" })
|
|
6520
|
+
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "px-4 py-2 font-bold w-24 text-right", children: "Size" }),
|
|
6521
|
+
/* @__PURE__ */ jsxRuntime.jsx("th", { className: "px-2 py-2 w-10" })
|
|
6660
6522
|
] }) }),
|
|
6661
6523
|
/* @__PURE__ */ jsxRuntime.jsxs("tbody", { children: [
|
|
6662
|
-
folders.map((folder) =>
|
|
6663
|
-
|
|
6664
|
-
|
|
6665
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
6666
|
-
|
|
6667
|
-
|
|
6668
|
-
|
|
6669
|
-
|
|
6524
|
+
folders.map((folder) => {
|
|
6525
|
+
const isChecked = selectedPaths.has(folder.fullPath);
|
|
6526
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("tr", { "data-storage-item": true, className: ui.cls("cursor-pointer transition-colors border-b group", ui.defaultBorderMixin, isChecked ? "bg-primary/5 dark:bg-primary/10" : "hover:bg-surface-100 dark:hover:bg-surface-800"), onClick: (e_7) => handleItemClick(folder, e_7), onDoubleClick: () => handleItemDoubleClick(folder), children: [
|
|
6527
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "pl-3 pr-0 py-2.5", onClick: (e_8) => e_8.stopPropagation(), children: /* @__PURE__ */ jsxRuntime.jsx(ui.Checkbox, { size: "small", checked: isChecked, onCheckedChange: () => {
|
|
6528
|
+
setSelectedPaths((prev_3) => {
|
|
6529
|
+
const next_3 = new Set(prev_3);
|
|
6530
|
+
if (next_3.has(folder.fullPath)) next_3.delete(folder.fullPath);
|
|
6531
|
+
else next_3.add(folder.fullPath);
|
|
6532
|
+
return next_3;
|
|
6533
|
+
});
|
|
6534
|
+
} }) }),
|
|
6535
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-2 py-2.5", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
6536
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderIcon, { size: ui.iconSize.smallest, className: "text-amber-500 dark:text-amber-400 shrink-0" }),
|
|
6537
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] font-medium truncate", children: folder.name })
|
|
6538
|
+
] }) }),
|
|
6539
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-4 py-2.5", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark", children: "Folder" }) }),
|
|
6540
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-4 py-2.5 text-right", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark", children: "—" }) }),
|
|
6541
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-2 py-2.5" })
|
|
6542
|
+
] }, folder.fullPath);
|
|
6543
|
+
}),
|
|
6670
6544
|
files.map((file_2) => {
|
|
6671
6545
|
const FileIconComp = getFileIcon(file_2.contentType);
|
|
6672
|
-
const
|
|
6673
|
-
return /* @__PURE__ */ jsxRuntime.jsxs("tr", { className: ui.cls("cursor-pointer transition-colors border-b
|
|
6674
|
-
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "
|
|
6546
|
+
const isChecked_0 = selectedPaths.has(file_2.fullPath);
|
|
6547
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("tr", { "data-storage-item": true, className: ui.cls("cursor-pointer transition-colors border-b group", ui.defaultBorderMixin, isChecked_0 ? "bg-primary/5 dark:bg-primary/10" : "hover:bg-surface-100 dark:hover:bg-surface-800"), onClick: (e_9) => handleItemClick(file_2, e_9), onDoubleClick: () => handleItemDoubleClick(file_2), children: [
|
|
6548
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "pl-3 pr-0 py-2.5", onClick: (e_10) => e_10.stopPropagation(), children: /* @__PURE__ */ jsxRuntime.jsx(ui.Checkbox, { size: "small", checked: isChecked_0, onCheckedChange: () => {
|
|
6549
|
+
setSelectedPaths((prev_4) => {
|
|
6550
|
+
const next_4 = new Set(prev_4);
|
|
6551
|
+
if (next_4.has(file_2.fullPath)) next_4.delete(file_2.fullPath);
|
|
6552
|
+
else next_4.add(file_2.fullPath);
|
|
6553
|
+
return next_4;
|
|
6554
|
+
});
|
|
6555
|
+
} }) }),
|
|
6556
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-2 py-2.5", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
6675
6557
|
/* @__PURE__ */ jsxRuntime.jsx(FileIconComp, { size: ui.iconSize.smallest, className: "text-surface-accent-400 shrink-0" }),
|
|
6676
6558
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] truncate", children: file_2.name })
|
|
6677
6559
|
] }) }),
|
|
6678
6560
|
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-4 py-2.5", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark", children: getExtension(file_2.name) || file_2.contentType?.split("/")[1]?.toUpperCase() || "—" }) }),
|
|
6679
|
-
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-4 py-2.5 text-right", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark font-mono text-[11px]", children: file_2.size !== void 0 ? formatFileSize(file_2.size) : "—" }) })
|
|
6561
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-4 py-2.5 text-right", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark font-mono text-[11px]", children: file_2.size !== void 0 ? formatFileSize(file_2.size) : "—" }) }),
|
|
6562
|
+
/* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-2 py-2.5", onClick: (e_11) => e_11.stopPropagation(), children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "smallest", className: "opacity-0 group-hover:opacity-100 transition-opacity", onClick: () => handleDeleteFile(file_2), children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2Icon, { size: 14 }) }) })
|
|
6680
6563
|
] }, file_2.fullPath);
|
|
6681
6564
|
})
|
|
6682
6565
|
] })
|
|
@@ -6685,10 +6568,13 @@ return result;
|
|
|
6685
6568
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-grow overflow-auto p-4", children: [
|
|
6686
6569
|
folders.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "mb-4", children: [
|
|
6687
6570
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-[10px] uppercase tracking-wider font-bold text-text-disabled dark:text-text-disabled-dark mb-2 block", children: "Folders" }),
|
|
6688
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid
|
|
6689
|
-
|
|
6690
|
-
/* @__PURE__ */ jsxRuntime.
|
|
6691
|
-
|
|
6571
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid gap-3 grid-cols-[repeat(auto-fill,minmax(140px,1fr))]", children: folders.map((folder_0) => {
|
|
6572
|
+
const isChecked_1 = selectedPaths.has(folder_0.fullPath);
|
|
6573
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { "data-storage-item": true, className: ui.cls("rounded-lg p-3 cursor-pointer border", "transition-colors duration-150", ui.defaultBorderMixin, "hover:bg-surface-100 dark:hover:bg-surface-800 hover:shadow-sm", "flex items-center gap-2", isChecked_1 && "ring-2 ring-primary bg-primary/5 dark:bg-primary/10"), onClick: (e_12) => handleItemClick(folder_0, e_12), onDoubleClick: () => handleItemDoubleClick(folder_0), children: [
|
|
6574
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderIcon, { size: ui.iconSize.smallest, className: "text-amber-500 dark:text-amber-400 shrink-0" }),
|
|
6575
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[13px] font-medium truncate", children: folder_0.name })
|
|
6576
|
+
] }, folder_0.fullPath);
|
|
6577
|
+
}) })
|
|
6692
6578
|
] }),
|
|
6693
6579
|
files.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
6694
6580
|
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", className: "text-[10px] uppercase tracking-wider font-bold text-text-disabled dark:text-text-disabled-dark mb-2 block", children: [
|
|
@@ -6696,16 +6582,15 @@ return result;
|
|
|
6696
6582
|
files.length,
|
|
6697
6583
|
")"
|
|
6698
6584
|
] }),
|
|
6699
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid
|
|
6585
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "grid gap-3 grid-cols-[repeat(auto-fill,minmax(140px,1fr))]", children: files.map((file_3) => {
|
|
6700
6586
|
const FileIconComp_0 = getFileIcon(file_3.contentType);
|
|
6701
6587
|
const ext = getExtension(file_3.name)?.toLowerCase() || "";
|
|
6702
6588
|
const isImage = file_3.contentType?.startsWith("image/") || ["jpg", "jpeg", "png", "gif", "webp", "svg"].includes(ext);
|
|
6703
|
-
const
|
|
6704
|
-
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("rounded-lg overflow-hidden cursor-pointer transition-
|
|
6705
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "aspect-square relative overflow-hidden bg-surface-100 dark:bg-surface-
|
|
6706
|
-
isImage && file_3.downloadUrl ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: file_3.downloadUrl, alt: file_3.name, className: "w-full h-full object-cover
|
|
6707
|
-
getExtension(file_3.name) && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "absolute bottom-1.5 right-1.5 px-1.5 py-0.5 rounded text-[9px] font-bold uppercase bg-black/50 text-white backdrop-blur-sm", children: getExtension(file_3.name) })
|
|
6708
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: ui.cls("absolute inset-0 bg-black/0 group-hover:bg-black/10", "transition-colors duration-200") })
|
|
6589
|
+
const isChecked_2 = selectedPaths.has(file_3.fullPath);
|
|
6590
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { "data-storage-item": true, className: ui.cls("rounded-lg overflow-hidden cursor-pointer border", "transition-shadow duration-150", ui.defaultBorderMixin, "hover:shadow-md", isChecked_2 && "ring-2 ring-primary"), onClick: (e_13) => handleItemClick(file_3, e_13), onDoubleClick: () => handleItemDoubleClick(file_3), children: [
|
|
6591
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "aspect-square relative overflow-hidden bg-surface-100 dark:bg-surface-800 flex items-center justify-center", children: [
|
|
6592
|
+
isImage && file_3.downloadUrl ? /* @__PURE__ */ jsxRuntime.jsx("img", { src: file_3.downloadUrl, alt: file_3.name, className: "w-full h-full object-cover", loading: "lazy" }) : /* @__PURE__ */ jsxRuntime.jsx(FileIconComp_0, { className: "text-surface-accent-400 dark:text-surface-accent-500 w-8 h-8" }),
|
|
6593
|
+
getExtension(file_3.name) && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "absolute bottom-1.5 right-1.5 px-1.5 py-0.5 rounded text-[9px] font-bold uppercase bg-black/50 text-white backdrop-blur-sm", children: getExtension(file_3.name) })
|
|
6709
6594
|
] }),
|
|
6710
6595
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "p-2.5", children: [
|
|
6711
6596
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", className: "text-[12px] font-medium truncate text-surface-900 dark:text-white", children: file_3.name }),
|
|
@@ -6716,37 +6601,79 @@ return result;
|
|
|
6716
6601
|
] })
|
|
6717
6602
|
] });
|
|
6718
6603
|
};
|
|
6719
|
-
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex h-full w-full bg-white dark:bg-surface-
|
|
6720
|
-
/* @__PURE__ */ jsxRuntime.
|
|
6604
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex h-full w-full bg-white dark:bg-surface-800 overflow-hidden text-text-primary dark:text-text-primary-dark", children: [
|
|
6605
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex h-full w-full", children: [
|
|
6721
6606
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-grow flex flex-col min-w-0 h-full", children: [
|
|
6722
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex items-center justify-between pr-2 border-b bg-white dark:bg-surface-
|
|
6607
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex items-center justify-between pr-2 border-b bg-white dark:bg-surface-800 shrink-0 h-10", ui.defaultBorderMixin), children: [
|
|
6723
6608
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1.5 flex-grow overflow-hidden px-3 py-2", children: [
|
|
6724
6609
|
currentPath && /* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Go up", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: handleNavigateUp, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ArrowLeftIcon, { size: ui.iconSize.smallest }) }) }),
|
|
6725
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center gap-0.5 overflow-x-auto no-scrollbar", children: segments.map((seg,
|
|
6726
|
-
|
|
6727
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", size: "small", className: ui.cls("px-1.5 py-0.5 min-h-0 min-w-0 h-6 text-xs whitespace-nowrap normal-case font-normal",
|
|
6610
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center gap-0.5 overflow-x-auto no-scrollbar", children: segments.map((seg, i_3) => /* @__PURE__ */ jsxRuntime.jsxs(React.Fragment, { children: [
|
|
6611
|
+
i_3 > 0 && /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-disabled dark:text-text-disabled-dark mx-0.5", children: "/" }),
|
|
6612
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", size: "small", className: ui.cls("px-1.5 py-0.5 min-h-0 min-w-0 h-6 text-xs whitespace-nowrap normal-case font-normal", i_3 === segments.length - 1 ? "text-text-primary dark:text-text-primary-dark font-medium" : "text-text-secondary dark:text-text-secondary-dark"), onClick: () => handleNavigate(seg.path), children: seg.label })
|
|
6728
6613
|
] }, seg.path)) }),
|
|
6729
6614
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-1" }),
|
|
6730
|
-
|
|
6615
|
+
selectedPaths.size > 0 ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-1.5 shrink-0", children: [
|
|
6616
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "body2", className: "text-[13px] font-medium whitespace-nowrap", children: [
|
|
6617
|
+
selectedPaths.size,
|
|
6618
|
+
" selected"
|
|
6619
|
+
] }),
|
|
6620
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { size: "small", variant: "text", onClick: () => {
|
|
6621
|
+
setDeleteDialogTarget("selection");
|
|
6622
|
+
setDeleteDialogOpen(true);
|
|
6623
|
+
}, children: [
|
|
6624
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2Icon, { size: 14, className: "mr-1" }),
|
|
6625
|
+
"Delete"
|
|
6626
|
+
] }),
|
|
6627
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { size: "small", variant: "text", onClick: () => {
|
|
6628
|
+
setSelectedPaths(/* @__PURE__ */ new Set());
|
|
6629
|
+
setSelectedFile(null);
|
|
6630
|
+
setSelectedDownloadUrl(null);
|
|
6631
|
+
}, children: [
|
|
6632
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.XIcon, { size: 14, className: "mr-1" }),
|
|
6633
|
+
"Deselect"
|
|
6634
|
+
] })
|
|
6635
|
+
] }) : !loading ? /* @__PURE__ */ jsxRuntime.jsxs(ui.Chip, { size: "small", className: "shrink-0 text-[10px]", children: [
|
|
6731
6636
|
files.length,
|
|
6732
6637
|
" file",
|
|
6733
6638
|
files.length !== 1 ? "s" : "",
|
|
6734
6639
|
folders.length > 0 ? `, ${folders.length} folder${folders.length !== 1 ? "s" : ""}` : ""
|
|
6735
|
-
] })
|
|
6640
|
+
] }) : null
|
|
6736
6641
|
] }),
|
|
6737
6642
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex shrink-0 items-center justify-end gap-1.5 pr-1", children: [
|
|
6738
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Grid view", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => setViewMode("grid"), className: ui.cls(viewMode === "grid" && "bg-surface-100 dark:bg-surface-
|
|
6739
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "List view", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => setViewMode("list"), className: ui.cls(viewMode === "list" && "bg-surface-100 dark:bg-surface-
|
|
6740
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-4 w-px bg-surface-200 dark:bg-surface-
|
|
6643
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Grid view", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => setViewMode("grid"), className: ui.cls(viewMode === "grid" && "bg-surface-100 dark:bg-surface-800"), children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.LayoutGridIcon, { size: ui.iconSize.smallest }) }) }),
|
|
6644
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "List view", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => setViewMode("list"), className: ui.cls(viewMode === "list" && "bg-surface-100 dark:bg-surface-800"), children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ListIcon, { size: ui.iconSize.smallest }) }) }),
|
|
6645
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: ui.cls("h-4 w-px mx-0.5", ui.defaultBorderMixin, "bg-surface-200 dark:bg-surface-700") }),
|
|
6741
6646
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Refresh", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: handleRefresh, disabled: loading, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.RefreshCwIcon, { size: ui.iconSize.smallest }) }) }),
|
|
6647
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "New folder", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => {
|
|
6648
|
+
setNewFolderName("");
|
|
6649
|
+
setNewFolderDialogOpen(true);
|
|
6650
|
+
}, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderPlusIcon, { size: ui.iconSize.smallest }) }) }),
|
|
6742
6651
|
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { size: "small", color: "primary", onClick: () => setUploadDialogOpen(true), children: [
|
|
6743
6652
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.UploadCloudIcon, { size: ui.iconSize.smallest, className: "mr-1" }),
|
|
6744
6653
|
"Upload"
|
|
6745
6654
|
] })
|
|
6746
6655
|
] })
|
|
6747
6656
|
] }),
|
|
6748
|
-
/* @__PURE__ */ jsxRuntime.
|
|
6749
|
-
|
|
6657
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { ...getDropRootProps(), className: "flex-grow flex flex-col overflow-hidden min-h-0 relative", onClick: (e_14) => {
|
|
6658
|
+
const target = e_14.target;
|
|
6659
|
+
if (!target.closest("[data-storage-item]") && selectedPaths.size > 0) {
|
|
6660
|
+
setSelectedPaths(/* @__PURE__ */ new Set());
|
|
6661
|
+
setSelectedFile(null);
|
|
6662
|
+
setSelectedDownloadUrl(null);
|
|
6663
|
+
}
|
|
6664
|
+
}, children: [
|
|
6665
|
+
/* @__PURE__ */ jsxRuntime.jsx("input", { ...getDropInputProps() }),
|
|
6666
|
+
renderContents(),
|
|
6667
|
+
isDragActive && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "absolute inset-0 z-10 flex items-center justify-center bg-primary/5 dark:bg-primary/10 backdrop-blur-[2px]", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col items-center gap-2 p-6 rounded-xl border-2 border-dashed border-primary bg-white/80 dark:bg-surface-900/80", children: [
|
|
6668
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.UploadCloudIcon, { className: "w-10 h-10 text-primary" }),
|
|
6669
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle2", className: "text-primary font-semibold", children: "Drop files to upload" }),
|
|
6670
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", color: "secondary", children: [
|
|
6671
|
+
"to /",
|
|
6672
|
+
currentPath || "root"
|
|
6673
|
+
] })
|
|
6674
|
+
] }) })
|
|
6675
|
+
] }),
|
|
6676
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("px-4 py-1.5 border-t bg-surface-50 dark:bg-surface-800 flex items-center justify-between shrink-0", ui.defaultBorderMixin), children: [
|
|
6750
6677
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-4 text-[11px]", children: [
|
|
6751
6678
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-text-disabled dark:text-text-disabled-dark font-bold uppercase tracking-tighter", children: "Path" }),
|
|
6752
6679
|
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "font-mono text-text-secondary dark:text-text-secondary-dark", children: [
|
|
@@ -6754,18 +6681,78 @@ return result;
|
|
|
6754
6681
|
currentPath || ""
|
|
6755
6682
|
] })
|
|
6756
6683
|
] }),
|
|
6757
|
-
|
|
6684
|
+
selectedPaths.size > 0 ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "text-[11px] text-text-secondary dark:text-text-secondary-dark", children: [
|
|
6685
|
+
selectedPaths.size,
|
|
6686
|
+
" item",
|
|
6687
|
+
selectedPaths.size !== 1 ? "s" : "",
|
|
6688
|
+
" selected"
|
|
6689
|
+
] }) : selectedFile ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "text-[11px] text-text-secondary dark:text-text-secondary-dark", children: [
|
|
6758
6690
|
"Selected: ",
|
|
6759
6691
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "font-mono", children: selectedFile.name })
|
|
6760
|
-
] })
|
|
6692
|
+
] }) : null
|
|
6761
6693
|
] })
|
|
6762
6694
|
] }),
|
|
6763
6695
|
selectedFile && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-80 lg:w-96 shrink-0", children: /* @__PURE__ */ jsxRuntime.jsx(FilePreviewPanel, { file: selectedFile, downloadUrl: selectedDownloadUrl, onClose: () => {
|
|
6764
6696
|
setSelectedFile(null);
|
|
6765
6697
|
setSelectedDownloadUrl(null);
|
|
6766
6698
|
}, onDelete: () => handleDeleteFile(selectedFile) }) })
|
|
6767
|
-
] })
|
|
6768
|
-
/* @__PURE__ */ jsxRuntime.jsx(UploadDialog, { open: uploadDialogOpen, currentPath, onClose: () => setUploadDialogOpen(false), onUpload: handleUpload })
|
|
6699
|
+
] }),
|
|
6700
|
+
/* @__PURE__ */ jsxRuntime.jsx(UploadDialog, { open: uploadDialogOpen, currentPath, onClose: () => setUploadDialogOpen(false), onUpload: handleUpload }),
|
|
6701
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Dialog, { open: deleteDialogOpen, onOpenChange: (open) => {
|
|
6702
|
+
if (!open && !deleting) {
|
|
6703
|
+
setDeleteDialogOpen(false);
|
|
6704
|
+
setDeleteDialogTarget(null);
|
|
6705
|
+
}
|
|
6706
|
+
}, children: [
|
|
6707
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { children: [
|
|
6708
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle1", className: "font-semibold mb-2", children: deleteDialogTarget === "selection" ? `Delete ${selectedPaths.size} item${selectedPaths.size !== 1 ? "s" : ""}?` : deleteDialogTarget ? `Delete folder "${deleteDialogTarget.name}"?` : "Delete?" }),
|
|
6709
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "body2", color: "secondary", children: deleteDialogTarget === "selection" ? "This will permanently delete all selected files and folders, including their contents. This action cannot be undone." : "This will permanently delete the folder and all of its contents. This action cannot be undone." })
|
|
6710
|
+
] }),
|
|
6711
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogActions, { children: [
|
|
6712
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", onClick: () => {
|
|
6713
|
+
setDeleteDialogOpen(false);
|
|
6714
|
+
setDeleteDialogTarget(null);
|
|
6715
|
+
}, disabled: deleting, children: "Cancel" }),
|
|
6716
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { color: "error", loading: deleting, onClick: deleteDialogTarget === "selection" ? handleBulkDelete : handleConfirmDeleteFolder, children: [
|
|
6717
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Trash2Icon, { size: 14, className: "mr-1" }),
|
|
6718
|
+
"Delete"
|
|
6719
|
+
] })
|
|
6720
|
+
] })
|
|
6721
|
+
] }),
|
|
6722
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Dialog, { open: newFolderDialogOpen, onOpenChange: (open_0) => {
|
|
6723
|
+
if (!open_0 && !creatingFolder) {
|
|
6724
|
+
setNewFolderDialogOpen(false);
|
|
6725
|
+
setNewFolderName("");
|
|
6726
|
+
}
|
|
6727
|
+
}, children: [
|
|
6728
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { children: [
|
|
6729
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle1", className: "font-semibold mb-4", children: "New Folder" }),
|
|
6730
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { autoFocus: true, size: "small", label: "Folder name", value: newFolderName, onChange: (e_15) => setNewFolderName(e_15.target.value), onKeyDown: (e_16) => {
|
|
6731
|
+
if (e_16.key === "Enter" && newFolderName.trim()) {
|
|
6732
|
+
e_16.preventDefault();
|
|
6733
|
+
handleCreateFolder();
|
|
6734
|
+
}
|
|
6735
|
+
}, disabled: creatingFolder, placeholder: "Enter folder name" }),
|
|
6736
|
+
currentPath && /* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", color: "secondary", className: "mt-2", children: [
|
|
6737
|
+
"Will be created in ",
|
|
6738
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "font-mono", children: [
|
|
6739
|
+
"/",
|
|
6740
|
+
currentPath,
|
|
6741
|
+
"/"
|
|
6742
|
+
] })
|
|
6743
|
+
] })
|
|
6744
|
+
] }),
|
|
6745
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogActions, { children: [
|
|
6746
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", onClick: () => {
|
|
6747
|
+
setNewFolderDialogOpen(false);
|
|
6748
|
+
setNewFolderName("");
|
|
6749
|
+
}, disabled: creatingFolder, children: "Cancel" }),
|
|
6750
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { color: "primary", loading: creatingFolder, disabled: !newFolderName.trim(), onClick: handleCreateFolder, children: [
|
|
6751
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FolderPlusIcon, { size: 14, className: "mr-1" }),
|
|
6752
|
+
"Create"
|
|
6753
|
+
] })
|
|
6754
|
+
] })
|
|
6755
|
+
] })
|
|
6769
6756
|
] });
|
|
6770
6757
|
};
|
|
6771
6758
|
const StorageView$1 = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
@@ -8127,7 +8114,7 @@ return result;
|
|
|
8127
8114
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "font-bold uppercase tracking-wider text-text-disabled dark:text-text-disabled-dark", children: "Tables" }),
|
|
8128
8115
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-[10px] text-text-disabled dark:text-text-disabled-dark font-mono", children: stats.tables })
|
|
8129
8116
|
] }),
|
|
8130
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "px-2 py-1.5 border-b border-surface-200/40 dark:border-surface-700/40", children: /* @__PURE__ */ jsxRuntime.jsx(ui.
|
|
8117
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "px-2 py-1.5 border-b border-surface-200/40 dark:border-surface-700/40", children: /* @__PURE__ */ jsxRuntime.jsx(ui.SearchBar, { size: "smallest", placeholder: "Filter tables…", onTextSearch: (val) => setSearchQuery(val ?? ""), innerClassName: "text-xs" }) }),
|
|
8131
8118
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-grow overflow-y-auto no-scrollbar p-1", children: [
|
|
8132
8119
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "space-y-0.5", children: filteredCollections.map((collection) => {
|
|
8133
8120
|
const table = collection.table ?? collection.slug;
|
|
@@ -8183,8 +8170,8 @@ return result;
|
|
|
8183
8170
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-center gap-2 px-4", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "subtitle2", className: "font-mono text-text-secondary dark:text-text-secondary-dark", children: "Schema Visualizer" }) }),
|
|
8184
8171
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex shrink-0 items-center gap-1.5", children: [
|
|
8185
8172
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center bg-surface-100 dark:bg-surface-950 rounded-md border border-surface-200/40 dark:border-surface-700/40", children: [
|
|
8186
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Left to right layout", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
8187
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Top to bottom layout", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
8173
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Left to right layout", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "small", variant: direction === "LR" ? "filled" : "text", color: direction === "LR" ? "primary" : "neutral", onClick: () => setDirection("LR"), className: "!rounded-r-none !px-2 !py-1 !text-[10px] !font-mono", children: "LR" }) }),
|
|
8174
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Top to bottom layout", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "small", variant: direction === "TB" ? "filled" : "text", color: direction === "TB" ? "primary" : "neutral", onClick: () => setDirection("TB"), className: "!rounded-l-none !px-2 !py-1 !text-[10px] !font-mono", children: "TB" }) })
|
|
8188
8175
|
] }),
|
|
8189
8176
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-4 w-px bg-surface-200 dark:bg-surface-950 mx-0.5" }),
|
|
8190
8177
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Fit to view", children: /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: handleFitView, children: /* @__PURE__ */ jsxRuntime.jsx("svg", { className: "w-4 h-4", fill: "none", stroke: "currentColor", viewBox: "0 0 24 24", children: /* @__PURE__ */ jsxRuntime.jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 8V4m0 0h4M4 4l5 5m11-1V4m0 0h-4m4 0l-5 5M4 16v4m0 0h4m-4 0l5-5m11 5l-5-5m5 5v-4m0 4h-4" }) }) }) }),
|
|
@@ -9212,10 +9199,10 @@ return result;
|
|
|
9212
9199
|
} }),
|
|
9213
9200
|
hasBody && /* @__PURE__ */ jsxRuntime.jsxs("div", { children: [
|
|
9214
9201
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-text-secondary dark:text-text-secondary-dark text-xs font-semibold uppercase tracking-wider mb-2 block", children: "Request Body" }),
|
|
9215
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
9202
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { multiline: true, minRows: 10, value: body, onChange: (e) => {
|
|
9216
9203
|
setBody(e.target.value);
|
|
9217
9204
|
setValidationError(null);
|
|
9218
|
-
},
|
|
9205
|
+
}, spellCheck: false, error: !!validationError, className: "w-full", inputClassName: "font-mono text-xs p-3 resize-y" }),
|
|
9219
9206
|
validationError && /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "text-red-500 mt-1 block text-xs", children: validationError })
|
|
9220
9207
|
] }),
|
|
9221
9208
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "rounded-lg bg-surface-100 dark:bg-surface-900 p-3", children: [
|
|
@@ -9269,7 +9256,7 @@ return result;
|
|
|
9269
9256
|
/* @__PURE__ */ jsxRuntime.jsx("code", { className: "text-xs font-mono font-semibold", children: p.name }),
|
|
9270
9257
|
p.required && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-red-500 ml-0.5 text-xs", children: "*" })
|
|
9271
9258
|
] }),
|
|
9272
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
9259
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { size: "small", placeholder: p.description ?? p.name, value: values[p.name] ?? "", onChange: (e) => onChange(p.name, e.target.value), className: "flex-1", inputClassName: "font-mono text-xs" })
|
|
9273
9260
|
] }, p.name);
|
|
9274
9261
|
$[6] = onChange;
|
|
9275
9262
|
$[7] = values;
|
|
@@ -9333,7 +9320,7 @@ return result;
|
|
|
9333
9320
|
}
|
|
9334
9321
|
let t3;
|
|
9335
9322
|
if ($[3] !== onAdd) {
|
|
9336
|
-
t3 = /* @__PURE__ */ jsxRuntime.jsxs("
|
|
9323
|
+
t3 = /* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { variant: "text", size: "small", color: "primary", onClick: onAdd, className: "text-xs p-0 min-h-0", children: [
|
|
9337
9324
|
t2,
|
|
9338
9325
|
" Add Header"
|
|
9339
9326
|
] });
|
|
@@ -9359,9 +9346,9 @@ return result;
|
|
|
9359
9346
|
let t62;
|
|
9360
9347
|
if ($[12] !== onChange || $[13] !== onRemove) {
|
|
9361
9348
|
t62 = (v, i) => /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center gap-2", children: [
|
|
9362
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
9363
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
9364
|
-
/* @__PURE__ */ jsxRuntime.jsx("
|
|
9349
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { size: "small", placeholder: "Header name", value: v.key, onChange: (e) => onChange(i, e.target.value, v.value), className: "w-1/3", inputClassName: "font-mono text-xs" }),
|
|
9350
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TextField, { size: "small", placeholder: "Value", value: v.value, onChange: (e_0) => onChange(i, v.key, e_0.target.value), className: "flex-1", inputClassName: "font-mono text-xs" }),
|
|
9351
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { size: "small", onClick: () => onRemove(i), className: "text-text-secondary hover:text-red-500 shrink-0", title: "Remove", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.XIcon, { size: ui.iconSize.small }) })
|
|
9365
9352
|
] }, i);
|
|
9366
9353
|
$[12] = onChange;
|
|
9367
9354
|
$[13] = onRemove;
|
|
@@ -9573,17 +9560,17 @@ return result;
|
|
|
9573
9560
|
"v",
|
|
9574
9561
|
spec.info.version
|
|
9575
9562
|
] }),
|
|
9576
|
-
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "mb-2", children: /* @__PURE__ */ jsxRuntime.jsx(ui.SearchBar, { placeholder: "Filter endpoints…", size: "small", onTextSearch: (val) => setSidebarFilter(val
|
|
9563
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "mb-2", children: /* @__PURE__ */ jsxRuntime.jsx(ui.SearchBar, { placeholder: "Filter endpoints…", size: "small", onTextSearch: (val) => setSidebarFilter(val ?? "") }) })
|
|
9577
9564
|
] }),
|
|
9578
9565
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex-1 overflow-y-auto px-2 pb-4", children: [
|
|
9579
9566
|
filteredGroups.map((group) => /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "mb-3", children: [
|
|
9580
9567
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { variant: "caption", className: "px-2 py-1.5 text-text-secondary dark:text-text-secondary-dark uppercase tracking-wider font-semibold text-[10px]", children: group.tag }),
|
|
9581
9568
|
group.endpoints.map((ep) => {
|
|
9582
9569
|
const isSelected = selectedEndpoint?.id === ep.id;
|
|
9583
|
-
return /* @__PURE__ */ jsxRuntime.jsxs("
|
|
9570
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { variant: "text", color: "neutral", fullWidth: true, onClick: () => {
|
|
9584
9571
|
setSelectedEndpoint(ep);
|
|
9585
9572
|
setTryItOpen(false);
|
|
9586
|
-
}, className: ui.cls("
|
|
9573
|
+
}, className: ui.cls("!justify-between !px-2.5 !py-1.5 !text-left !text-sm", isSelected ? "bg-surface-200 dark:bg-surface-800 font-medium" : "text-text-primary dark:text-text-primary-dark"), children: [
|
|
9587
9574
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate text-[13px] opacity-90", children: ep.summary || ep.shortPath }),
|
|
9588
9575
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: ui.cls("text-[10px] font-bold uppercase shrink-0", METHOD_COLORS[ep.method] ?? "text-text-secondary"), children: ep.method })
|
|
9589
9576
|
] }, ep.id);
|