@ai-matrx/office 0.7.0 → 0.8.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/CHANGELOG.md +15 -0
- package/dist/docs.cjs +177 -28
- package/dist/docs.cjs.map +1 -1
- package/dist/docs.d.cts +83 -2
- package/dist/docs.d.ts +83 -2
- package/dist/docs.js +154 -5
- package/dist/docs.js.map +1 -1
- package/dist/univer-collab.cjs +1004 -1
- package/dist/univer-collab.cjs.map +1 -1
- package/dist/univer-collab.d.cts +252 -1
- package/dist/univer-collab.d.ts +252 -1
- package/dist/univer-collab.js +1010 -1
- package/dist/univer-collab.js.map +1 -1
- package/package.json +3 -2
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,20 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 0.8.0
|
|
4
|
+
|
|
5
|
+
Docs co-editing on the ordered log (COLLAB-DESIGN unit C3), in `./univer/collab` (loaded on demand):
|
|
6
|
+
|
|
7
|
+
- `transformDocsOp(x, y, side)` → `{ op, lost }`: ot-json1 `transformNoConflict` with our text-x transform. Rules R1–R5 from the C0b spike plus R6 (a merge retain whose style lost every key becomes a plain retain; REPLACE retains untouched). `composeDocsOps`, `invertDocsOp` (inverts a copy: `invertWithDoc` mutates its op), `normalizeDocsOp`, `applyDocsOp`. New dependency `ot-json1` (already in the graph through `@univerjs/core`).
|
|
8
|
+
- `docsStateHash(snapshot)` (Web Crypto SHA-256 of `canonicalDocsSnapshot`) and `stampDeterministicIds` for raw snapshots.
|
|
9
|
+
- `openDocsOtRoom({ port, transport, clientId, presence, replace, onNotice })`: capture of applied rich-text mutations with their pre-state inverse and command label, remote apply with `fromCollab` (unit re-addressed, `textRanges: null`, `noNeedSetTextRange`), an IME composition queue, undo/redo items rebased over every remote op (undo reverts only your own change), saves only from the chosen quiet seat with a matching hash, restore through `collab_replace`. Page setup is a barrier (§18).
|
|
10
|
+
- `DocumentModel.startOtRoom(factory)`, `collabMode()`, and the view port's optional `undoRedo`. Command depth per view is closed in a try/finally around `executeCommand`. `write`, `replaceContent` and `rest` route to the room when one is open.
|
|
11
|
+
- `documentOtFactory({ documentId, uid, clientId, onNotice, … })` and `documentUsesOrderedRoom(documentId, knob, isNew)`: the room for a cloud document (store `udt_document_snapshots`, doors over the docs host's client, Yjs awareness for presence and `quiet_hash` only).
|
|
12
|
+
- Evidence: the §6.4 property over the three C0 corpora, the eight owner-ruled pairs, 20,000 seeds each: 0 divergences, 0 throws; Univer's own transform diverges on the same draws (red). `DOCS_OT_FUZZ_SEEDS=20000 pnpm vitest run src/univer/collab/docs-ot/concurrent-docs-edits-converge.test.ts` (default run: 2,000 seeds).
|
|
13
|
+
|
|
14
|
+
### Consumer action
|
|
15
|
+
|
|
16
|
+
Wire `model.startOtRoom(documentOtFactory(...))` for documents where `documentUsesOrderedRoom` is true; the 0.6 relay stays the path for every other document.
|
|
17
|
+
|
|
3
18
|
## 0.7.0
|
|
4
19
|
|
|
5
20
|
New `./collab/sheets-transform` entry: the co-editing transformer for workbook edits (COLLAB-DESIGN unit C5a). Pure functions, no runtime wiring: nothing calls it until the Sheets flip (C6).
|
package/dist/docs.cjs
CHANGED
|
@@ -45,6 +45,9 @@ function takeCovered(snapshot) {
|
|
|
45
45
|
}
|
|
46
46
|
|
|
47
47
|
// src/docs/document-model.ts
|
|
48
|
+
var RICH_TEXT_EDITING_ID = "doc.mutation.rich-text-editing";
|
|
49
|
+
var COMMAND_TYPE = 0;
|
|
50
|
+
var DEPTH_GUARDED = /* @__PURE__ */ Symbol.for("ai-matrx.office.docs.command-depth-guard");
|
|
48
51
|
var DOCUMENT_SAVE_DELAY_MS = 2500;
|
|
49
52
|
var viewIds = 0;
|
|
50
53
|
var DocumentModel = (_class = class {
|
|
@@ -61,17 +64,21 @@ var DocumentModel = (_class = class {
|
|
|
61
64
|
__init6() {this.knownSnapshots = /* @__PURE__ */ new Set()}
|
|
62
65
|
__init7() {this.collabListeners = /* @__PURE__ */ new Set()}
|
|
63
66
|
__init8() {this.collab = null}
|
|
67
|
+
/** The ordered-log room (C3); exclusive with `collab` (the 0.6 relay room). */
|
|
68
|
+
__init9() {this.ot = null}
|
|
69
|
+
__init10() {this.otStarting = null}
|
|
70
|
+
__init11() {this.otListeners = /* @__PURE__ */ new Set()}
|
|
64
71
|
/** The saved snapshot the body started from, and the room entries it already holds. */
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
+
__init12() {this.baseId = null}
|
|
73
|
+
__init13() {this.baseCovered = /* @__PURE__ */ new Set()}
|
|
74
|
+
__init14() {this.collabStarting = null}
|
|
75
|
+
__init15() {this.awareness = null}
|
|
76
|
+
__init16() {this.awarenessListeners = /* @__PURE__ */ new Set()}
|
|
77
|
+
__init17() {this.realtimeClose = null}
|
|
78
|
+
__init18() {this.pageClose = null}
|
|
72
79
|
/** The last view's editor, alive and off the page until a view takes it back. */
|
|
73
|
-
|
|
74
|
-
constructor(handle, deps) {;_class.prototype.__init.call(this);_class.prototype.__init2.call(this);_class.prototype.__init3.call(this);_class.prototype.__init4.call(this);_class.prototype.__init5.call(this);_class.prototype.__init6.call(this);_class.prototype.__init7.call(this);_class.prototype.__init8.call(this);_class.prototype.__init9.call(this);_class.prototype.__init10.call(this);_class.prototype.__init11.call(this);_class.prototype.__init12.call(this);_class.prototype.__init13.call(this);_class.prototype.__init14.call(this);_class.prototype.__init15.call(this);_class.prototype.__init16.call(this);_class.prototype.__init17.call(this);_class.prototype.__init18.call(this);_class.prototype.__init19.call(this);_class.prototype.__init20.call(this);
|
|
80
|
+
__init19() {this.parked = null}
|
|
81
|
+
constructor(handle, deps) {;_class.prototype.__init.call(this);_class.prototype.__init2.call(this);_class.prototype.__init3.call(this);_class.prototype.__init4.call(this);_class.prototype.__init5.call(this);_class.prototype.__init6.call(this);_class.prototype.__init7.call(this);_class.prototype.__init8.call(this);_class.prototype.__init9.call(this);_class.prototype.__init10.call(this);_class.prototype.__init11.call(this);_class.prototype.__init12.call(this);_class.prototype.__init13.call(this);_class.prototype.__init14.call(this);_class.prototype.__init15.call(this);_class.prototype.__init16.call(this);_class.prototype.__init17.call(this);_class.prototype.__init18.call(this);_class.prototype.__init19.call(this);_class.prototype.__init20.call(this);_class.prototype.__init21.call(this);_class.prototype.__init22.call(this);_class.prototype.__init23.call(this);_class.prototype.__init24.call(this);
|
|
75
82
|
this.documentId = handle.id;
|
|
76
83
|
this.handle = handle;
|
|
77
84
|
this.deps = deps;
|
|
@@ -124,7 +131,14 @@ var DocumentModel = (_class = class {
|
|
|
124
131
|
const subscription = port.commandService.onMutationExecutedForCollab(
|
|
125
132
|
(info, options) => this.onViewMutation(id, info, options)
|
|
126
133
|
);
|
|
127
|
-
|
|
134
|
+
const view = { id, port, dispose: () => {
|
|
135
|
+
}, commands: [], pre: null };
|
|
136
|
+
const hooks = this.trackCommands(view);
|
|
137
|
+
view.dispose = () => {
|
|
138
|
+
subscription.dispose();
|
|
139
|
+
hooks();
|
|
140
|
+
};
|
|
141
|
+
this.views.set(id, view);
|
|
128
142
|
if (!this.handle.hasPending()) {
|
|
129
143
|
try {
|
|
130
144
|
const mounted = port.snapshot();
|
|
@@ -137,8 +151,8 @@ var DocumentModel = (_class = class {
|
|
|
137
151
|
return () => {
|
|
138
152
|
if (detached) return;
|
|
139
153
|
detached = true;
|
|
140
|
-
const
|
|
141
|
-
if (!
|
|
154
|
+
const view2 = this.views.get(id);
|
|
155
|
+
if (!view2) return;
|
|
142
156
|
if (this.views.size === 1) {
|
|
143
157
|
try {
|
|
144
158
|
const snapshot = port.snapshot();
|
|
@@ -147,7 +161,7 @@ var DocumentModel = (_class = class {
|
|
|
147
161
|
console.warn(`[document-model] could not keep ${this.documentId}'s last view's document`, error);
|
|
148
162
|
}
|
|
149
163
|
}
|
|
150
|
-
|
|
164
|
+
view2.dispose();
|
|
151
165
|
this.views.delete(id);
|
|
152
166
|
if (this.lastEditedView === id) this.lastEditedView = null;
|
|
153
167
|
};
|
|
@@ -171,19 +185,74 @@ var DocumentModel = (_class = class {
|
|
|
171
185
|
return editor;
|
|
172
186
|
}
|
|
173
187
|
onViewMutation(viewId, info, options) {
|
|
174
|
-
if (this.relaying || _optionalChain([options, 'optionalAccess',
|
|
188
|
+
if (this.relaying || _optionalChain([options, 'optionalAccess', _7 => _7.fromCollab]) || _optionalChain([options, 'optionalAccess', _8 => _8.fromChangeset])) return;
|
|
175
189
|
const view = this.views.get(viewId);
|
|
176
190
|
if (!view || !view.port.editable()) return;
|
|
177
191
|
this.lastEditedView = viewId;
|
|
178
192
|
this.relay(info, viewId);
|
|
179
193
|
for (const listener of this.collabListeners) listener(info, options);
|
|
194
|
+
if (this.otListeners.size && !_optionalChain([options, 'optionalAccess', _9 => _9.onlyLocal])) {
|
|
195
|
+
const m = {
|
|
196
|
+
id: info.id,
|
|
197
|
+
params: info.params,
|
|
198
|
+
pre: info.id === RICH_TEXT_EDITING_ID ? view.pre : null,
|
|
199
|
+
cmd: _nullishCoalesce(view.commands[0], () => ( null)),
|
|
200
|
+
content: isContentMutation(info)
|
|
201
|
+
};
|
|
202
|
+
view.pre = null;
|
|
203
|
+
for (const listener of Array.from(this.otListeners)) listener(m);
|
|
204
|
+
}
|
|
180
205
|
if (isContentMutation(info)) this.markDirty();
|
|
181
206
|
}
|
|
207
|
+
/**
|
|
208
|
+
* Per view: the outermost command running (a mutation's group label) and, while a room listens, the document
|
|
209
|
+
* before each rich-text mutation (its inverse is computed from the APPLIED actions against this copy). Univer's
|
|
210
|
+
* `executeCommand` has no `finally`: a command that mutates then throws never fires `onCommandExecuted`, so
|
|
211
|
+
* the depth is restored in a try/finally around the instance's `executeCommand` (C0 surprise 7).
|
|
212
|
+
*/
|
|
213
|
+
trackCommands(view) {
|
|
214
|
+
const cs = view.port.commandService;
|
|
215
|
+
if (typeof cs.beforeCommandExecuted !== "function" || typeof cs.onCommandExecuted !== "function") return () => {
|
|
216
|
+
};
|
|
217
|
+
const before = cs.beforeCommandExecuted((info) => {
|
|
218
|
+
if (info.type === COMMAND_TYPE) view.commands.push(info.id);
|
|
219
|
+
else if (info.id === RICH_TEXT_EDITING_ID && this.otListeners.size && !this.relaying) {
|
|
220
|
+
try {
|
|
221
|
+
const snap = view.port.snapshot();
|
|
222
|
+
view.pre = snap ? structuredClone(snap) : null;
|
|
223
|
+
} catch (e3) {
|
|
224
|
+
view.pre = null;
|
|
225
|
+
}
|
|
226
|
+
}
|
|
227
|
+
});
|
|
228
|
+
const after = cs.onCommandExecuted((info) => {
|
|
229
|
+
if (info.type !== COMMAND_TYPE) return;
|
|
230
|
+
const at = view.commands.lastIndexOf(info.id);
|
|
231
|
+
if (at >= 0) view.commands.splice(at, 1);
|
|
232
|
+
});
|
|
233
|
+
const guarded = cs;
|
|
234
|
+
if (typeof cs.executeCommand === "function" && !guarded[DEPTH_GUARDED]) {
|
|
235
|
+
const original = cs.executeCommand.bind(cs);
|
|
236
|
+
guarded[DEPTH_GUARDED] = true;
|
|
237
|
+
cs.executeCommand = async (id, params, options) => {
|
|
238
|
+
const depth = view.commands.length;
|
|
239
|
+
try {
|
|
240
|
+
return await original(id, params, options);
|
|
241
|
+
} finally {
|
|
242
|
+
if (view.commands.length > depth) view.commands.length = depth;
|
|
243
|
+
}
|
|
244
|
+
};
|
|
245
|
+
}
|
|
246
|
+
return () => {
|
|
247
|
+
before.dispose();
|
|
248
|
+
after.dispose();
|
|
249
|
+
};
|
|
250
|
+
}
|
|
182
251
|
/** The unit id a view's document has (what a replayed mutation must be addressed to). */
|
|
183
252
|
unitIdOf(view) {
|
|
184
253
|
try {
|
|
185
|
-
return _nullishCoalesce(_nullishCoalesce(_optionalChain([view, 'access',
|
|
186
|
-
} catch (
|
|
254
|
+
return _nullishCoalesce(_nullishCoalesce(_optionalChain([view, 'access', _10 => _10.port, 'access', _11 => _11.unitId, 'optionalCall', _12 => _12()]), () => ( _optionalChain([view, 'access', _13 => _13.port, 'access', _14 => _14.snapshot, 'call', _15 => _15(), 'optionalAccess', _16 => _16.id]))), () => ( null));
|
|
255
|
+
} catch (e4) {
|
|
187
256
|
return null;
|
|
188
257
|
}
|
|
189
258
|
}
|
|
@@ -216,7 +285,7 @@ var DocumentModel = (_class = class {
|
|
|
216
285
|
/** A view could not follow an edit: say so, then show the saved version (unless this tab has unsaved edits of its own). */
|
|
217
286
|
applyFailed(mutationId, error) {
|
|
218
287
|
try {
|
|
219
|
-
_optionalChain([this, 'access',
|
|
288
|
+
_optionalChain([this, 'access', _17 => _17.deps, 'access', _18 => _18.onApplyFailed, 'optionalCall', _19 => _19(this.documentId, mutationId, error)]);
|
|
220
289
|
} catch (notifyError) {
|
|
221
290
|
console.warn(`[document-model] the notice for ${this.documentId}'s failed apply also failed`, notifyError);
|
|
222
291
|
}
|
|
@@ -229,19 +298,24 @@ var DocumentModel = (_class = class {
|
|
|
229
298
|
markDirty() {
|
|
230
299
|
this.handle.touch();
|
|
231
300
|
}
|
|
232
|
-
|
|
301
|
+
__init20() {this.saving = false}
|
|
233
302
|
/**
|
|
234
303
|
* The content of the version the server holds (loaded or last written). A
|
|
235
304
|
* save of the same content is no save: attaching, detaching, waking or a
|
|
236
305
|
* flush of an unchanged document never writes a snapshot row.
|
|
237
306
|
*/
|
|
238
|
-
|
|
307
|
+
__init21() {this.savedFingerprint = null}
|
|
239
308
|
/**
|
|
240
309
|
* Write the body as it is now. Returns false when this tab is a collab peer
|
|
241
310
|
* that does not write (the elected host writes the canonical snapshot; a
|
|
242
311
|
* peer's edits reach it through the room). An explicit Save always writes.
|
|
243
312
|
*/
|
|
244
313
|
async write(reason) {
|
|
314
|
+
if (this.ot) {
|
|
315
|
+
const wrote = await this.ot.write(reason);
|
|
316
|
+
if (wrote) _optionalChain([this, 'access', _20 => _20.deps, 'access', _21 => _21.onSaved, 'optionalCall', _22 => _22(this.documentId, reason === "manual" ? "manual" : "autosave")]);
|
|
317
|
+
return wrote;
|
|
318
|
+
}
|
|
245
319
|
const snapshot = this.latest();
|
|
246
320
|
if (!snapshot) throw new Error("There is no open document to save.");
|
|
247
321
|
if (this.collab && !this.collab.isHost() && reason !== "manual") return false;
|
|
@@ -264,7 +338,7 @@ var DocumentModel = (_class = class {
|
|
|
264
338
|
this.saving = false;
|
|
265
339
|
}
|
|
266
340
|
if (this.views.size === 0) this.stored = snapshot;
|
|
267
|
-
_optionalChain([this, 'access',
|
|
341
|
+
_optionalChain([this, 'access', _23 => _23.deps, 'access', _24 => _24.onSaved, 'optionalCall', _25 => _25(this.documentId, origin)]);
|
|
268
342
|
return true;
|
|
269
343
|
}
|
|
270
344
|
hasUnsaved() {
|
|
@@ -286,7 +360,7 @@ var DocumentModel = (_class = class {
|
|
|
286
360
|
* person chooses; `overUnsaved` is "Take theirs" (`./documentModels.ts`).
|
|
287
361
|
*/
|
|
288
362
|
async onRemoteSnapshot(snapshotId, { overUnsaved = false } = {}) {
|
|
289
|
-
if (this.collab) return;
|
|
363
|
+
if (this.collab || this.ot) return;
|
|
290
364
|
if (this.knownSnapshots.has(snapshotId)) return;
|
|
291
365
|
if (this.saving) return;
|
|
292
366
|
if (this.hasUnsaved() && !overUnsaved) {
|
|
@@ -305,8 +379,9 @@ var DocumentModel = (_class = class {
|
|
|
305
379
|
* room the peers reload it and the shared log is emptied.
|
|
306
380
|
*/
|
|
307
381
|
replaceContent(row) {
|
|
382
|
+
if (this.ot) return this.ot.replace(row.snapshot);
|
|
308
383
|
this.show(row);
|
|
309
|
-
_optionalChain([this, 'access',
|
|
384
|
+
_optionalChain([this, 'access', _26 => _26.collab, 'optionalAccess', _27 => _27.announceReplaced, 'call', _28 => _28(row.id)]);
|
|
310
385
|
}
|
|
311
386
|
/** A peer replaced the document: show the newest save (once). */
|
|
312
387
|
async onPeerReplaced() {
|
|
@@ -329,7 +404,7 @@ var DocumentModel = (_class = class {
|
|
|
329
404
|
this.relaying = true;
|
|
330
405
|
try {
|
|
331
406
|
for (const view of this.views.values()) view.port.remount(snapshot);
|
|
332
|
-
_optionalChain([this, 'access',
|
|
407
|
+
_optionalChain([this, 'access', _29 => _29.parked, 'optionalAccess', _30 => _30.remount, 'call', _31 => _31(snapshot)]);
|
|
333
408
|
} finally {
|
|
334
409
|
this.relaying = false;
|
|
335
410
|
}
|
|
@@ -340,7 +415,7 @@ var DocumentModel = (_class = class {
|
|
|
340
415
|
* binds to. Local edits from any view go out once; a peer's edit is applied
|
|
341
416
|
* to every view.
|
|
342
417
|
*/
|
|
343
|
-
|
|
418
|
+
__init22() {this.virtualCommandService = {
|
|
344
419
|
onMutationExecutedForCollab: (listener) => {
|
|
345
420
|
this.collabListeners.add(listener);
|
|
346
421
|
return { dispose: () => this.collabListeners.delete(listener) };
|
|
@@ -388,7 +463,79 @@ var DocumentModel = (_class = class {
|
|
|
388
463
|
}
|
|
389
464
|
return this.collabStarting;
|
|
390
465
|
}
|
|
466
|
+
/** The model as the ordered-log room sees it (COLLAB-DESIGN §6.7: the model is the client, not the view). */
|
|
467
|
+
__init23() {this.otPort = {
|
|
468
|
+
onLocal: (listener) => {
|
|
469
|
+
this.otListeners.add(listener);
|
|
470
|
+
return () => void this.otListeners.delete(listener);
|
|
471
|
+
},
|
|
472
|
+
applyRemote: (id, params) => {
|
|
473
|
+
if (this.views.size === 0) throw new Error("no view of the document is mounted");
|
|
474
|
+
this.relaying = true;
|
|
475
|
+
try {
|
|
476
|
+
for (const view of this.views.values()) {
|
|
477
|
+
const unitId = this.unitIdOf(view);
|
|
478
|
+
const input = Array.isArray(params.actions) ? params.actions.length : 0;
|
|
479
|
+
const p = { ...params, ...unitId ? { unitId } : {}, textRanges: null, noNeedSetTextRange: true };
|
|
480
|
+
const ok = view.port.commandService.syncExecuteCommand(id, p, { onlyLocal: true, fromCollab: true });
|
|
481
|
+
if (ok === false) throw new Error(`"${id}" was refused by the editor`);
|
|
482
|
+
if (input > 0 && Array.isArray(p.actions) && p.actions.length === 0) throw new Error(`"${id}" was emptied by the editor`);
|
|
483
|
+
}
|
|
484
|
+
} finally {
|
|
485
|
+
this.relaying = false;
|
|
486
|
+
}
|
|
487
|
+
if (isContentMutation({ id, type: 2, params })) this.markDirty();
|
|
488
|
+
},
|
|
489
|
+
snapshot: () => this.latest(),
|
|
490
|
+
load: (snapshot) => {
|
|
491
|
+
const s2 = snapshot;
|
|
492
|
+
this.stored = s2;
|
|
493
|
+
this.savedFingerprint = contentFingerprint(s2);
|
|
494
|
+
this.relaying = true;
|
|
495
|
+
try {
|
|
496
|
+
for (const view of this.views.values()) view.port.remount(s2);
|
|
497
|
+
_optionalChain([this, 'access', _32 => _32.parked, 'optionalAccess', _33 => _33.remount, 'call', _34 => _34(s2)]);
|
|
498
|
+
} finally {
|
|
499
|
+
this.relaying = false;
|
|
500
|
+
}
|
|
501
|
+
},
|
|
502
|
+
undoTargets: () => {
|
|
503
|
+
const out = [];
|
|
504
|
+
for (const view of this.views.values()) {
|
|
505
|
+
const unitId = this.unitIdOf(view);
|
|
506
|
+
const service = _optionalChain([view, 'access', _35 => _35.port, 'access', _36 => _36.undoRedo, 'optionalCall', _37 => _37()]);
|
|
507
|
+
if (unitId && service) out.push({ service, unitId });
|
|
508
|
+
}
|
|
509
|
+
return out;
|
|
510
|
+
},
|
|
511
|
+
markDirty: () => this.markDirty()
|
|
512
|
+
}}
|
|
513
|
+
/** Join the document's ordered-log room once (C3). Exclusive with `startCollab`. */
|
|
514
|
+
startOtRoom(factory) {
|
|
515
|
+
if (this.ot || this.collab) return Promise.resolve();
|
|
516
|
+
if (!this.otStarting) {
|
|
517
|
+
this.otStarting = factory(this.otPort, (awareness) => {
|
|
518
|
+
this.awareness = awareness;
|
|
519
|
+
for (const listener of Array.from(this.awarenessListeners)) listener();
|
|
520
|
+
}).then((handle) => {
|
|
521
|
+
if (!handle) return;
|
|
522
|
+
if (this.views.size === 0) {
|
|
523
|
+
handle.stop();
|
|
524
|
+
return;
|
|
525
|
+
}
|
|
526
|
+
this.ot = handle;
|
|
527
|
+
}).finally(() => {
|
|
528
|
+
this.otStarting = null;
|
|
529
|
+
});
|
|
530
|
+
}
|
|
531
|
+
return this.otStarting;
|
|
532
|
+
}
|
|
533
|
+
/** Which co-editing room this document is in right now. */
|
|
534
|
+
collabMode() {
|
|
535
|
+
return this.ot ? "ordered" : this.collab ? "relay" : null;
|
|
536
|
+
}
|
|
391
537
|
isCollabHost() {
|
|
538
|
+
if (this.ot) return this.ot.isSaver();
|
|
392
539
|
return this.collab ? this.collab.isHost() : true;
|
|
393
540
|
}
|
|
394
541
|
getAwareness() {
|
|
@@ -414,11 +561,13 @@ var DocumentModel = (_class = class {
|
|
|
414
561
|
* so a collaborator's save still reaches the body a returning view boots from.
|
|
415
562
|
*/
|
|
416
563
|
rest() {
|
|
417
|
-
_optionalChain([this, 'access',
|
|
564
|
+
_optionalChain([this, 'access', _38 => _38.collab, 'optionalAccess', _39 => _39.stop, 'call', _40 => _40()]);
|
|
418
565
|
this.collab = null;
|
|
566
|
+
_optionalChain([this, 'access', _41 => _41.ot, 'optionalAccess', _42 => _42.stop, 'call', _43 => _43()]);
|
|
567
|
+
this.ot = null;
|
|
419
568
|
this.awareness = null;
|
|
420
569
|
}
|
|
421
|
-
|
|
570
|
+
__init24() {this.closed = false}
|
|
422
571
|
close() {
|
|
423
572
|
this.closed = true;
|
|
424
573
|
const parked = this.parked;
|
|
@@ -430,9 +579,9 @@ var DocumentModel = (_class = class {
|
|
|
430
579
|
console.warn(`[document-model] could not dispose ${this.documentId}'s kept editor`, error);
|
|
431
580
|
}
|
|
432
581
|
}
|
|
433
|
-
_optionalChain([this, 'access',
|
|
582
|
+
_optionalChain([this, 'access', _44 => _44.realtimeClose, 'optionalCall', _45 => _45()]);
|
|
434
583
|
this.realtimeClose = null;
|
|
435
|
-
_optionalChain([this, 'access',
|
|
584
|
+
_optionalChain([this, 'access', _46 => _46.pageClose, 'optionalCall', _47 => _47()]);
|
|
436
585
|
this.pageClose = null;
|
|
437
586
|
}
|
|
438
587
|
}, _class);
|