@tita-agent/dsh-data-table 0.0.0-stage → 0.2.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/LICENSE +21 -0
- package/README.md +172 -2
- package/cordis.patch.yml +7 -0
- package/lib/client.js +16766 -0
- package/lib/contract-envelope.d.ts +91 -0
- package/lib/contract-envelope.js +106 -0
- package/lib/contract-layout.d.ts +130 -0
- package/lib/contract-layout.js +138 -0
- package/lib/contract-refs.d.ts +39 -0
- package/lib/contract-refs.js +9 -0
- package/lib/contract-version.d.ts +311 -0
- package/lib/contract-version.js +270 -0
- package/lib/contract-wire.d.ts +147 -0
- package/lib/contract-wire.js +99 -0
- package/lib/contracts.d.ts +12 -0
- package/lib/contracts.js +12 -0
- package/lib/types/audit.d.ts +42 -0
- package/lib/types/audit.js +39 -0
- package/lib/types/client/ProjectImportMenu.d.ts +30 -0
- package/lib/types/client/ProjectImportMenu.js +70 -0
- package/lib/types/client/SheetPanel.d.ts +33 -0
- package/lib/types/client/SheetPanel.js +1766 -0
- package/lib/types/client/SheetToggle.d.ts +18 -0
- package/lib/types/client/SheetToggle.js +26 -0
- package/lib/types/client/index.d.ts +15 -0
- package/lib/types/client/index.js +110 -0
- package/lib/types/client/persistence/changes.d.ts +15 -0
- package/lib/types/client/persistence/changes.js +51 -0
- package/lib/types/client/persistence/ids.d.ts +34 -0
- package/lib/types/client/persistence/ids.js +48 -0
- package/lib/types/client/persistence/merge.d.ts +35 -0
- package/lib/types/client/persistence/merge.js +362 -0
- package/lib/types/client/store.d.ts +61 -0
- package/lib/types/client/store.js +152 -0
- package/lib/types/client/surface-context.d.ts +27 -0
- package/lib/types/client/surface-context.js +104 -0
- package/lib/types/client/surface-control.d.ts +2 -0
- package/lib/types/client/surface-control.js +12 -0
- package/lib/types/client/transport/workbookApi.d.ts +159 -0
- package/lib/types/client/transport/workbookApi.js +246 -0
- package/lib/types/client/univer/StandaloneWorkbookPage.d.ts +5 -0
- package/lib/types/client/univer/StandaloneWorkbookPage.js +7 -0
- package/lib/types/client/univer/WorkbookCanvas.d.ts +40 -0
- package/lib/types/client/univer/WorkbookCanvas.js +87 -0
- package/lib/types/client/univer/WorkbookView.d.ts +3 -0
- package/lib/types/client/univer/WorkbookView.js +2 -0
- package/lib/types/client/univer/loader.d.ts +18 -0
- package/lib/types/client/univer/loader.js +81 -0
- package/lib/types/client/univer/standalone-entry.d.ts +1 -0
- package/lib/types/client/univer/standalone-entry.js +19 -0
- package/lib/types/client/versions/VersionChrome.d.ts +33 -0
- package/lib/types/client/versions/VersionChrome.js +21 -0
- package/lib/types/client/versions/inspect.d.ts +70 -0
- package/lib/types/client/versions/inspect.js +88 -0
- package/lib/types/client/versions/preview-decoration.d.ts +11 -0
- package/lib/types/client/versions/preview-decoration.js +54 -0
- package/lib/types/client/versions/records.d.ts +19 -0
- package/lib/types/client/versions/records.js +70 -0
- package/lib/types/client/workspace-host.d.ts +61 -0
- package/lib/types/client/workspace-host.js +124 -0
- package/lib/types/collaboration-hub.d.ts +31 -0
- package/lib/types/collaboration-hub.js +69 -0
- package/lib/types/contract/ids.d.ts +24 -0
- package/lib/types/contract/ids.js +46 -0
- package/lib/types/contract/mutations.d.ts +25 -0
- package/lib/types/contract/mutations.js +782 -0
- package/lib/types/contract/operations.d.ts +54 -0
- package/lib/types/contract/operations.js +203 -0
- package/lib/types/contract/snapshots.d.ts +176 -0
- package/lib/types/contract/snapshots.js +351 -0
- package/lib/types/contract/univer-api-catalog.d.ts +29 -0
- package/lib/types/contract/univer-api-catalog.js +264 -0
- package/lib/types/errors.d.ts +8 -0
- package/lib/types/errors.js +12 -0
- package/lib/types/http/assets-routes.d.ts +3 -0
- package/lib/types/http/assets-routes.js +169 -0
- package/lib/types/http/collaboration.d.ts +10 -0
- package/lib/types/http/collaboration.js +154 -0
- package/lib/types/http/history.d.ts +15 -0
- package/lib/types/http/history.js +134 -0
- package/lib/types/http/project-files.d.ts +79 -0
- package/lib/types/http/project-files.js +206 -0
- package/lib/types/http/project-scope.d.ts +50 -0
- package/lib/types/http/project-scope.js +52 -0
- package/lib/types/http/routes.d.ts +98 -0
- package/lib/types/http/routes.js +323 -0
- package/lib/types/http/standalone.d.ts +9 -0
- package/lib/types/http/standalone.js +31 -0
- package/lib/types/http/trunk.d.ts +10 -0
- package/lib/types/http/trunk.js +322 -0
- package/lib/types/http/worktree.d.ts +9 -0
- package/lib/types/http/worktree.js +145 -0
- package/lib/types/index.d.ts +18 -0
- package/lib/types/index.js +156 -0
- package/lib/types/invariant.d.ts +15 -0
- package/lib/types/invariant.js +15 -0
- package/lib/types/request-params.d.ts +21 -0
- package/lib/types/request-params.js +76 -0
- package/lib/types/store/paths.d.ts +68 -0
- package/lib/types/store/paths.js +148 -0
- package/lib/types/store/project.d.ts +88 -0
- package/lib/types/store/project.js +120 -0
- package/lib/types/store/read.d.ts +110 -0
- package/lib/types/store/read.js +404 -0
- package/lib/types/store/retention.d.ts +27 -0
- package/lib/types/store/retention.js +111 -0
- package/lib/types/store/write.d.ts +22 -0
- package/lib/types/store/write.js +210 -0
- package/lib/types/tools/arguments.d.ts +40 -0
- package/lib/types/tools/arguments.js +130 -0
- package/lib/types/tools/cells.d.ts +50 -0
- package/lib/types/tools/cells.js +298 -0
- package/lib/types/tools/index.d.ts +2 -0
- package/lib/types/tools/index.js +250 -0
- package/lib/types/tools/render.d.ts +47 -0
- package/lib/types/tools/render.js +290 -0
- package/lib/types/tools/univer-api.d.ts +18 -0
- package/lib/types/tools/univer-api.js +198 -0
- package/lib/types/tools/workbook-catalog.d.ts +3 -0
- package/lib/types/tools/workbook-catalog.js +83 -0
- package/lib/types/tools/workbook-edit.d.ts +192 -0
- package/lib/types/tools/workbook-edit.js +912 -0
- package/lib/types/tools/workbook-find.d.ts +11 -0
- package/lib/types/tools/workbook-find.js +89 -0
- package/lib/types/tools/workbook-history.d.ts +2 -0
- package/lib/types/tools/workbook-history.js +59 -0
- package/lib/types/tools/workbook-read.d.ts +21 -0
- package/lib/types/tools/workbook-read.js +204 -0
- package/lib/types/types.d.ts +377 -0
- package/lib/types/types.js +34 -0
- package/lib/types/univer/apply-operation.d.ts +14 -0
- package/lib/types/univer/apply-operation.js +398 -0
- package/lib/types/univer/chunk.d.ts +68 -0
- package/lib/types/univer/chunk.js +16 -0
- package/lib/types/univer/decoration.d.ts +34 -0
- package/lib/types/univer/decoration.js +88 -0
- package/lib/types/univer/diagnostics.d.ts +31 -0
- package/lib/types/univer/diagnostics.js +141 -0
- package/lib/types/univer/engine.d.ts +33 -0
- package/lib/types/univer/engine.js +338 -0
- package/lib/types/univer/entry.d.ts +8 -0
- package/lib/types/univer/entry.js +11 -0
- package/lib/types/univer/facade.d.ts +107 -0
- package/lib/types/univer/facade.js +1 -0
- package/lib/types/univer/fonts.d.ts +202 -0
- package/lib/types/univer/fonts.js +140 -0
- package/lib/types/univer/plugins/collaboration.d.ts +23 -0
- package/lib/types/univer/plugins/collaboration.js +47 -0
- package/lib/types/univer/plugins/export.d.ts +39 -0
- package/lib/types/univer/plugins/export.js +246 -0
- package/lib/types/univer/plugins/history.d.ts +24 -0
- package/lib/types/univer/plugins/history.js +50 -0
- package/lib/types/univer/plugins/version.d.ts +13 -0
- package/lib/types/univer/plugins/version.js +13 -0
- package/lib/types/version/diff.d.ts +36 -0
- package/lib/types/version/diff.js +156 -0
- package/lib/types/version/grouping.d.ts +7 -0
- package/lib/types/version/grouping.js +94 -0
- package/lib/types/version/records.d.ts +17 -0
- package/lib/types/version/records.js +102 -0
- package/lib/types/version/session.d.ts +36 -0
- package/lib/types/version/session.js +89 -0
- package/lib/types/version/summary.d.ts +24 -0
- package/lib/types/version/summary.js +111 -0
- package/lib/types/workbook-manager.d.ts +191 -0
- package/lib/types/workbook-manager.js +935 -0
- package/lib/types/xlsx-export-worker.d.ts +5 -0
- package/lib/types/xlsx-export-worker.js +24 -0
- package/lib/types/xlsx-export.d.ts +21 -0
- package/lib/types/xlsx-export.js +371 -0
- package/lib/types/xlsx-import-worker.d.ts +1 -0
- package/lib/types/xlsx-import-worker.js +19 -0
- package/lib/univer-client.js +690 -0
- package/lib/workbook-page.js +23826 -0
- package/lib/xlsx-export-worker.js +104 -0
- package/lib/xlsx-import-worker.js +46 -0
- package/package.json +106 -3
- package/src/audit.ts +58 -0
- package/src/client/ProjectImportMenu.tsx +100 -0
- package/src/client/SheetPanel.module.css +1578 -0
- package/src/client/SheetPanel.tsx +1934 -0
- package/src/client/SheetToggle.module.css +73 -0
- package/src/client/SheetToggle.tsx +65 -0
- package/src/client/contract.d.ts +19 -0
- package/src/client/index.ts +131 -0
- package/src/client/persistence/changes.ts +58 -0
- package/src/client/persistence/ids.ts +60 -0
- package/src/client/persistence/merge.ts +392 -0
- package/src/client/store.ts +188 -0
- package/src/client/surface-context.ts +123 -0
- package/src/client/surface-control.ts +13 -0
- package/src/client/transport/workbookApi.ts +355 -0
- package/src/client/univer/SheetView.module.css +110 -0
- package/src/client/univer/StandaloneWorkbookPage.module.css +8 -0
- package/src/client/univer/StandaloneWorkbookPage.tsx +15 -0
- package/src/client/univer/WorkbookCanvas.tsx +128 -0
- package/src/client/univer/WorkbookView.module.css +30 -0
- package/src/client/univer/WorkbookView.tsx +3 -0
- package/src/client/univer/loader.ts +90 -0
- package/src/client/univer/react-dom-client.d.ts +10 -0
- package/src/client/univer/standalone-entry.tsx +19 -0
- package/src/client/univer/standalone.css +12 -0
- package/src/client/univer/univer-locales.d.ts +89 -0
- package/src/client/univer/univer-modules.d.ts +26 -0
- package/src/client/versions/VersionChrome.tsx +114 -0
- package/src/client/versions/inspect.ts +138 -0
- package/src/client/versions/preview-decoration.ts +54 -0
- package/src/client/versions/records.ts +78 -0
- package/src/client/workspace-host.ts +147 -0
- package/src/collaboration-hub.ts +83 -0
- package/src/contract/ids.ts +50 -0
- package/src/contract/mutations.ts +791 -0
- package/src/contract/operations.ts +221 -0
- package/src/contract/snapshots.ts +383 -0
- package/src/contract/univer-api-catalog.ts +289 -0
- package/src/css-modules.d.ts +6 -0
- package/src/errors.ts +25 -0
- package/src/http/assets-routes.ts +177 -0
- package/src/http/collaboration.ts +144 -0
- package/src/http/history.ts +151 -0
- package/src/http/project-files.ts +227 -0
- package/src/http/project-scope.ts +77 -0
- package/src/http/routes.ts +364 -0
- package/src/http/standalone.ts +32 -0
- package/src/http/trunk.ts +322 -0
- package/src/http/worktree.ts +119 -0
- package/src/index.ts +165 -0
- package/src/invariant.ts +17 -0
- package/src/request-params.ts +92 -0
- package/src/store/paths.ts +165 -0
- package/src/store/project.ts +137 -0
- package/src/store/read.ts +454 -0
- package/src/store/retention.ts +106 -0
- package/src/store/write.ts +230 -0
- package/src/tools/arguments.ts +128 -0
- package/src/tools/cells.ts +298 -0
- package/src/tools/index.ts +274 -0
- package/src/tools/render.ts +301 -0
- package/src/tools/univer-api.ts +243 -0
- package/src/tools/workbook-catalog.ts +94 -0
- package/src/tools/workbook-edit.ts +987 -0
- package/src/tools/workbook-find.ts +80 -0
- package/src/tools/workbook-history.ts +63 -0
- package/src/tools/workbook-read.ts +210 -0
- package/src/types.ts +432 -0
- package/src/univer/apply-operation.ts +369 -0
- package/src/univer/chunk.ts +77 -0
- package/src/univer/decoration.ts +111 -0
- package/src/univer/diagnostics.ts +136 -0
- package/src/univer/engine.ts +370 -0
- package/src/univer/entry.ts +14 -0
- package/src/univer/facade.ts +91 -0
- package/src/univer/fonts.ts +148 -0
- package/src/univer/overrides.css +33 -0
- package/src/univer/plugins/collaboration.ts +47 -0
- package/src/univer/plugins/export.ts +236 -0
- package/src/univer/plugins/history.ts +49 -0
- package/src/univer/plugins/version.ts +13 -0
- package/src/version/diff.ts +169 -0
- package/src/version/grouping.ts +96 -0
- package/src/version/records.ts +113 -0
- package/src/version/session.ts +90 -0
- package/src/version/summary.ts +117 -0
- package/src/workbook-manager.ts +1111 -0
- package/src/xlsx-export-worker.ts +34 -0
- package/src/xlsx-export.ts +373 -0
- package/src/xlsx-import-worker.ts +30 -0
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Lazy Univer half for dsh-data-table. The heavy Univer engine lives
|
|
3
|
+
* in a separate chunk (`lib/univer-client.js`, served by the node half at
|
|
4
|
+
* `/data-sheet/univer-client.js`); this module loads that chunk on the first
|
|
5
|
+
* sheet render so the ~16MB graph is never in the page's boot bundle.
|
|
6
|
+
* CSV export is engine-free and stays here.
|
|
7
|
+
* @module dsh-data-table/client/univer
|
|
8
|
+
*/
|
|
9
|
+
import type { WorkbookLocalChange, WorkbookPresencePayload, WorkbookSelectionRange } from '../../types.ts';
|
|
10
|
+
import type { WorkbookMount, WorkbookMountOptions } from '../../univer/chunk.ts';
|
|
11
|
+
export type { WorkbookDecoration, WorkbookDecorationCell, WorkbookMount, WorkbookMountOptions } from '../../univer/chunk.ts';
|
|
12
|
+
/**
|
|
13
|
+
* Mount one resident Univer engine into a container with a workbook snapshot.
|
|
14
|
+
* Resolves after the engine chunk arrived (first call pays the fetch/parse).
|
|
15
|
+
* `options.readOnly` mounts a preview residency: the snapshot is a past
|
|
16
|
+
* Version, so no edit is reported and none can be made (PRD v3.2 §7.2).
|
|
17
|
+
*/
|
|
18
|
+
export declare function mountWorkbook(container: HTMLElement, workbookData: object, onDirty?: (change?: WorkbookLocalChange) => void, onPresence?: (presence: WorkbookPresencePayload) => void, options?: WorkbookMountOptions, onSelection?: (ranges: readonly WorkbookSelectionRange[]) => void): Promise<WorkbookMount>;
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Lazy Univer half for dsh-data-table. The heavy Univer engine lives
|
|
3
|
+
* in a separate chunk (`lib/univer-client.js`, served by the node half at
|
|
4
|
+
* `/data-sheet/univer-client.js`); this module loads that chunk on the first
|
|
5
|
+
* sheet render so the ~16MB graph is never in the page's boot bundle.
|
|
6
|
+
* CSV export is engine-free and stays here.
|
|
7
|
+
* @module dsh-data-table/client/univer
|
|
8
|
+
*/
|
|
9
|
+
/**
|
|
10
|
+
* Engine-chunk candidates, tried in order: the node-half route is the durable
|
|
11
|
+
* source (registered when the dsh server runs the current plugin code); the
|
|
12
|
+
* dist asset is the stopgap for a server that was started before the route
|
|
13
|
+
* existed (each failed source is a dead end, not retried).
|
|
14
|
+
*/
|
|
15
|
+
function dataSheetAssetPath(path, keepQuery = false) {
|
|
16
|
+
const transport = globalThis.__DSH_TRANSPORT__;
|
|
17
|
+
if (transport?.ownsHost === true) {
|
|
18
|
+
// The path travels as a query parameter, so a cache-busting query string
|
|
19
|
+
// would become part of the resolved file path; drop it in this mode.
|
|
20
|
+
const [withoutQuery] = keepQuery ? path.split('?') : [path];
|
|
21
|
+
return `/api/data-sheet?path=${encodeURIComponent(withoutQuery ?? path)}`;
|
|
22
|
+
}
|
|
23
|
+
return path;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Build tag appended to the engine chunk URL. The chunk is a plain script the
|
|
27
|
+
* browser caches by URL, so a rebuilt chunk used to keep running in an already
|
|
28
|
+
* open page; a unique query makes every build a different URL. The host
|
|
29
|
+
* transport mode passes the path as a query parameter, so the tag is only
|
|
30
|
+
* added on the direct route (which matches on `pathname` and ignores queries).
|
|
31
|
+
*/
|
|
32
|
+
const CHUNK_VERSION = typeof __DSH_DATA_SHEET_BUILD__ === 'string' ? __DSH_DATA_SHEET_BUILD__ : 'dev';
|
|
33
|
+
const chunkPath = `/data-sheet/univer-client.js?v=${encodeURIComponent(CHUNK_VERSION)}`;
|
|
34
|
+
const CHUNK_SOURCES = [dataSheetAssetPath(chunkPath, true), '/assets/data-sheet-univer.js'];
|
|
35
|
+
let chunkPromise = null;
|
|
36
|
+
/** Load the engine chunk once (script tag; shared across concurrent callers). */
|
|
37
|
+
function loadChunk() {
|
|
38
|
+
if (window.__bestExcelUniver !== undefined)
|
|
39
|
+
return Promise.resolve(window.__bestExcelUniver);
|
|
40
|
+
if (chunkPromise !== null)
|
|
41
|
+
return chunkPromise;
|
|
42
|
+
chunkPromise = (async () => {
|
|
43
|
+
for (const src of CHUNK_SOURCES) {
|
|
44
|
+
try {
|
|
45
|
+
await new Promise((resolve, reject) => {
|
|
46
|
+
const el = document.createElement('script');
|
|
47
|
+
el.async = true;
|
|
48
|
+
el.src = src;
|
|
49
|
+
el.addEventListener('load', () => {
|
|
50
|
+
if (window.__bestExcelUniver === undefined)
|
|
51
|
+
reject(new Error(`univer chunk loaded without its global: ${src}`));
|
|
52
|
+
else
|
|
53
|
+
resolve();
|
|
54
|
+
}, { once: true });
|
|
55
|
+
el.addEventListener('error', () => reject(new Error(`univer chunk failed to load: ${src}`)));
|
|
56
|
+
document.head.append(el);
|
|
57
|
+
});
|
|
58
|
+
const api = window.__bestExcelUniver;
|
|
59
|
+
if (api === undefined)
|
|
60
|
+
throw new Error('univer chunk resolved without its global');
|
|
61
|
+
return api;
|
|
62
|
+
}
|
|
63
|
+
catch (error) {
|
|
64
|
+
if (src === CHUNK_SOURCES[CHUNK_SOURCES.length - 1])
|
|
65
|
+
throw error;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
throw new Error('unreachable');
|
|
69
|
+
})();
|
|
70
|
+
return chunkPromise;
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Mount one resident Univer engine into a container with a workbook snapshot.
|
|
74
|
+
* Resolves after the engine chunk arrived (first call pays the fetch/parse).
|
|
75
|
+
* `options.readOnly` mounts a preview residency: the snapshot is a past
|
|
76
|
+
* Version, so no edit is reported and none can be made (PRD v3.2 §7.2).
|
|
77
|
+
*/
|
|
78
|
+
export async function mountWorkbook(container, workbookData, onDirty, onPresence, options, onSelection) {
|
|
79
|
+
const api = await loadChunk();
|
|
80
|
+
return api.mountWorkbook(container, workbookData, onDirty, onPresence, options, onSelection);
|
|
81
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import './standalone.css';
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
+
import { createRoot } from 'react-dom/client';
|
|
3
|
+
import { setDshSessionId } from "../transport/workbookApi.js";
|
|
4
|
+
import { StandaloneWorkbookPage } from "./StandaloneWorkbookPage.js";
|
|
5
|
+
import './standalone.css';
|
|
6
|
+
const root = document.getElementById('data-sheet-workbook-root');
|
|
7
|
+
if (root !== null) {
|
|
8
|
+
const query = new URLSearchParams(window.location.search);
|
|
9
|
+
// The project this page reads: the address that opened it carries the Session id
|
|
10
|
+
// (see `standaloneWorkbookPath`), because a page in its own document — a new tab
|
|
11
|
+
// or the in-app full page — has no sidebar to ask.
|
|
12
|
+
setDshSessionId(query.get('sessionId') ?? undefined);
|
|
13
|
+
const pathMatch = /^\/data-sheet\/workbook\/([^/]+)\/view$/.exec(window.location.pathname);
|
|
14
|
+
const queryId = query.get('workbook');
|
|
15
|
+
const workbookId = pathMatch?.[1] === undefined
|
|
16
|
+
? (queryId ?? 'main')
|
|
17
|
+
: decodeURIComponent(pathMatch[1]);
|
|
18
|
+
createRoot(root).render(_jsx(StandaloneWorkbookPage, { workbookId: workbookId }));
|
|
19
|
+
}
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { type VersionManagerActions, type VersionManagerGroup } from '@tita-agent/ui/versions';
|
|
2
|
+
import type { VersionRestoreRequest } from './inspect.ts';
|
|
3
|
+
export interface VersionChromeProps {
|
|
4
|
+
open: boolean;
|
|
5
|
+
onOpenChange: (open: boolean) => void;
|
|
6
|
+
/** Name of the artifact, for the drawer's header line. */
|
|
7
|
+
artifactName: string;
|
|
8
|
+
/** How many Versions the list holds, and when the newest one landed. */
|
|
9
|
+
versionCount: number;
|
|
10
|
+
headLabel: string | undefined;
|
|
11
|
+
/** The Version the canvas would restore, or undo, to. */
|
|
12
|
+
restorableId: string | undefined;
|
|
13
|
+
loading: boolean;
|
|
14
|
+
groups: VersionManagerGroup[];
|
|
15
|
+
actions: VersionManagerActions;
|
|
16
|
+
save: {
|
|
17
|
+
open: boolean;
|
|
18
|
+
pending: boolean;
|
|
19
|
+
/** True while no artifact is open: there is nothing to name. */
|
|
20
|
+
disabled: boolean;
|
|
21
|
+
onOpenChange: (open: boolean) => void;
|
|
22
|
+
onConfirm: (name: string) => void;
|
|
23
|
+
};
|
|
24
|
+
restore: {
|
|
25
|
+
/** The pending confirmation, or null when the dialog is closed. */
|
|
26
|
+
request: VersionRestoreRequest | null;
|
|
27
|
+
pending: boolean;
|
|
28
|
+
onOpenChange: (open: boolean) => void;
|
|
29
|
+
onConfirm: () => void;
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
/** Drawer, 保存版本 dialog and 恢复 confirmation, as one piece of chrome. */
|
|
33
|
+
export declare function VersionChrome({ open, onOpenChange, artifactName, versionCount, headLabel, restorableId, loading, groups, actions, save, restore, }: VersionChromeProps): React.ReactElement;
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
/**
|
|
3
|
+
* The version drawer and the two dialogs that answer from it (docs/issue/0022 P5).
|
|
4
|
+
*
|
|
5
|
+
* This is the chrome half of the history surface: `records.ts` turns a stored
|
|
6
|
+
* Version into the row the list draws, `inspect.ts` produces what the comparison
|
|
7
|
+
* bar needs, and this assembles the Drawer, the 保存版本 dialog and the
|
|
8
|
+
* 恢复/撤销 confirmation out of them. It was inline in `SheetPanel.tsx`, which is
|
|
9
|
+
* pinned at its size for a reason — the panel's job is the canvas and the wire,
|
|
10
|
+
* and the copy and structure of the history UI are not part of that.
|
|
11
|
+
*/
|
|
12
|
+
import { Button } from '@tita-agent/ui/components';
|
|
13
|
+
import { Drawer, DrawerBody, DrawerContent, DrawerDescription, DrawerHeader, DrawerTitle, } from '@tita-agent/ui/overlays';
|
|
14
|
+
import { Save } from '@tita-agent/ui/icons';
|
|
15
|
+
import { RestoreDialog, SaveVersionDialog, VersionManager, } from '@tita-agent/ui/versions';
|
|
16
|
+
/** Drawer, 保存版本 dialog and 恢复 confirmation, as one piece of chrome. */
|
|
17
|
+
export function VersionChrome({ open, onOpenChange, artifactName, versionCount, headLabel, restorableId, loading, groups, actions, save, restore, }) {
|
|
18
|
+
return (_jsxs(_Fragment, { children: [_jsx(Drawer, { open: open, onOpenChange: onOpenChange, children: _jsxs(DrawerContent, { "aria-label": "\u7248\u672C\u7BA1\u7406", children: [_jsxs(DrawerHeader, { children: [_jsxs("div", { children: [_jsx(DrawerTitle, { children: "\u7248\u672C\u7BA1\u7406" }), _jsx(DrawerDescription, { children: versionCount === 0
|
|
19
|
+
? `${artifactName} · 还没有版本`
|
|
20
|
+
: `${artifactName} · ${versionCount} 个版本 · 最近保存 ${headLabel ?? ''}` })] }), _jsxs(Button, { variant: "outline", size: "sm", disabled: save.disabled, onClick: () => save.onOpenChange(true), children: [_jsx(Save, { size: 14, "aria-hidden": "true" }), "\u4FDD\u5B58\u7248\u672C"] })] }), _jsx(DrawerBody, { children: _jsx(VersionManager, { loading: loading, groups: groups, actions: { ...actions, restorableId } }) })] }) }), _jsx(SaveVersionDialog, { open: save.open, onOpenChange: save.onOpenChange, pending: save.pending, onConfirm: save.onConfirm }), _jsx(RestoreDialog, { open: restore.request !== null, onOpenChange: restore.onOpenChange, targetLabel: restore.request?.label ?? '', ...(restore.request?.summary === undefined ? {} : { targetSummary: restore.request.summary }), ...(restore.request === null ? {} : { mode: restore.request.mode }), artifactLabel: "\u5DE5\u4F5C\u7C3F\u5185\u5BB9", pending: restore.pending, onConfirm: restore.onConfirm })] }));
|
|
21
|
+
}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import { type VersionInspectOption, type VersionInspectorSummary, type VersionManagerEntry } from '@tita-agent/ui/versions';
|
|
2
|
+
import type { WorkbookChange } from '../../types.ts';
|
|
3
|
+
import type { WorkbookDecoration } from '../univer/loader.ts';
|
|
4
|
+
/**
|
|
5
|
+
* One preview residency (docs/issue/0002 PRD v3.2 §7.2). `step` is part of the
|
|
6
|
+
* canvas's React `key` so replaying a Step of the same Version remounts it;
|
|
7
|
+
* `snapshot` is the content the canvas renders read-only.
|
|
8
|
+
*/
|
|
9
|
+
export interface WorkbookPreviewState {
|
|
10
|
+
versionId: string;
|
|
11
|
+
revision: number;
|
|
12
|
+
/** Rebuilt content state; the canvas renders exactly this. */
|
|
13
|
+
snapshot: object;
|
|
14
|
+
/** Step index when the preview is a Step replay rather than the Version end. */
|
|
15
|
+
step: number | null;
|
|
16
|
+
/**
|
|
17
|
+
* What is on screen vs what it is compared against: a Step against the state
|
|
18
|
+
* before it, a Version against the newer one it followed. Drives the canvas
|
|
19
|
+
* overlay so the reader does not have to find the changed cells (v3.3 §7.2).
|
|
20
|
+
*/
|
|
21
|
+
changes: WorkbookChange[];
|
|
22
|
+
/**
|
|
23
|
+
* Which end of the measured range the canvas is showing, so only changes the
|
|
24
|
+
* reader can actually see get tinted.
|
|
25
|
+
*/
|
|
26
|
+
changesSide: 'before' | 'after';
|
|
27
|
+
/** True when the changes could not be rebuilt (compressed history). */
|
|
28
|
+
changesUnavailable?: boolean;
|
|
29
|
+
/** True when the diff stopped at the server's limit, so the counts are a floor. */
|
|
30
|
+
changesTruncated?: boolean;
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* The overlay for a residency: identical to what an in-place swap painted, so a
|
|
34
|
+
* remount and a swap show exactly the same thing.
|
|
35
|
+
*/
|
|
36
|
+
export declare function previewDecorationOf(preview: WorkbookPreviewState | null): WorkbookDecoration | undefined;
|
|
37
|
+
/**
|
|
38
|
+
* Counts + legend for the bar, derived from the same list the canvas tints.
|
|
39
|
+
*
|
|
40
|
+
* The counts carry the same bucket names the engine paints with, so the legend
|
|
41
|
+
* and the grid are read as one thing; `truncated` is carried through because a
|
|
42
|
+
* capped list would otherwise read as the whole comparison.
|
|
43
|
+
*/
|
|
44
|
+
export declare function inspectorSummaryOf(preview: WorkbookPreviewState | null): VersionInspectorSummary;
|
|
45
|
+
/**
|
|
46
|
+
* Preview switcher options: every Version the artifact could be swapped onto,
|
|
47
|
+
* newest-first, labelled the way its row was. Built from the timeline so the
|
|
48
|
+
* selector can never offer a Version the list does not show.
|
|
49
|
+
*
|
|
50
|
+
* The Steps give the picker its second level; the shared helper budgets a Step's
|
|
51
|
+
* summary to one menu line.
|
|
52
|
+
*/
|
|
53
|
+
export declare function inspectOptionsOf(entries: readonly VersionManagerEntry[]): VersionInspectOption[];
|
|
54
|
+
/**
|
|
55
|
+
* Revision a baseline id measures against.
|
|
56
|
+
*
|
|
57
|
+
* A Step is measured at the revision it produced. Falling back to the Version
|
|
58
|
+
* rather than refusing keeps a record written before the field existed usable —
|
|
59
|
+
* it just compares the whole Version.
|
|
60
|
+
*/
|
|
61
|
+
export declare function baselineRevisionOf(entry: VersionManagerEntry | undefined, fallbackRevision: number, step?: number): number;
|
|
62
|
+
/** What 「恢复」/「撤销这次改动」 posts, once the confirmation dialog is answered. */
|
|
63
|
+
export interface VersionRestoreRequest {
|
|
64
|
+
revision: number;
|
|
65
|
+
/** Render-time label, for the dialog and the notice. */
|
|
66
|
+
label: string;
|
|
67
|
+
/** Durable summary written into the new Version's record. */
|
|
68
|
+
summary: string;
|
|
69
|
+
mode: 'restore' | 'undo';
|
|
70
|
+
}
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The read-only comparison surface, as view models (docs/issue/0022 P5).
|
|
3
|
+
*
|
|
4
|
+
* `records.ts` translates a stored Version into the row the drawer draws; this
|
|
5
|
+
* takes that row — or a fetched diff — and produces the things the *inspect*
|
|
6
|
+
* half needs: the two pickers' options, the canvas overlay, the counts in the
|
|
7
|
+
* bar, and the revision a baseline id addresses. All of it is pure, which is the
|
|
8
|
+
* point: the panel is 1800 lines of ref-mutating effects, and each of these was
|
|
9
|
+
* a `useMemo` body buried in the middle of it.
|
|
10
|
+
*/
|
|
11
|
+
import { versionChangeDirection } from '#contracts';
|
|
12
|
+
import { versionOptionLabel, versionStepOptionLabel, } from '@tita-agent/ui/versions';
|
|
13
|
+
import { toDecoration } from "./preview-decoration.js";
|
|
14
|
+
/**
|
|
15
|
+
* The overlay for a residency: identical to what an in-place swap painted, so a
|
|
16
|
+
* remount and a swap show exactly the same thing.
|
|
17
|
+
*/
|
|
18
|
+
export function previewDecorationOf(preview) {
|
|
19
|
+
return preview === null ? undefined : toDecoration(preview.changes, preview.changesSide);
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Counts + legend for the bar, derived from the same list the canvas tints.
|
|
23
|
+
*
|
|
24
|
+
* The counts carry the same bucket names the engine paints with, so the legend
|
|
25
|
+
* and the grid are read as one thing; `truncated` is carried through because a
|
|
26
|
+
* capped list would otherwise read as the whole comparison.
|
|
27
|
+
*/
|
|
28
|
+
export function inspectorSummaryOf(preview) {
|
|
29
|
+
const summary = { total: 0, add: 0, remove: 0, modify: 0, structure: 0, style: 0 };
|
|
30
|
+
if (preview === null)
|
|
31
|
+
return summary;
|
|
32
|
+
summary.total = preview.changes.length;
|
|
33
|
+
if (preview.changesUnavailable === true)
|
|
34
|
+
summary.unavailable = true;
|
|
35
|
+
if (preview.changesTruncated === true)
|
|
36
|
+
summary.truncated = true;
|
|
37
|
+
for (const change of preview.changes) {
|
|
38
|
+
summary[versionChangeDirection({
|
|
39
|
+
kind: change.kind,
|
|
40
|
+
target: '',
|
|
41
|
+
description: '',
|
|
42
|
+
...(change.row === undefined ? {} : { row: change.row }),
|
|
43
|
+
...(change.column === undefined ? {} : { column: change.column }),
|
|
44
|
+
...(change.before === undefined ? {} : { before: change.before }),
|
|
45
|
+
...(change.after === undefined ? {} : { after: change.after }),
|
|
46
|
+
...(change.styleOnly === true ? { styleOnly: true } : {}),
|
|
47
|
+
})] += 1;
|
|
48
|
+
}
|
|
49
|
+
return summary;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Preview switcher options: every Version the artifact could be swapped onto,
|
|
53
|
+
* newest-first, labelled the way its row was. Built from the timeline so the
|
|
54
|
+
* selector can never offer a Version the list does not show.
|
|
55
|
+
*
|
|
56
|
+
* The Steps give the picker its second level; the shared helper budgets a Step's
|
|
57
|
+
* summary to one menu line.
|
|
58
|
+
*/
|
|
59
|
+
export function inspectOptionsOf(entries) {
|
|
60
|
+
return entries
|
|
61
|
+
.filter(entry => entry.replayable)
|
|
62
|
+
.map(entry => ({
|
|
63
|
+
id: entry.id,
|
|
64
|
+
label: versionOptionLabel({ summary: entry.summary, ...(entry.timestamp === undefined ? { time: entry.time } : { timestamp: entry.timestamp }) }),
|
|
65
|
+
steps: (entry.steps ?? []).map(step => ({
|
|
66
|
+
index: step.index,
|
|
67
|
+
label: versionStepOptionLabel(step),
|
|
68
|
+
...(step.revision === undefined ? {} : { revision: step.revision }),
|
|
69
|
+
})),
|
|
70
|
+
}));
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Revision a baseline id measures against.
|
|
74
|
+
*
|
|
75
|
+
* A Step is measured at the revision it produced. Falling back to the Version
|
|
76
|
+
* rather than refusing keeps a record written before the field existed usable —
|
|
77
|
+
* it just compares the whole Version.
|
|
78
|
+
*/
|
|
79
|
+
export function baselineRevisionOf(entry, fallbackRevision, step) {
|
|
80
|
+
if (entry === undefined)
|
|
81
|
+
return fallbackRevision;
|
|
82
|
+
if (step !== undefined) {
|
|
83
|
+
const found = entry.steps?.find(candidate => candidate.index === step);
|
|
84
|
+
if (found?.revision !== undefined)
|
|
85
|
+
return found.revision;
|
|
86
|
+
}
|
|
87
|
+
return entry.revision ?? fallbackRevision;
|
|
88
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { WorkbookChange } from '../../types.ts';
|
|
2
|
+
import type { WorkbookDecoration } from '../univer/loader.ts';
|
|
3
|
+
/**
|
|
4
|
+
* Turn a change list into the canvas overlay (PRD v3.3 §7.2): every changed
|
|
5
|
+
* cell, toned by direction, plus the first changed cell as the focus so
|
|
6
|
+
* switching what is inspected moves the viewport onto what actually changed.
|
|
7
|
+
*
|
|
8
|
+
* A removed cell exists only in the baseline, so it cannot be tinted in this
|
|
9
|
+
* snapshot; it is counted in the bar instead of being painted nowhere.
|
|
10
|
+
*/
|
|
11
|
+
export declare function toDecoration(changes: WorkbookChange[], side: 'before' | 'after'): WorkbookDecoration | undefined;
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Turning a diff into a canvas overlay (docs/issue/0022 P5).
|
|
3
|
+
*
|
|
4
|
+
* The *order* of a diff is not the same as its direction, and which tones may be
|
|
5
|
+
* painted depends on which side of the comparison the canvas is showing: a
|
|
6
|
+
* removed cell does not exist in the snapshot that is on screen, so painting it
|
|
7
|
+
* would tint an empty cell. That rule is the whole reason this is a module.
|
|
8
|
+
*/
|
|
9
|
+
import { versionChangeDirection } from '#contracts';
|
|
10
|
+
/**
|
|
11
|
+
* Turn a change list into the canvas overlay (PRD v3.3 §7.2): every changed
|
|
12
|
+
* cell, toned by direction, plus the first changed cell as the focus so
|
|
13
|
+
* switching what is inspected moves the viewport onto what actually changed.
|
|
14
|
+
*
|
|
15
|
+
* A removed cell exists only in the baseline, so it cannot be tinted in this
|
|
16
|
+
* snapshot; it is counted in the bar instead of being painted nowhere.
|
|
17
|
+
*/
|
|
18
|
+
export function toDecoration(changes, side) {
|
|
19
|
+
const cells = [];
|
|
20
|
+
let focus;
|
|
21
|
+
for (const change of changes) {
|
|
22
|
+
if (change.kind !== 'cell' || change.row === undefined || change.column === undefined)
|
|
23
|
+
continue;
|
|
24
|
+
const sheetRef = change.sheetId ?? change.sheetName;
|
|
25
|
+
const direction = versionChangeDirection({
|
|
26
|
+
kind: 'cell',
|
|
27
|
+
target: '',
|
|
28
|
+
description: '',
|
|
29
|
+
row: change.row,
|
|
30
|
+
column: change.column,
|
|
31
|
+
...(change.before === undefined ? {} : { before: change.before }),
|
|
32
|
+
...(change.after === undefined ? {} : { after: change.after }),
|
|
33
|
+
});
|
|
34
|
+
// A diff is directional, and the canvas shows exactly one of its two sides:
|
|
35
|
+
// - showing the newer side, an addition/replacement is paint-able (green /
|
|
36
|
+
// amber) and a deletion has no cell here at all;
|
|
37
|
+
// - showing the older side — the default when previewing an old Version
|
|
38
|
+
// against the current content — it is the other way round, and the cell
|
|
39
|
+
// that no longer exists is the red one.
|
|
40
|
+
// Painting the wrong side's cells would tint empty cells and claim a change
|
|
41
|
+
// the reader cannot see.
|
|
42
|
+
const tone = direction === 'add' ? 'add' : direction === 'remove' ? 'remove' : 'modify';
|
|
43
|
+
const paintable = side === 'after' ? tone !== 'remove' : tone !== 'add';
|
|
44
|
+
if (!paintable)
|
|
45
|
+
continue;
|
|
46
|
+
cells.push({ ...(sheetRef === undefined ? {} : { sheetRef }), row: change.row, column: change.column, tone });
|
|
47
|
+
if (focus === undefined) {
|
|
48
|
+
focus = { ...(sheetRef === undefined ? {} : { sheetRef }), row: change.row, column: change.column };
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
if (cells.length === 0 && focus === undefined)
|
|
52
|
+
return undefined;
|
|
53
|
+
return { cells, ...(focus === undefined ? {} : { focus }) };
|
|
54
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A stored Version as the panel renders it (docs/issue/0022 P5).
|
|
3
|
+
*
|
|
4
|
+
* The history payload and the shared `VersionManager` speak different shapes:
|
|
5
|
+
* the payload is what the store knows (revisions, steps, lineage), and the row
|
|
6
|
+
* model is what a person sees. This is that translation, and nothing else — it
|
|
7
|
+
* is the module PRD 0002 keeps touching, so it is a module rather than twelve
|
|
8
|
+
* helpers at the bottom of the panel.
|
|
9
|
+
*/
|
|
10
|
+
import { formatVersionTime, type VersionManagerEntry } from '@tita-agent/ui/versions';
|
|
11
|
+
import type { WorkbookHistoryVersion } from '../../types.ts';
|
|
12
|
+
import type { HistoryEntry } from '../transport/workbookApi.ts';
|
|
13
|
+
/** The history payload's Version, under the name the panel's rows use. */
|
|
14
|
+
export type HistoryVersion = WorkbookHistoryVersion;
|
|
15
|
+
/** The shared component formats Version times; re-exported so callers did not have to move. */
|
|
16
|
+
export declare const formatHistoryTime: typeof formatVersionTime;
|
|
17
|
+
export declare function historyVersionsFromEntries(entries: HistoryEntry[]): HistoryVersion[];
|
|
18
|
+
/** Shared drawer entry shape (docs/issue/0002 Phase 3 / PRD v3 §7). */
|
|
19
|
+
export declare function toVersionManagerEntry(version: HistoryVersion, index: number, all: HistoryVersion[]): VersionManagerEntry;
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A stored Version as the panel renders it (docs/issue/0022 P5).
|
|
3
|
+
*
|
|
4
|
+
* The history payload and the shared `VersionManager` speak different shapes:
|
|
5
|
+
* the payload is what the store knows (revisions, steps, lineage), and the row
|
|
6
|
+
* model is what a person sees. This is that translation, and nothing else — it
|
|
7
|
+
* is the module PRD 0002 keeps touching, so it is a module rather than twelve
|
|
8
|
+
* helpers at the bottom of the panel.
|
|
9
|
+
*/
|
|
10
|
+
import { formatVersionTime } from '@tita-agent/ui/versions';
|
|
11
|
+
/** The shared component formats Version times; re-exported so callers did not have to move. */
|
|
12
|
+
export const formatHistoryTime = formatVersionTime;
|
|
13
|
+
export function historyVersionsFromEntries(entries) {
|
|
14
|
+
return entries.map((entry, index) => ({
|
|
15
|
+
versionId: `revision:${entry.revision}`,
|
|
16
|
+
number: index + 1,
|
|
17
|
+
startRevision: entry.revision,
|
|
18
|
+
revision: entry.revision,
|
|
19
|
+
parentRevision: entry.parentRevision ?? Math.max(0, entry.revision - 1),
|
|
20
|
+
actor: entry.actor,
|
|
21
|
+
timestamp: entry.timestamp,
|
|
22
|
+
summary: entry.summary,
|
|
23
|
+
stepCount: 1,
|
|
24
|
+
steps: [{ index: 0, opId: entry.opId, type: entry.type, summary: entry.summary }],
|
|
25
|
+
canPreview: entry.canPreview === true,
|
|
26
|
+
status: 'final',
|
|
27
|
+
// A legacy operation-log row is a deliberate step, not session churn.
|
|
28
|
+
kind: 'named',
|
|
29
|
+
branch: 'main',
|
|
30
|
+
}));
|
|
31
|
+
}
|
|
32
|
+
/** Shared drawer entry shape (docs/issue/0002 Phase 3 / PRD v3 §7). */
|
|
33
|
+
export function toVersionManagerEntry(version, index, all) {
|
|
34
|
+
const status = version.branch === 'superseded'
|
|
35
|
+
? 'superseded'
|
|
36
|
+
: version.status === 'final'
|
|
37
|
+
? 'committed'
|
|
38
|
+
: 'open';
|
|
39
|
+
const restoredFromNumber = version.restoredFromNumber
|
|
40
|
+
?? (version.restoredFromRevision === undefined
|
|
41
|
+
? undefined
|
|
42
|
+
: all.find(candidate => candidate.revision === version.restoredFromRevision)?.number);
|
|
43
|
+
const restoredFrom = restoredFromNumber === undefined
|
|
44
|
+
? undefined
|
|
45
|
+
: all.find(candidate => candidate.number === restoredFromNumber);
|
|
46
|
+
return {
|
|
47
|
+
id: version.versionId,
|
|
48
|
+
number: version.number ?? all.length - index,
|
|
49
|
+
revision: version.revision,
|
|
50
|
+
summary: version.summary,
|
|
51
|
+
actor: version.actor === 'agent' ? 'agent' : 'user',
|
|
52
|
+
time: formatHistoryTime(version.timestamp),
|
|
53
|
+
timestamp: version.timestamp,
|
|
54
|
+
status,
|
|
55
|
+
kind: version.kind,
|
|
56
|
+
...(restoredFrom === undefined
|
|
57
|
+
? (restoredFromNumber === undefined ? {} : { restoredFromNumber })
|
|
58
|
+
: { restoredFromTime: formatHistoryTime(restoredFrom.timestamp) }),
|
|
59
|
+
stepCount: version.stepCount,
|
|
60
|
+
replayable: version.canPreview,
|
|
61
|
+
steps: version.steps.map(step => ({
|
|
62
|
+
id: step.opId,
|
|
63
|
+
index: step.index,
|
|
64
|
+
label: `Step ${step.index + 1}`,
|
|
65
|
+
summary: step.summary,
|
|
66
|
+
...(step.revision === undefined ? {} : { revision: step.revision }),
|
|
67
|
+
})),
|
|
68
|
+
...(version.intent === undefined ? {} : { intent: version.intent }),
|
|
69
|
+
};
|
|
70
|
+
}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Resident host for the embedded Table workspace.
|
|
3
|
+
*
|
|
4
|
+
* The dock renders only the active tab's body (`DockSurface` → `renderTab`), so
|
|
5
|
+
* switching DSH tabs — or switching conversation sessions — unmounts the pane's
|
|
6
|
+
* React tree. When the workspace lived in that tree, every re-entry disposed the
|
|
7
|
+
* Univer engine, re-fetched the whole snapshot and rebuilt the sheet, which is
|
|
8
|
+
* exactly the "reloads on every visit" the panel used to show.
|
|
9
|
+
*
|
|
10
|
+
* The workspace therefore lives in one long-lived container that is created
|
|
11
|
+
* once and merely *moves* between the pane and an off-screen parking lot. Re-
|
|
12
|
+
* entering the tab re-parents the existing DOM and React tree, so the editor,
|
|
13
|
+
* its scroll position, its unsaved drafts and its collaboration stream all
|
|
14
|
+
* survive. A long stay in the parking lot releases it again, so the engine is
|
|
15
|
+
* not held for the life of the page either.
|
|
16
|
+
*
|
|
17
|
+
* The DOM access and the timer are injected so the adoption/parking bookkeeping
|
|
18
|
+
* can be tested without a browser (this repository has no DOM test
|
|
19
|
+
* environment).
|
|
20
|
+
*
|
|
21
|
+
* @module dsh-data-table/client/workspace-host
|
|
22
|
+
*/
|
|
23
|
+
/** How long a parked workspace is kept warm before it is released. */
|
|
24
|
+
export declare const PARKED_RELEASE_MS: number;
|
|
25
|
+
/** Minimal DOM surface this module needs; injectable for tests. */
|
|
26
|
+
export interface WorkspaceHostEnvironment {
|
|
27
|
+
/** Create the element that owns the workspace. */
|
|
28
|
+
createContainer(): HTMLElement;
|
|
29
|
+
/** Create the off-screen element a parked workspace is moved into. */
|
|
30
|
+
createParkingLot(): HTMLElement;
|
|
31
|
+
/** The document body the parking lot is attached to. */
|
|
32
|
+
body(): HTMLElement;
|
|
33
|
+
/** Schedule the idle release (injectable so tests stay deterministic). */
|
|
34
|
+
schedule(callback: () => void, delayMs: number): unknown;
|
|
35
|
+
/** Cancel a scheduled idle release. */
|
|
36
|
+
cancel(handle: unknown): void;
|
|
37
|
+
}
|
|
38
|
+
/** Replace the DOM environment (tests only). Resets any resident workspace. */
|
|
39
|
+
export declare function setWorkspaceHostEnvironment(next: WorkspaceHostEnvironment): void;
|
|
40
|
+
/** The resident container, or null when nothing is resident. */
|
|
41
|
+
export declare function workspaceHostElement(): HTMLElement | null;
|
|
42
|
+
/** Whether the resident workspace is currently parked off-screen. */
|
|
43
|
+
export declare function isWorkspaceHostParked(): boolean;
|
|
44
|
+
/**
|
|
45
|
+
* Put the resident workspace inside `target`, creating it on first use.
|
|
46
|
+
* @param target - the pane element that should display the workspace.
|
|
47
|
+
* @param mount - called once per workspace lifetime; may return a disposer.
|
|
48
|
+
* @returns the resident container.
|
|
49
|
+
*/
|
|
50
|
+
export declare function adoptWorkspaceHost(target: HTMLElement, mount: (container: HTMLElement) => void | (() => void)): HTMLElement;
|
|
51
|
+
/**
|
|
52
|
+
* Move the resident workspace off-screen without destroying it.
|
|
53
|
+
*
|
|
54
|
+
* Its measured size is kept so the engine sees no resize while parked; that is
|
|
55
|
+
* what makes re-adoption invisible instead of a relayout. The workspace is
|
|
56
|
+
* released after {@link PARKED_RELEASE_MS} so a tab the user has moved on from
|
|
57
|
+
* does not pin a whole engine for the life of the page.
|
|
58
|
+
*/
|
|
59
|
+
export declare function parkWorkspaceHost(): void;
|
|
60
|
+
/** Release the resident workspace, unmounting its React tree. Safe when empty. */
|
|
61
|
+
export declare function disposeWorkspaceHost(): void;
|