@arbidocs/blocks 0.3.113 → 0.3.115
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/index.cjs +42 -5
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +14 -1
- package/dist/index.d.ts +14 -1
- package/dist/index.js +43 -6
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
package/dist/index.d.cts
CHANGED
|
@@ -1113,6 +1113,12 @@ interface StudioPersistence {
|
|
|
1113
1113
|
*/
|
|
1114
1114
|
savePublished: (arbi: Arbi | null, live: boolean, slug: string, data: unknown) => Promise<PersistVia>;
|
|
1115
1115
|
loadPublished: <T>(arbi: Arbi | null, live: boolean, slug: string) => Promise<LoadResult<T>>;
|
|
1116
|
+
/**
|
|
1117
|
+
* Delete a slug's stored authoring + published pages (backend and localStorage
|
|
1118
|
+
* mirror). Lets a page be reset to empty; also the deterministic-reset hook a
|
|
1119
|
+
* test/demo needs, since backend content otherwise wins over a fresh seed.
|
|
1120
|
+
*/
|
|
1121
|
+
deletePage: (arbi: Arbi | null, live: boolean, slug: string) => Promise<void>;
|
|
1116
1122
|
saveTheme: (arbi: Arbi | null, live: boolean, theme: unknown) => Promise<PersistVia>;
|
|
1117
1123
|
loadTheme: <T>(arbi: Arbi | null, live: boolean) => Promise<LoadResult<T>>;
|
|
1118
1124
|
}
|
|
@@ -1174,6 +1180,13 @@ interface StudioEditorProps {
|
|
|
1174
1180
|
live: boolean;
|
|
1175
1181
|
initialSlug?: string;
|
|
1176
1182
|
testIdPrefix?: string;
|
|
1183
|
+
/**
|
|
1184
|
+
* Install a DEV-only `window.__studioResetSlug(slug)` hook that clears a slug's
|
|
1185
|
+
* stored page so a fresh seed governs the canvas. For tests/demos only — it can
|
|
1186
|
+
* delete pages, so keep it off in production (pass `import.meta.env.DEV`). The
|
|
1187
|
+
* package stays env-agnostic; the consumer owns the flag.
|
|
1188
|
+
*/
|
|
1189
|
+
resetSeam?: boolean;
|
|
1177
1190
|
/**
|
|
1178
1191
|
* Optional sink for published image bytes. When omitted, publishing inlines
|
|
1179
1192
|
* each asset as a `data:` URI (self-contained, no backend). Provide this to
|
|
@@ -1181,7 +1194,7 @@ interface StudioEditorProps {
|
|
|
1181
1194
|
*/
|
|
1182
1195
|
publishAsset?: MaterializeOptions['publishAsset'];
|
|
1183
1196
|
}
|
|
1184
|
-
declare function StudioEditor({ config, pages, persistence, themeBundle, defaultTheme, brandLabel, backHref, backLabel, live, initialSlug, testIdPrefix, publishAsset, }: StudioEditorProps): react.JSX.Element;
|
|
1197
|
+
declare function StudioEditor({ config, pages, persistence, themeBundle, defaultTheme, brandLabel, backHref, backLabel, live, initialSlug, testIdPrefix, publishAsset, resetSeam, }: StudioEditorProps): react.JSX.Element;
|
|
1185
1198
|
|
|
1186
1199
|
interface PageRendererProps {
|
|
1187
1200
|
config: Config;
|
package/dist/index.d.ts
CHANGED
|
@@ -1113,6 +1113,12 @@ interface StudioPersistence {
|
|
|
1113
1113
|
*/
|
|
1114
1114
|
savePublished: (arbi: Arbi | null, live: boolean, slug: string, data: unknown) => Promise<PersistVia>;
|
|
1115
1115
|
loadPublished: <T>(arbi: Arbi | null, live: boolean, slug: string) => Promise<LoadResult<T>>;
|
|
1116
|
+
/**
|
|
1117
|
+
* Delete a slug's stored authoring + published pages (backend and localStorage
|
|
1118
|
+
* mirror). Lets a page be reset to empty; also the deterministic-reset hook a
|
|
1119
|
+
* test/demo needs, since backend content otherwise wins over a fresh seed.
|
|
1120
|
+
*/
|
|
1121
|
+
deletePage: (arbi: Arbi | null, live: boolean, slug: string) => Promise<void>;
|
|
1116
1122
|
saveTheme: (arbi: Arbi | null, live: boolean, theme: unknown) => Promise<PersistVia>;
|
|
1117
1123
|
loadTheme: <T>(arbi: Arbi | null, live: boolean) => Promise<LoadResult<T>>;
|
|
1118
1124
|
}
|
|
@@ -1174,6 +1180,13 @@ interface StudioEditorProps {
|
|
|
1174
1180
|
live: boolean;
|
|
1175
1181
|
initialSlug?: string;
|
|
1176
1182
|
testIdPrefix?: string;
|
|
1183
|
+
/**
|
|
1184
|
+
* Install a DEV-only `window.__studioResetSlug(slug)` hook that clears a slug's
|
|
1185
|
+
* stored page so a fresh seed governs the canvas. For tests/demos only — it can
|
|
1186
|
+
* delete pages, so keep it off in production (pass `import.meta.env.DEV`). The
|
|
1187
|
+
* package stays env-agnostic; the consumer owns the flag.
|
|
1188
|
+
*/
|
|
1189
|
+
resetSeam?: boolean;
|
|
1177
1190
|
/**
|
|
1178
1191
|
* Optional sink for published image bytes. When omitted, publishing inlines
|
|
1179
1192
|
* each asset as a `data:` URI (self-contained, no backend). Provide this to
|
|
@@ -1181,7 +1194,7 @@ interface StudioEditorProps {
|
|
|
1181
1194
|
*/
|
|
1182
1195
|
publishAsset?: MaterializeOptions['publishAsset'];
|
|
1183
1196
|
}
|
|
1184
|
-
declare function StudioEditor({ config, pages, persistence, themeBundle, defaultTheme, brandLabel, backHref, backLabel, live, initialSlug, testIdPrefix, publishAsset, }: StudioEditorProps): react.JSX.Element;
|
|
1197
|
+
declare function StudioEditor({ config, pages, persistence, themeBundle, defaultTheme, brandLabel, backHref, backLabel, live, initialSlug, testIdPrefix, publishAsset, resetSeam, }: StudioEditorProps): react.JSX.Element;
|
|
1185
1198
|
|
|
1186
1199
|
interface PageRendererProps {
|
|
1187
1200
|
config: Config;
|
package/dist/index.js
CHANGED
|
@@ -5,7 +5,7 @@ import { MessageSquare, Cpu, Code, Cloud, Layers, Target, Award, MapPin, Phone,
|
|
|
5
5
|
import { Input, Card, CardHeader, CardTitle, CardContent, useArbi, ArbiProvider, useAiTask, useWorkspaceDocs as useWorkspaceDocs$1, useSemanticSearch as useSemanticSearch$1, cn, Table, TableHeader, TableRow, TableHead, TableBody, TableCell, Button, Avatar, AvatarImage, AvatarFallback, AiMarkdown, Badge, Switch, useConfigs, useAgents, Checkbox, Tabs as Tabs$1, TabsList, TabsTrigger, TabsContent, Separator, ArbiWebSocketProvider, useDocuments, useThumbnails } from '@arbidocs/react';
|
|
6
6
|
export { Table, TableBody, TableCell, TableHead, TableHeader, TableRow, redlineStats, textToArtifact, toRedlineMarkdown } from '@arbidocs/react';
|
|
7
7
|
import { jsxs, jsx, Fragment } from 'react/jsx-runtime';
|
|
8
|
-
import { QueryClient, QueryClientProvider, useQuery } from '@tanstack/react-query';
|
|
8
|
+
import { QueryClient, QueryClientProvider, useQuery, useQueryClient } from '@tanstack/react-query';
|
|
9
9
|
import { AgGridReact } from 'ag-grid-react';
|
|
10
10
|
import { themeQuartz, AllCommunityModule } from 'ag-grid-community';
|
|
11
11
|
import { Link, useParams } from 'react-router-dom';
|
|
@@ -2375,7 +2375,8 @@ function StudioEditor({
|
|
|
2375
2375
|
live,
|
|
2376
2376
|
initialSlug,
|
|
2377
2377
|
testIdPrefix = "studio",
|
|
2378
|
-
publishAsset
|
|
2378
|
+
publishAsset,
|
|
2379
|
+
resetSeam = false
|
|
2379
2380
|
}) {
|
|
2380
2381
|
const arbi = useArbi();
|
|
2381
2382
|
const materialize = useMemo(
|
|
@@ -2406,6 +2407,14 @@ function StudioEditor({
|
|
|
2406
2407
|
cancelled = true;
|
|
2407
2408
|
};
|
|
2408
2409
|
}, [slug, live]);
|
|
2410
|
+
useEffect(() => {
|
|
2411
|
+
if (!resetSeam) return;
|
|
2412
|
+
const w = window;
|
|
2413
|
+
w.__studioResetSlug = (s) => persistence.deletePage(arbi, live, s);
|
|
2414
|
+
return () => {
|
|
2415
|
+
delete w.__studioResetSlug;
|
|
2416
|
+
};
|
|
2417
|
+
}, [resetSeam, arbi, live, persistence]);
|
|
2409
2418
|
const persist4 = useCallback(
|
|
2410
2419
|
async (toSave) => {
|
|
2411
2420
|
setSaving(true);
|
|
@@ -2691,6 +2700,26 @@ function createStudioPersistence(cfg) {
|
|
|
2691
2700
|
function loadPublished(arbi, live, slug) {
|
|
2692
2701
|
return readPage(arbi, live, publishedKey(slug), publishedFile(slug));
|
|
2693
2702
|
}
|
|
2703
|
+
async function deletePage(arbi, live, slug) {
|
|
2704
|
+
try {
|
|
2705
|
+
localStorage.removeItem(pageKey(slug));
|
|
2706
|
+
localStorage.removeItem(publishedKey(slug));
|
|
2707
|
+
} catch {
|
|
2708
|
+
}
|
|
2709
|
+
if (!canUseArbi(arbi, live)) return;
|
|
2710
|
+
try {
|
|
2711
|
+
await arbi.selectWorkspace(WORKSPACE_ID);
|
|
2712
|
+
const docs = await arbi.documents.list();
|
|
2713
|
+
const names = [pageFile(slug), publishedFile(slug)];
|
|
2714
|
+
const ids = docs.filter(
|
|
2715
|
+
(d) => (d.folder ?? "").includes(FOLDER) && names.some((n) => (d.file_name ?? "").endsWith(n))
|
|
2716
|
+
).map((d) => d.external_id);
|
|
2717
|
+
if (ids.length) await arbi.documents.delete(ids);
|
|
2718
|
+
console.info(`[studio] deleted ${ids.length} doc(s) for "${slug}" from ARBI`);
|
|
2719
|
+
} catch (e) {
|
|
2720
|
+
console.warn(`[studio] ARBI delete failed for "${slug}"`, e);
|
|
2721
|
+
}
|
|
2722
|
+
}
|
|
2694
2723
|
async function saveTheme(arbi, live, theme) {
|
|
2695
2724
|
try {
|
|
2696
2725
|
localStorage.setItem(THEME_KEY, JSON.stringify(theme));
|
|
@@ -2727,7 +2756,7 @@ function createStudioPersistence(cfg) {
|
|
|
2727
2756
|
return null;
|
|
2728
2757
|
}
|
|
2729
2758
|
}
|
|
2730
|
-
return { savePage, loadPage, savePublished, loadPublished, saveTheme, loadTheme };
|
|
2759
|
+
return { savePage, loadPage, savePublished, loadPublished, deletePage, saveTheme, loadTheme };
|
|
2731
2760
|
}
|
|
2732
2761
|
function AiTextField({
|
|
2733
2762
|
value,
|
|
@@ -2885,7 +2914,9 @@ function ImageFieldControl({
|
|
|
2885
2914
|
const [busy, setBusy] = useState(false);
|
|
2886
2915
|
const arbi = useArbi();
|
|
2887
2916
|
const gen = useImageGen();
|
|
2917
|
+
const queryClient = useQueryClient();
|
|
2888
2918
|
const tp = (...q) => tid(`${testIdPrefix}-image`, name, ...q);
|
|
2919
|
+
const refreshAssets = () => queryClient.invalidateQueries({ queryKey: ["arbi", "documents", workspaceId] });
|
|
2889
2920
|
const { data: docs } = useDocuments(workspaceId);
|
|
2890
2921
|
const imageDocs = useMemo(
|
|
2891
2922
|
() => (docs ?? []).filter(
|
|
@@ -2906,7 +2937,10 @@ function ImageFieldControl({
|
|
|
2906
2937
|
await arbi.selectWorkspace(workspaceId);
|
|
2907
2938
|
const res = await arbi.documents.uploadFile(file, file.name, { folder });
|
|
2908
2939
|
const id = res.doc_ext_ids?.[0];
|
|
2909
|
-
if (id)
|
|
2940
|
+
if (id) {
|
|
2941
|
+
onChange(asAssetRef(id));
|
|
2942
|
+
void refreshAssets();
|
|
2943
|
+
}
|
|
2910
2944
|
} finally {
|
|
2911
2945
|
setBusy(false);
|
|
2912
2946
|
}
|
|
@@ -2914,7 +2948,10 @@ function ImageFieldControl({
|
|
|
2914
2948
|
const onGenerate = async () => {
|
|
2915
2949
|
if (!prompt.trim() || gen.isGenerating) return;
|
|
2916
2950
|
const id = await gen.generate(prompt);
|
|
2917
|
-
if (id)
|
|
2951
|
+
if (id) {
|
|
2952
|
+
onChange(asAssetRef(id));
|
|
2953
|
+
void refreshAssets();
|
|
2954
|
+
}
|
|
2918
2955
|
};
|
|
2919
2956
|
const MODES = [
|
|
2920
2957
|
{ key: "asset", label: "Assets", icon: ImagePlus },
|
|
@@ -2959,7 +2996,7 @@ function ImageFieldControl({
|
|
|
2959
2996
|
{
|
|
2960
2997
|
src: thumb,
|
|
2961
2998
|
alt: d.file_name ?? "",
|
|
2962
|
-
className: "aspect-square w-full object-
|
|
2999
|
+
className: "aspect-square w-full bg-muted object-contain"
|
|
2963
3000
|
}
|
|
2964
3001
|
) : /* @__PURE__ */ jsx("span", { className: "flex aspect-square w-full items-center justify-center bg-muted text-muted-foreground", children: /* @__PURE__ */ jsx(ImagePlus, { className: "size-4" }) })
|
|
2965
3002
|
},
|