@liveblocks/client 0.13.3 → 0.15.0-alpha.2
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/lib/cjs/AbstractCrdt.d.ts +13 -7
- package/lib/cjs/AbstractCrdt.js +2 -5
- package/lib/cjs/LiveList.d.ts +16 -6
- package/lib/cjs/LiveList.js +148 -17
- package/lib/cjs/LiveMap.d.ts +12 -4
- package/lib/cjs/LiveMap.js +57 -7
- package/lib/cjs/LiveObject.d.ts +22 -8
- package/lib/cjs/LiveObject.js +109 -24
- package/lib/cjs/LiveRegister.d.ts +13 -5
- package/lib/cjs/LiveRegister.js +23 -4
- package/lib/cjs/immutable.d.ts +1 -0
- package/lib/cjs/immutable.js +64 -6
- package/lib/cjs/index.d.ts +1 -0
- package/lib/cjs/index.js +8 -1
- package/lib/cjs/live.d.ts +7 -0
- package/lib/cjs/room.d.ts +9 -1
- package/lib/cjs/room.js +131 -70
- package/lib/cjs/types.d.ts +25 -0
- package/lib/cjs/utils.d.ts +4 -1
- package/lib/cjs/utils.js +101 -1
- package/lib/esm/AbstractCrdt.d.ts +13 -7
- package/lib/esm/AbstractCrdt.js +2 -5
- package/lib/esm/LiveList.d.ts +16 -6
- package/lib/esm/LiveList.js +149 -18
- package/lib/esm/LiveMap.d.ts +12 -4
- package/lib/esm/LiveMap.js +57 -7
- package/lib/esm/LiveObject.d.ts +22 -8
- package/lib/esm/LiveObject.js +109 -24
- package/lib/esm/LiveRegister.d.ts +13 -5
- package/lib/esm/LiveRegister.js +24 -5
- package/lib/esm/immutable.d.ts +1 -0
- package/lib/esm/immutable.js +63 -6
- package/lib/esm/index.d.ts +1 -0
- package/lib/esm/index.js +1 -0
- package/lib/esm/live.d.ts +7 -0
- package/lib/esm/room.d.ts +9 -1
- package/lib/esm/room.js +132 -71
- package/lib/esm/types.d.ts +25 -0
- package/lib/esm/utils.d.ts +4 -1
- package/lib/esm/utils.js +99 -1
- package/package.json +2 -2
- package/lib/cjs/immutable/index.d.ts +0 -7
- package/lib/cjs/immutable/index.js +0 -214
- package/lib/esm/immutable/index.d.ts +0 -7
- package/lib/esm/immutable/index.js +0 -207
|
@@ -1,7 +1,8 @@
|
|
|
1
|
-
import { Op } from "./live";
|
|
1
|
+
import { Op, SerializedCrdt } from "./live";
|
|
2
|
+
import { StorageUpdate } from "./types";
|
|
2
3
|
export declare type ApplyResult = {
|
|
3
4
|
reverse: Op[];
|
|
4
|
-
modified:
|
|
5
|
+
modified: StorageUpdate;
|
|
5
6
|
} | {
|
|
6
7
|
modified: false;
|
|
7
8
|
};
|
|
@@ -10,7 +11,7 @@ export interface Doc {
|
|
|
10
11
|
generateOpId: () => string;
|
|
11
12
|
addItem: (id: string, item: AbstractCrdt) => void;
|
|
12
13
|
deleteItem: (id: string) => void;
|
|
13
|
-
dispatch: (ops: Op[], reverseOps: Op[],
|
|
14
|
+
dispatch: (ops: Op[], reverseOps: Op[], storageUpdates: Map<string, StorageUpdate>) => void;
|
|
14
15
|
}
|
|
15
16
|
export declare abstract class AbstractCrdt {
|
|
16
17
|
#private;
|
|
@@ -33,7 +34,7 @@ export declare abstract class AbstractCrdt {
|
|
|
33
34
|
/**
|
|
34
35
|
* INTERNAL
|
|
35
36
|
*/
|
|
36
|
-
_apply(op: Op): ApplyResult;
|
|
37
|
+
_apply(op: Op, isLocal: boolean): ApplyResult;
|
|
37
38
|
/**
|
|
38
39
|
* INTERNAL
|
|
39
40
|
*/
|
|
@@ -45,7 +46,7 @@ export declare abstract class AbstractCrdt {
|
|
|
45
46
|
/**
|
|
46
47
|
* INTERNAL
|
|
47
48
|
*/
|
|
48
|
-
abstract _attachChild(id: string, key: string, crdt: AbstractCrdt): ApplyResult;
|
|
49
|
+
abstract _attachChild(id: string, key: string, crdt: AbstractCrdt, isLocal: boolean): ApplyResult;
|
|
49
50
|
/**
|
|
50
51
|
* INTERNAL
|
|
51
52
|
*/
|
|
@@ -53,9 +54,14 @@ export declare abstract class AbstractCrdt {
|
|
|
53
54
|
/**
|
|
54
55
|
* INTERNAL
|
|
55
56
|
*/
|
|
56
|
-
abstract _detachChild(crdt: AbstractCrdt):
|
|
57
|
+
abstract _detachChild(crdt: AbstractCrdt): ApplyResult;
|
|
57
58
|
/**
|
|
58
59
|
* INTERNAL
|
|
59
60
|
*/
|
|
60
|
-
abstract _serialize(parentId: string, parentKey: string): Op[];
|
|
61
|
+
abstract _serialize(parentId: string, parentKey: string, doc?: Doc): Op[];
|
|
62
|
+
/**
|
|
63
|
+
* INTERNAL
|
|
64
|
+
*/
|
|
65
|
+
abstract _toSerializedCrdt(): SerializedCrdt;
|
|
66
|
+
abstract _getType(): string;
|
|
61
67
|
}
|
package/lib/cjs/AbstractCrdt.js
CHANGED
|
@@ -48,14 +48,11 @@ class AbstractCrdt {
|
|
|
48
48
|
/**
|
|
49
49
|
* INTERNAL
|
|
50
50
|
*/
|
|
51
|
-
_apply(op) {
|
|
51
|
+
_apply(op, isLocal) {
|
|
52
52
|
switch (op.type) {
|
|
53
53
|
case live_1.OpType.DeleteCrdt: {
|
|
54
54
|
if (this._parent != null && this._parentKey != null) {
|
|
55
|
-
|
|
56
|
-
const reverse = this._serialize(this._parent._id, this._parentKey);
|
|
57
|
-
this._parent._detachChild(this);
|
|
58
|
-
return { modified: parent, reverse };
|
|
55
|
+
return this._parent._detachChild(this);
|
|
59
56
|
}
|
|
60
57
|
return { modified: false };
|
|
61
58
|
}
|
package/lib/cjs/LiveList.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { AbstractCrdt, Doc, ApplyResult } from "./AbstractCrdt";
|
|
2
|
-
import { SerializedList, SerializedCrdtWithId, Op } from "./live";
|
|
2
|
+
import { SerializedList, SerializedCrdtWithId, Op, SerializedCrdt } from "./live";
|
|
3
3
|
/**
|
|
4
4
|
* The LiveList class represents an ordered collection of items that is synchorinized across clients.
|
|
5
5
|
*/
|
|
@@ -13,7 +13,8 @@ export declare class LiveList<T> extends AbstractCrdt {
|
|
|
13
13
|
/**
|
|
14
14
|
* INTERNAL
|
|
15
15
|
*/
|
|
16
|
-
_serialize(parentId?: string, parentKey?: string): Op[];
|
|
16
|
+
_serialize(parentId?: string, parentKey?: string, doc?: Doc): Op[];
|
|
17
|
+
_indexOfPosition(position: string): number;
|
|
17
18
|
/**
|
|
18
19
|
* INTERNAL
|
|
19
20
|
*/
|
|
@@ -25,19 +26,27 @@ export declare class LiveList<T> extends AbstractCrdt {
|
|
|
25
26
|
/**
|
|
26
27
|
* INTERNAL
|
|
27
28
|
*/
|
|
28
|
-
_attachChild(id: string, key: string, child: AbstractCrdt): ApplyResult;
|
|
29
|
+
_attachChild(id: string, key: string, child: AbstractCrdt, isLocal: boolean): ApplyResult;
|
|
29
30
|
/**
|
|
30
31
|
* INTERNAL
|
|
31
32
|
*/
|
|
32
|
-
_detachChild(child: AbstractCrdt):
|
|
33
|
+
_detachChild(child: AbstractCrdt): ApplyResult;
|
|
33
34
|
/**
|
|
34
35
|
* INTERNAL
|
|
35
36
|
*/
|
|
36
|
-
_setChildKey(key: string, child: AbstractCrdt):
|
|
37
|
+
_setChildKey(key: string, child: AbstractCrdt, previousKey: string): ApplyResult;
|
|
37
38
|
/**
|
|
38
39
|
* INTERNAL
|
|
39
40
|
*/
|
|
40
|
-
_apply(op: Op): ApplyResult;
|
|
41
|
+
_apply(op: Op, isLocal: boolean): ApplyResult;
|
|
42
|
+
/**
|
|
43
|
+
* INTERNAL
|
|
44
|
+
*/
|
|
45
|
+
_getType(): string;
|
|
46
|
+
/**
|
|
47
|
+
* INTERNAL
|
|
48
|
+
*/
|
|
49
|
+
_toSerializedCrdt(): SerializedCrdt;
|
|
41
50
|
/**
|
|
42
51
|
* Returns the number of elements.
|
|
43
52
|
*/
|
|
@@ -69,6 +78,7 @@ export declare class LiveList<T> extends AbstractCrdt {
|
|
|
69
78
|
* Returns an Array of all the elements in the LiveList.
|
|
70
79
|
*/
|
|
71
80
|
toArray(): T[];
|
|
81
|
+
toCrdtArray(): AbstractCrdt[];
|
|
72
82
|
/**
|
|
73
83
|
* Tests whether all elements pass the test implemented by the provided function.
|
|
74
84
|
* @param predicate Function to test for each element, taking two arguments (the element and its index).
|
package/lib/cjs/LiveList.js
CHANGED
|
@@ -17,6 +17,7 @@ const AbstractCrdt_1 = require("./AbstractCrdt");
|
|
|
17
17
|
const utils_1 = require("./utils");
|
|
18
18
|
const live_1 = require("./live");
|
|
19
19
|
const position_1 = require("./position");
|
|
20
|
+
const LiveRegister_1 = require("./LiveRegister");
|
|
20
21
|
/**
|
|
21
22
|
* The LiveList class represents an ordered collection of items that is synchorinized across clients.
|
|
22
23
|
*/
|
|
@@ -54,7 +55,7 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
54
55
|
/**
|
|
55
56
|
* INTERNAL
|
|
56
57
|
*/
|
|
57
|
-
_serialize(parentId, parentKey) {
|
|
58
|
+
_serialize(parentId, parentKey, doc) {
|
|
58
59
|
if (this._id == null) {
|
|
59
60
|
throw new Error("Cannot serialize item is not attached");
|
|
60
61
|
}
|
|
@@ -64,16 +65,20 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
64
65
|
const ops = [];
|
|
65
66
|
const op = {
|
|
66
67
|
id: this._id,
|
|
68
|
+
opId: doc === null || doc === void 0 ? void 0 : doc.generateOpId(),
|
|
67
69
|
type: live_1.OpType.CreateList,
|
|
68
70
|
parentId,
|
|
69
71
|
parentKey,
|
|
70
72
|
};
|
|
71
73
|
ops.push(op);
|
|
72
74
|
for (const [value, key] of __classPrivateFieldGet(this, _LiveList_items, "f")) {
|
|
73
|
-
ops.push(...value._serialize(this._id, key));
|
|
75
|
+
ops.push(...value._serialize(this._id, key, doc));
|
|
74
76
|
}
|
|
75
77
|
return ops;
|
|
76
78
|
}
|
|
79
|
+
_indexOfPosition(position) {
|
|
80
|
+
return __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((item) => item[1] === position);
|
|
81
|
+
}
|
|
77
82
|
/**
|
|
78
83
|
* INTERNAL
|
|
79
84
|
*/
|
|
@@ -95,7 +100,7 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
95
100
|
/**
|
|
96
101
|
* INTERNAL
|
|
97
102
|
*/
|
|
98
|
-
_attachChild(id, key, child) {
|
|
103
|
+
_attachChild(id, key, child, isLocal) {
|
|
99
104
|
var _a;
|
|
100
105
|
if (this._doc == null) {
|
|
101
106
|
throw new Error("Can't attach child if doc is not present");
|
|
@@ -103,30 +108,66 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
103
108
|
child._attach(id, this._doc);
|
|
104
109
|
child._setParentLink(this, key);
|
|
105
110
|
const index = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[1] === key);
|
|
106
|
-
|
|
111
|
+
let newKey = key;
|
|
112
|
+
// If there is a conflict
|
|
107
113
|
if (index !== -1) {
|
|
108
|
-
|
|
114
|
+
if (isLocal) {
|
|
115
|
+
// If change is local => assign a temporary position to newly attached child
|
|
116
|
+
let before = __classPrivateFieldGet(this, _LiveList_items, "f")[index] ? __classPrivateFieldGet(this, _LiveList_items, "f")[index][1] : undefined;
|
|
117
|
+
let after = __classPrivateFieldGet(this, _LiveList_items, "f")[index + 1]
|
|
118
|
+
? __classPrivateFieldGet(this, _LiveList_items, "f")[index + 1][1]
|
|
119
|
+
: undefined;
|
|
120
|
+
newKey = (0, position_1.makePosition)(before, after);
|
|
121
|
+
child._setParentLink(this, newKey);
|
|
122
|
+
}
|
|
123
|
+
else {
|
|
124
|
+
// If change is remote => assign a temporary position to existing child until we get the fix from the backend
|
|
125
|
+
__classPrivateFieldGet(this, _LiveList_items, "f")[index][1] = (0, position_1.makePosition)(key, (_a = __classPrivateFieldGet(this, _LiveList_items, "f")[index + 1]) === null || _a === void 0 ? void 0 : _a[1]);
|
|
126
|
+
}
|
|
109
127
|
}
|
|
110
|
-
__classPrivateFieldGet(this, _LiveList_items, "f").push([child,
|
|
128
|
+
__classPrivateFieldGet(this, _LiveList_items, "f").push([child, newKey]);
|
|
111
129
|
__classPrivateFieldGet(this, _LiveList_items, "f").sort((itemA, itemB) => (0, position_1.compare)(itemA[1], itemB[1]));
|
|
112
|
-
|
|
130
|
+
const newIndex = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[1] === newKey);
|
|
131
|
+
return {
|
|
132
|
+
reverse: [{ type: live_1.OpType.DeleteCrdt, id }],
|
|
133
|
+
modified: {
|
|
134
|
+
node: this,
|
|
135
|
+
type: "LiveList",
|
|
136
|
+
updates: [
|
|
137
|
+
{
|
|
138
|
+
index: newIndex,
|
|
139
|
+
type: "insert",
|
|
140
|
+
item: child instanceof LiveRegister_1.LiveRegister ? child.data : child,
|
|
141
|
+
},
|
|
142
|
+
],
|
|
143
|
+
},
|
|
144
|
+
};
|
|
113
145
|
}
|
|
114
146
|
/**
|
|
115
147
|
* INTERNAL
|
|
116
148
|
*/
|
|
117
149
|
_detachChild(child) {
|
|
118
|
-
const indexToDelete = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((item) => item[0] === child);
|
|
119
|
-
__classPrivateFieldGet(this, _LiveList_items, "f").splice(indexToDelete, 1);
|
|
120
150
|
if (child) {
|
|
151
|
+
const reverse = child._serialize(this._id, child._parentKey, this._doc);
|
|
152
|
+
const indexToDelete = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((item) => item[0] === child);
|
|
153
|
+
__classPrivateFieldGet(this, _LiveList_items, "f").splice(indexToDelete, 1);
|
|
121
154
|
child._detach();
|
|
155
|
+
const storageUpdate = {
|
|
156
|
+
node: this,
|
|
157
|
+
type: "LiveList",
|
|
158
|
+
updates: [{ index: indexToDelete, type: "delete" }],
|
|
159
|
+
};
|
|
160
|
+
return { modified: storageUpdate, reverse };
|
|
122
161
|
}
|
|
162
|
+
return { modified: false };
|
|
123
163
|
}
|
|
124
164
|
/**
|
|
125
165
|
* INTERNAL
|
|
126
166
|
*/
|
|
127
|
-
_setChildKey(key, child) {
|
|
167
|
+
_setChildKey(key, child, previousKey) {
|
|
128
168
|
var _a;
|
|
129
169
|
child._setParentLink(this, key);
|
|
170
|
+
const previousIndex = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[0]._id === child._id);
|
|
130
171
|
const index = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[1] === key);
|
|
131
172
|
// Assign a temporary position until we get the fix from the backend
|
|
132
173
|
if (index !== -1) {
|
|
@@ -137,12 +178,54 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
137
178
|
item[1] = key;
|
|
138
179
|
}
|
|
139
180
|
__classPrivateFieldGet(this, _LiveList_items, "f").sort((itemA, itemB) => (0, position_1.compare)(itemA[1], itemB[1]));
|
|
181
|
+
const newIndex = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[0]._id === child._id);
|
|
182
|
+
const updatesDelta = newIndex === previousIndex
|
|
183
|
+
? []
|
|
184
|
+
: [
|
|
185
|
+
{
|
|
186
|
+
index: newIndex,
|
|
187
|
+
item: child instanceof LiveRegister_1.LiveRegister ? child.data : child,
|
|
188
|
+
previousIndex: previousIndex,
|
|
189
|
+
type: "move",
|
|
190
|
+
},
|
|
191
|
+
];
|
|
192
|
+
return {
|
|
193
|
+
modified: {
|
|
194
|
+
node: this,
|
|
195
|
+
type: "LiveList",
|
|
196
|
+
updates: updatesDelta,
|
|
197
|
+
},
|
|
198
|
+
reverse: [
|
|
199
|
+
{
|
|
200
|
+
type: live_1.OpType.SetParentKey,
|
|
201
|
+
id: item === null || item === void 0 ? void 0 : item[0]._id,
|
|
202
|
+
parentKey: previousKey,
|
|
203
|
+
},
|
|
204
|
+
],
|
|
205
|
+
};
|
|
140
206
|
}
|
|
141
207
|
/**
|
|
142
208
|
* INTERNAL
|
|
143
209
|
*/
|
|
144
|
-
_apply(op) {
|
|
145
|
-
return super._apply(op);
|
|
210
|
+
_apply(op, isLocal) {
|
|
211
|
+
return super._apply(op, isLocal);
|
|
212
|
+
}
|
|
213
|
+
/**
|
|
214
|
+
* INTERNAL
|
|
215
|
+
*/
|
|
216
|
+
_getType() {
|
|
217
|
+
return "LiveList";
|
|
218
|
+
}
|
|
219
|
+
/**
|
|
220
|
+
* INTERNAL
|
|
221
|
+
*/
|
|
222
|
+
_toSerializedCrdt() {
|
|
223
|
+
var _a;
|
|
224
|
+
return {
|
|
225
|
+
type: live_1.CrdtType.List,
|
|
226
|
+
parentId: (_a = this._parent) === null || _a === void 0 ? void 0 : _a._id,
|
|
227
|
+
parentKey: this._parentKey,
|
|
228
|
+
};
|
|
146
229
|
}
|
|
147
230
|
/**
|
|
148
231
|
* Returns the number of elements.
|
|
@@ -164,7 +247,7 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
164
247
|
*/
|
|
165
248
|
insert(element, index) {
|
|
166
249
|
if (index < 0 || index > __classPrivateFieldGet(this, _LiveList_items, "f").length) {
|
|
167
|
-
throw new Error(`Cannot
|
|
250
|
+
throw new Error(`Cannot insert list item at index "${index}". index should be between 0 and ${__classPrivateFieldGet(this, _LiveList_items, "f").length}`);
|
|
168
251
|
}
|
|
169
252
|
let before = __classPrivateFieldGet(this, _LiveList_items, "f")[index - 1] ? __classPrivateFieldGet(this, _LiveList_items, "f")[index - 1][1] : undefined;
|
|
170
253
|
let after = __classPrivateFieldGet(this, _LiveList_items, "f")[index] ? __classPrivateFieldGet(this, _LiveList_items, "f")[index][1] : undefined;
|
|
@@ -173,10 +256,23 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
173
256
|
value._setParentLink(this, position);
|
|
174
257
|
__classPrivateFieldGet(this, _LiveList_items, "f").push([value, position]);
|
|
175
258
|
__classPrivateFieldGet(this, _LiveList_items, "f").sort((itemA, itemB) => (0, position_1.compare)(itemA[1], itemB[1]));
|
|
259
|
+
const newIndex = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[1] === position);
|
|
176
260
|
if (this._doc && this._id) {
|
|
177
261
|
const id = this._doc.generateId();
|
|
178
262
|
value._attach(id, this._doc);
|
|
179
|
-
|
|
263
|
+
const storageUpdates = new Map();
|
|
264
|
+
storageUpdates.set(this._id, {
|
|
265
|
+
node: this,
|
|
266
|
+
type: "LiveList",
|
|
267
|
+
updates: [
|
|
268
|
+
{
|
|
269
|
+
index: newIndex,
|
|
270
|
+
item: value instanceof LiveRegister_1.LiveRegister ? value.data : value,
|
|
271
|
+
type: "insert",
|
|
272
|
+
},
|
|
273
|
+
],
|
|
274
|
+
});
|
|
275
|
+
this._doc.dispatch(value._serialize(this._id, position, this._doc), [{ type: live_1.OpType.DeleteCrdt, id }], storageUpdates);
|
|
180
276
|
}
|
|
181
277
|
}
|
|
182
278
|
/**
|
|
@@ -217,11 +313,26 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
217
313
|
item[1] = position;
|
|
218
314
|
item[0]._setParentLink(this, position);
|
|
219
315
|
__classPrivateFieldGet(this, _LiveList_items, "f").sort((itemA, itemB) => (0, position_1.compare)(itemA[1], itemB[1]));
|
|
316
|
+
const newIndex = __classPrivateFieldGet(this, _LiveList_items, "f").findIndex((entry) => entry[1] === position);
|
|
220
317
|
if (this._doc && this._id) {
|
|
318
|
+
const storageUpdates = new Map();
|
|
319
|
+
storageUpdates.set(this._id, {
|
|
320
|
+
node: this,
|
|
321
|
+
type: "LiveList",
|
|
322
|
+
updates: [
|
|
323
|
+
{
|
|
324
|
+
index: newIndex,
|
|
325
|
+
previousIndex: index,
|
|
326
|
+
item: item[0],
|
|
327
|
+
type: "move",
|
|
328
|
+
},
|
|
329
|
+
],
|
|
330
|
+
});
|
|
221
331
|
this._doc.dispatch([
|
|
222
332
|
{
|
|
223
333
|
type: live_1.OpType.SetParentKey,
|
|
224
334
|
id: item[0]._id,
|
|
335
|
+
opId: this._doc.generateOpId(),
|
|
225
336
|
parentKey: position,
|
|
226
337
|
},
|
|
227
338
|
], [
|
|
@@ -230,7 +341,7 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
230
341
|
id: item[0]._id,
|
|
231
342
|
parentKey: previousPosition,
|
|
232
343
|
},
|
|
233
|
-
],
|
|
344
|
+
], storageUpdates);
|
|
234
345
|
}
|
|
235
346
|
}
|
|
236
347
|
/**
|
|
@@ -247,12 +358,19 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
247
358
|
if (this._doc) {
|
|
248
359
|
const childRecordId = item[0]._id;
|
|
249
360
|
if (childRecordId) {
|
|
361
|
+
const storageUpdates = new Map();
|
|
362
|
+
storageUpdates.set(this._id, {
|
|
363
|
+
node: this,
|
|
364
|
+
type: "LiveList",
|
|
365
|
+
updates: [{ index: index, type: "delete" }],
|
|
366
|
+
});
|
|
250
367
|
this._doc.dispatch([
|
|
251
368
|
{
|
|
252
369
|
id: childRecordId,
|
|
370
|
+
opId: this._doc.generateOpId(),
|
|
253
371
|
type: live_1.OpType.DeleteCrdt,
|
|
254
372
|
},
|
|
255
|
-
], item[0]._serialize(this._id, item[1]),
|
|
373
|
+
], item[0]._serialize(this._id, item[1]), storageUpdates);
|
|
256
374
|
}
|
|
257
375
|
}
|
|
258
376
|
}
|
|
@@ -260,16 +378,26 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
260
378
|
if (this._doc) {
|
|
261
379
|
let ops = [];
|
|
262
380
|
let reverseOps = [];
|
|
381
|
+
let updateDelta = [];
|
|
382
|
+
let i = 0;
|
|
263
383
|
for (const item of __classPrivateFieldGet(this, _LiveList_items, "f")) {
|
|
264
384
|
item[0]._detach();
|
|
265
385
|
const childId = item[0]._id;
|
|
266
386
|
if (childId) {
|
|
267
387
|
ops.push({ id: childId, type: live_1.OpType.DeleteCrdt });
|
|
268
388
|
reverseOps.push(...item[0]._serialize(this._id, item[1]));
|
|
389
|
+
updateDelta.push({ index: i, type: "delete" });
|
|
269
390
|
}
|
|
391
|
+
i++;
|
|
270
392
|
}
|
|
271
393
|
__classPrivateFieldSet(this, _LiveList_items, [], "f");
|
|
272
|
-
|
|
394
|
+
const storageUpdates = new Map();
|
|
395
|
+
storageUpdates.set(this._id, {
|
|
396
|
+
node: this,
|
|
397
|
+
type: "LiveList",
|
|
398
|
+
updates: updateDelta,
|
|
399
|
+
});
|
|
400
|
+
this._doc.dispatch(ops, reverseOps, storageUpdates);
|
|
273
401
|
}
|
|
274
402
|
else {
|
|
275
403
|
for (const item of __classPrivateFieldGet(this, _LiveList_items, "f")) {
|
|
@@ -284,6 +412,9 @@ class LiveList extends AbstractCrdt_1.AbstractCrdt {
|
|
|
284
412
|
toArray() {
|
|
285
413
|
return __classPrivateFieldGet(this, _LiveList_items, "f").map((entry) => (0, utils_1.selfOrRegisterValue)(entry[0]));
|
|
286
414
|
}
|
|
415
|
+
toCrdtArray() {
|
|
416
|
+
return __classPrivateFieldGet(this, _LiveList_items, "f").map((entry) => entry[0]);
|
|
417
|
+
}
|
|
287
418
|
/**
|
|
288
419
|
* Tests whether all elements pass the test implemented by the provided function.
|
|
289
420
|
* @param predicate Function to test for each element, taking two arguments (the element and its index).
|
package/lib/cjs/LiveMap.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { AbstractCrdt, Doc, ApplyResult } from "./AbstractCrdt";
|
|
2
|
-
import { Op, SerializedCrdtWithId } from "./live";
|
|
2
|
+
import { Op, SerializedCrdtWithId, SerializedCrdt } from "./live";
|
|
3
3
|
/**
|
|
4
4
|
* The LiveMap class is similar to a JavaScript Map that is synchronized on all clients.
|
|
5
5
|
* Keys should be a string, and values should be serializable to JSON.
|
|
@@ -11,7 +11,7 @@ export declare class LiveMap<TKey extends string, TValue> extends AbstractCrdt {
|
|
|
11
11
|
/**
|
|
12
12
|
* INTERNAL
|
|
13
13
|
*/
|
|
14
|
-
_serialize(parentId?: string, parentKey?: string): Op[];
|
|
14
|
+
_serialize(parentId?: string, parentKey?: string, doc?: Doc): Op[];
|
|
15
15
|
/**
|
|
16
16
|
* INTERNAL
|
|
17
17
|
*/
|
|
@@ -23,7 +23,7 @@ export declare class LiveMap<TKey extends string, TValue> extends AbstractCrdt {
|
|
|
23
23
|
/**
|
|
24
24
|
* INTERNAL
|
|
25
25
|
*/
|
|
26
|
-
_attachChild(id: string, key: TKey, child: AbstractCrdt): ApplyResult;
|
|
26
|
+
_attachChild(id: string, key: TKey, child: AbstractCrdt, isLocal: boolean): ApplyResult;
|
|
27
27
|
/**
|
|
28
28
|
* INTERNAL
|
|
29
29
|
*/
|
|
@@ -31,7 +31,15 @@ export declare class LiveMap<TKey extends string, TValue> extends AbstractCrdt {
|
|
|
31
31
|
/**
|
|
32
32
|
* INTERNAL
|
|
33
33
|
*/
|
|
34
|
-
_detachChild(child: AbstractCrdt):
|
|
34
|
+
_detachChild(child: AbstractCrdt): ApplyResult;
|
|
35
|
+
/**
|
|
36
|
+
* INTERNAL
|
|
37
|
+
*/
|
|
38
|
+
_getType(): string;
|
|
39
|
+
/**
|
|
40
|
+
* INTERNAL
|
|
41
|
+
*/
|
|
42
|
+
_toSerializedCrdt(): SerializedCrdt;
|
|
35
43
|
/**
|
|
36
44
|
* Returns a specified element from the LiveMap.
|
|
37
45
|
* @param key The key of the element to return.
|
package/lib/cjs/LiveMap.js
CHANGED
|
@@ -41,7 +41,7 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
41
41
|
/**
|
|
42
42
|
* INTERNAL
|
|
43
43
|
*/
|
|
44
|
-
_serialize(parentId, parentKey) {
|
|
44
|
+
_serialize(parentId, parentKey, doc) {
|
|
45
45
|
if (this._id == null) {
|
|
46
46
|
throw new Error("Cannot serialize item is not attached");
|
|
47
47
|
}
|
|
@@ -51,13 +51,14 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
51
51
|
const ops = [];
|
|
52
52
|
const op = {
|
|
53
53
|
id: this._id,
|
|
54
|
+
opId: doc === null || doc === void 0 ? void 0 : doc.generateOpId(),
|
|
54
55
|
type: live_1.OpType.CreateMap,
|
|
55
56
|
parentId,
|
|
56
57
|
parentKey,
|
|
57
58
|
};
|
|
58
59
|
ops.push(op);
|
|
59
60
|
for (const [key, value] of __classPrivateFieldGet(this, _LiveMap_map, "f")) {
|
|
60
|
-
ops.push(...value._serialize(this._id, key));
|
|
61
|
+
ops.push(...value._serialize(this._id, key, doc));
|
|
61
62
|
}
|
|
62
63
|
return ops;
|
|
63
64
|
}
|
|
@@ -99,7 +100,7 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
99
100
|
/**
|
|
100
101
|
* INTERNAL
|
|
101
102
|
*/
|
|
102
|
-
_attachChild(id, key, child) {
|
|
103
|
+
_attachChild(id, key, child, isLocal) {
|
|
103
104
|
if (this._doc == null) {
|
|
104
105
|
throw new Error("Can't attach child if doc is not present");
|
|
105
106
|
}
|
|
@@ -115,7 +116,14 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
115
116
|
child._setParentLink(this, key);
|
|
116
117
|
child._attach(id, this._doc);
|
|
117
118
|
__classPrivateFieldGet(this, _LiveMap_map, "f").set(key, child);
|
|
118
|
-
return {
|
|
119
|
+
return {
|
|
120
|
+
modified: {
|
|
121
|
+
node: this,
|
|
122
|
+
type: "LiveMap",
|
|
123
|
+
updates: { [key]: { type: "update" } },
|
|
124
|
+
},
|
|
125
|
+
reverse,
|
|
126
|
+
};
|
|
119
127
|
}
|
|
120
128
|
/**
|
|
121
129
|
* INTERNAL
|
|
@@ -130,12 +138,36 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
130
138
|
* INTERNAL
|
|
131
139
|
*/
|
|
132
140
|
_detachChild(child) {
|
|
141
|
+
const reverse = child._serialize(this._id, child._parentKey, this._doc);
|
|
133
142
|
for (const [key, value] of __classPrivateFieldGet(this, _LiveMap_map, "f")) {
|
|
134
143
|
if (value === child) {
|
|
135
144
|
__classPrivateFieldGet(this, _LiveMap_map, "f").delete(key);
|
|
136
145
|
}
|
|
137
146
|
}
|
|
138
147
|
child._detach();
|
|
148
|
+
const storageUpdate = {
|
|
149
|
+
node: this,
|
|
150
|
+
type: "LiveMap",
|
|
151
|
+
updates: { [child._parentKey]: { type: "delete" } },
|
|
152
|
+
};
|
|
153
|
+
return { modified: storageUpdate, reverse };
|
|
154
|
+
}
|
|
155
|
+
/**
|
|
156
|
+
* INTERNAL
|
|
157
|
+
*/
|
|
158
|
+
_getType() {
|
|
159
|
+
return "LiveMap";
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* INTERNAL
|
|
163
|
+
*/
|
|
164
|
+
_toSerializedCrdt() {
|
|
165
|
+
var _a;
|
|
166
|
+
return {
|
|
167
|
+
type: live_1.CrdtType.Map,
|
|
168
|
+
parentId: (_a = this._parent) === null || _a === void 0 ? void 0 : _a._id,
|
|
169
|
+
parentKey: this._parentKey,
|
|
170
|
+
};
|
|
139
171
|
}
|
|
140
172
|
/**
|
|
141
173
|
* Returns a specified element from the LiveMap.
|
|
@@ -165,9 +197,15 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
165
197
|
if (this._doc && this._id) {
|
|
166
198
|
const id = this._doc.generateId();
|
|
167
199
|
item._attach(id, this._doc);
|
|
168
|
-
|
|
200
|
+
const storageUpdates = new Map();
|
|
201
|
+
storageUpdates.set(this._id, {
|
|
202
|
+
node: this,
|
|
203
|
+
type: "LiveMap",
|
|
204
|
+
updates: { [key]: { type: "update" } },
|
|
205
|
+
});
|
|
206
|
+
this._doc.dispatch(item._serialize(this._id, key, this._doc), oldValue
|
|
169
207
|
? oldValue._serialize(this._id, key)
|
|
170
|
-
: [{ type: live_1.OpType.DeleteCrdt, id }],
|
|
208
|
+
: [{ type: live_1.OpType.DeleteCrdt, id }], storageUpdates);
|
|
171
209
|
}
|
|
172
210
|
}
|
|
173
211
|
/**
|
|
@@ -195,7 +233,19 @@ class LiveMap extends AbstractCrdt_1.AbstractCrdt {
|
|
|
195
233
|
}
|
|
196
234
|
item._detach();
|
|
197
235
|
if (this._doc && item._id) {
|
|
198
|
-
|
|
236
|
+
const storageUpdates = new Map();
|
|
237
|
+
storageUpdates.set(this._id, {
|
|
238
|
+
node: this,
|
|
239
|
+
type: "LiveMap",
|
|
240
|
+
updates: { [key]: { type: "delete" } },
|
|
241
|
+
});
|
|
242
|
+
this._doc.dispatch([
|
|
243
|
+
{
|
|
244
|
+
type: live_1.OpType.DeleteCrdt,
|
|
245
|
+
id: item._id,
|
|
246
|
+
opId: this._doc.generateOpId(),
|
|
247
|
+
},
|
|
248
|
+
], item._serialize(this._id, key), storageUpdates);
|
|
199
249
|
}
|
|
200
250
|
__classPrivateFieldGet(this, _LiveMap_map, "f").delete(key);
|
|
201
251
|
return true;
|
package/lib/cjs/LiveObject.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { AbstractCrdt, Doc, ApplyResult } from "./AbstractCrdt";
|
|
2
|
-
import { Op, SerializedCrdtWithId } from "./live";
|
|
2
|
+
import { Op, SerializedCrdt, SerializedCrdtWithId } from "./live";
|
|
3
3
|
/**
|
|
4
4
|
* The LiveObject class is similar to a JavaScript object that is synchronized on all clients.
|
|
5
5
|
* Keys should be a string, and values should be serializable to JSON.
|
|
@@ -11,13 +11,15 @@ export declare class LiveObject<T extends Record<string, any> = Record<string, a
|
|
|
11
11
|
/**
|
|
12
12
|
* INTERNAL
|
|
13
13
|
*/
|
|
14
|
-
_serialize(parentId?: string, parentKey?: string): Op[];
|
|
14
|
+
_serialize(parentId?: string, parentKey?: string, doc?: Doc): Op[];
|
|
15
15
|
/**
|
|
16
16
|
* INTERNAL
|
|
17
17
|
*/
|
|
18
|
-
static _deserialize([id, item]: SerializedCrdtWithId, parentToChildren: Map<string, SerializedCrdtWithId[]>, doc: Doc): LiveObject<
|
|
19
|
-
|
|
20
|
-
|
|
18
|
+
static _deserialize([id, item]: SerializedCrdtWithId, parentToChildren: Map<string, SerializedCrdtWithId[]>, doc: Doc): LiveObject<Record<string, any>>;
|
|
19
|
+
/**
|
|
20
|
+
* INTERNAL
|
|
21
|
+
*/
|
|
22
|
+
static _deserializeChildren(object: LiveObject, parentToChildren: Map<string, SerializedCrdtWithId[]>, doc: Doc): LiveObject<Record<string, any>>;
|
|
21
23
|
/**
|
|
22
24
|
* INTERNAL
|
|
23
25
|
*/
|
|
@@ -25,11 +27,15 @@ export declare class LiveObject<T extends Record<string, any> = Record<string, a
|
|
|
25
27
|
/**
|
|
26
28
|
* INTERNAL
|
|
27
29
|
*/
|
|
28
|
-
_attachChild(id: string, key: keyof T, child: AbstractCrdt): ApplyResult;
|
|
30
|
+
_attachChild(id: string, key: keyof T, child: AbstractCrdt, isLocal: boolean): ApplyResult;
|
|
31
|
+
/**
|
|
32
|
+
* INTERNAL
|
|
33
|
+
*/
|
|
34
|
+
_detachChild(child: AbstractCrdt): ApplyResult;
|
|
29
35
|
/**
|
|
30
36
|
* INTERNAL
|
|
31
37
|
*/
|
|
32
|
-
|
|
38
|
+
_detachChildren(): void;
|
|
33
39
|
/**
|
|
34
40
|
* INTERNAL
|
|
35
41
|
*/
|
|
@@ -37,7 +43,15 @@ export declare class LiveObject<T extends Record<string, any> = Record<string, a
|
|
|
37
43
|
/**
|
|
38
44
|
* INTERNAL
|
|
39
45
|
*/
|
|
40
|
-
_apply(op: Op): ApplyResult;
|
|
46
|
+
_apply(op: Op, isLocal: boolean): ApplyResult;
|
|
47
|
+
/**
|
|
48
|
+
* INTERNAL
|
|
49
|
+
*/
|
|
50
|
+
_toSerializedCrdt(): SerializedCrdt;
|
|
51
|
+
/**
|
|
52
|
+
* INTERNAL
|
|
53
|
+
*/
|
|
54
|
+
_getType(): string;
|
|
41
55
|
/**
|
|
42
56
|
* Transform the LiveObject into a javascript object
|
|
43
57
|
*/
|