@colyseus/schema 3.0.10 → 3.0.12
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/build/cjs/index.js +95 -88
- package/build/cjs/index.js.map +1 -1
- package/build/esm/index.mjs +95 -88
- package/build/esm/index.mjs.map +1 -1
- package/build/umd/index.js +95 -88
- package/lib/Metadata.js +1 -2
- package/lib/Metadata.js.map +1 -1
- package/lib/annotations.js +4 -3
- package/lib/annotations.js.map +1 -1
- package/lib/decoder/DecodeOperation.js +0 -13
- package/lib/decoder/DecodeOperation.js.map +1 -1
- package/lib/encoder/ChangeTree.d.ts +1 -0
- package/lib/encoder/ChangeTree.js +2 -1
- package/lib/encoder/ChangeTree.js.map +1 -1
- package/lib/encoder/Encoder.d.ts +0 -1
- package/lib/encoder/Encoder.js +22 -30
- package/lib/encoder/Encoder.js.map +1 -1
- package/lib/encoder/Root.d.ts +1 -1
- package/lib/encoder/Root.js +20 -3
- package/lib/encoder/Root.js.map +1 -1
- package/lib/encoder/StateView.d.ts +2 -4
- package/lib/encoder/StateView.js +19 -13
- package/lib/encoder/StateView.js.map +1 -1
- package/lib/types/custom/ArraySchema.js +5 -1
- package/lib/types/custom/ArraySchema.js.map +1 -1
- package/lib/types/custom/MapSchema.js +23 -22
- package/lib/types/custom/MapSchema.js.map +1 -1
- package/package.json +1 -1
- package/src/Metadata.ts +1 -2
- package/src/annotations.ts +4 -4
- package/src/decoder/DecodeOperation.ts +0 -14
- package/src/encoder/ChangeTree.ts +3 -4
- package/src/encoder/Encoder.ts +25 -41
- package/src/encoder/Root.ts +21 -4
- package/src/encoder/StateView.ts +22 -15
- package/src/types/custom/ArraySchema.ts +8 -1
- package/src/types/custom/MapSchema.ts +24 -27
package/build/cjs/index.js
CHANGED
|
@@ -859,14 +859,13 @@ const Metadata = {
|
|
|
859
859
|
fieldIndex++;
|
|
860
860
|
for (const field in fields) {
|
|
861
861
|
const type = fields[field];
|
|
862
|
-
const normalizedType = getNormalizedType(type);
|
|
863
862
|
// FIXME: this code is duplicated from @type() annotation
|
|
864
863
|
const complexTypeKlass = (Array.isArray(type))
|
|
865
864
|
? getType("array")
|
|
866
865
|
: (typeof (Object.keys(type)[0]) === "string") && getType(Object.keys(type)[0]);
|
|
867
866
|
const childType = (complexTypeKlass)
|
|
868
867
|
? Object.values(type)[0]
|
|
869
|
-
:
|
|
868
|
+
: getNormalizedType(type);
|
|
870
869
|
Metadata.addField(metadata, fieldIndex, field, type, getPropertyDescriptor(`_${field}`, fieldIndex, childType, complexTypeKlass));
|
|
871
870
|
fieldIndex++;
|
|
872
871
|
}
|
|
@@ -1238,6 +1237,7 @@ class ChangeTree {
|
|
|
1238
1237
|
//
|
|
1239
1238
|
this.root?.remove(previousValue[$changes]);
|
|
1240
1239
|
}
|
|
1240
|
+
deleteOperationAtIndex(this.allChanges, allChangesIndex);
|
|
1241
1241
|
//
|
|
1242
1242
|
// FIXME: this is looking a ugly and repeated
|
|
1243
1243
|
//
|
|
@@ -1246,7 +1246,6 @@ class ChangeTree {
|
|
|
1246
1246
|
enqueueChangeTree(this.root, this, 'filteredChanges');
|
|
1247
1247
|
}
|
|
1248
1248
|
else {
|
|
1249
|
-
deleteOperationAtIndex(this.allChanges, allChangesIndex);
|
|
1250
1249
|
enqueueChangeTree(this.root, this, 'changes');
|
|
1251
1250
|
}
|
|
1252
1251
|
}
|
|
@@ -1533,19 +1532,6 @@ function decodeValue(decoder, operation, ref, index, type, bytes, it, allChanges
|
|
|
1533
1532
|
//
|
|
1534
1533
|
if (operation !== exports.OPERATION.DELETE_AND_ADD) {
|
|
1535
1534
|
ref[$deleteByIndex](index);
|
|
1536
|
-
// //
|
|
1537
|
-
// // FIXME: is this in the correct place?
|
|
1538
|
-
// // (This is sounding like a workaround just for ArraySchema, see
|
|
1539
|
-
// // "should splice and move" test on ArraySchema.test.ts)
|
|
1540
|
-
// //
|
|
1541
|
-
// allChanges.push({
|
|
1542
|
-
// ref,
|
|
1543
|
-
// refId: decoder.currentRefId,
|
|
1544
|
-
// op: OPERATION.DELETE,
|
|
1545
|
-
// field: index as unknown as string,
|
|
1546
|
-
// value: undefined,
|
|
1547
|
-
// previousValue,
|
|
1548
|
-
// });
|
|
1549
1535
|
}
|
|
1550
1536
|
value = undefined;
|
|
1551
1537
|
}
|
|
@@ -1893,7 +1879,8 @@ class ArraySchema {
|
|
|
1893
1879
|
else {
|
|
1894
1880
|
if (setValue[$changes]) {
|
|
1895
1881
|
assertInstanceType(setValue, obj[$childType], obj, key);
|
|
1896
|
-
|
|
1882
|
+
const previousValue = obj.items[key];
|
|
1883
|
+
if (previousValue !== undefined) {
|
|
1897
1884
|
if (setValue[$changes].isNew) {
|
|
1898
1885
|
this[$changes].indexedOperation(Number(key), exports.OPERATION.MOVE_AND_ADD);
|
|
1899
1886
|
}
|
|
@@ -1905,10 +1892,13 @@ class ArraySchema {
|
|
|
1905
1892
|
this[$changes].indexedOperation(Number(key), exports.OPERATION.MOVE);
|
|
1906
1893
|
}
|
|
1907
1894
|
}
|
|
1895
|
+
// remove root reference from previous value
|
|
1896
|
+
previousValue[$changes].root?.remove(previousValue[$changes]);
|
|
1908
1897
|
}
|
|
1909
1898
|
else if (setValue[$changes].isNew) {
|
|
1910
1899
|
this[$changes].indexedOperation(Number(key), exports.OPERATION.ADD);
|
|
1911
1900
|
}
|
|
1901
|
+
setValue[$changes].setParent(this, obj[$changes].root, key);
|
|
1912
1902
|
}
|
|
1913
1903
|
else {
|
|
1914
1904
|
obj.$changeAt(Number(key), setValue);
|
|
@@ -2546,33 +2536,34 @@ class MapSchema {
|
|
|
2546
2536
|
// See: https://github.com/colyseus/colyseus/issues/561#issuecomment-1646733468
|
|
2547
2537
|
key = key.toString();
|
|
2548
2538
|
const changeTree = this[$changes];
|
|
2549
|
-
// get "index" for this value.
|
|
2550
|
-
const isReplace = typeof (changeTree.indexes[key]) !== "undefined";
|
|
2551
|
-
const index = (isReplace)
|
|
2552
|
-
? changeTree.indexes[key]
|
|
2553
|
-
: changeTree.indexes[$numFields] ?? 0;
|
|
2554
|
-
let operation = (isReplace)
|
|
2555
|
-
? exports.OPERATION.REPLACE
|
|
2556
|
-
: exports.OPERATION.ADD;
|
|
2557
2539
|
const isRef = (value[$changes]) !== undefined;
|
|
2558
|
-
|
|
2559
|
-
|
|
2560
|
-
//
|
|
2561
|
-
|
|
2562
|
-
|
|
2540
|
+
let index;
|
|
2541
|
+
let operation;
|
|
2542
|
+
// IS REPLACE?
|
|
2543
|
+
if (typeof (changeTree.indexes[key]) !== "undefined") {
|
|
2544
|
+
index = changeTree.indexes[key];
|
|
2545
|
+
operation = exports.OPERATION.REPLACE;
|
|
2546
|
+
const previousValue = this.$items.get(key);
|
|
2547
|
+
if (previousValue === value) {
|
|
2548
|
+
// if value is the same, avoid re-encoding it.
|
|
2549
|
+
return;
|
|
2550
|
+
}
|
|
2551
|
+
else if (isRef) {
|
|
2552
|
+
// if is schema, force ADD operation if value differ from previous one.
|
|
2553
|
+
operation = exports.OPERATION.DELETE_AND_ADD;
|
|
2554
|
+
// remove reference from previous value
|
|
2555
|
+
if (previousValue !== undefined) {
|
|
2556
|
+
previousValue[$changes].root?.remove(previousValue[$changes]);
|
|
2557
|
+
}
|
|
2558
|
+
}
|
|
2559
|
+
}
|
|
2560
|
+
else {
|
|
2561
|
+
index = changeTree.indexes[$numFields] ?? 0;
|
|
2562
|
+
operation = exports.OPERATION.ADD;
|
|
2563
2563
|
this.$indexes.set(index, key);
|
|
2564
2564
|
changeTree.indexes[key] = index;
|
|
2565
2565
|
changeTree.indexes[$numFields] = index + 1;
|
|
2566
2566
|
}
|
|
2567
|
-
else if (!isRef &&
|
|
2568
|
-
this.$items.get(key) === value) {
|
|
2569
|
-
// if value is the same, avoid re-encoding it.
|
|
2570
|
-
return;
|
|
2571
|
-
}
|
|
2572
|
-
else if (isRef && // if is schema, force ADD operation if value differ from previous one.
|
|
2573
|
-
this.$items.get(key) !== value) {
|
|
2574
|
-
operation = exports.OPERATION.ADD;
|
|
2575
|
-
}
|
|
2576
2567
|
this.$items.set(key, value);
|
|
2577
2568
|
changeTree.change(index, operation);
|
|
2578
2569
|
//
|
|
@@ -2944,13 +2935,14 @@ function getPropertyDescriptor(fieldCached, fieldIndex, type, complexTypeKlass)
|
|
|
2944
2935
|
const changeTree = this[$changes];
|
|
2945
2936
|
//
|
|
2946
2937
|
// Replacing existing "ref", remove it from root.
|
|
2947
|
-
// TODO: if there are other references to this instance, we should not remove it from root.
|
|
2948
2938
|
//
|
|
2949
2939
|
if (previousValue !== undefined && previousValue[$changes]) {
|
|
2950
2940
|
changeTree.root?.remove(previousValue[$changes]);
|
|
2941
|
+
this.constructor[$track](changeTree, fieldIndex, exports.OPERATION.DELETE_AND_ADD);
|
|
2942
|
+
}
|
|
2943
|
+
else {
|
|
2944
|
+
this.constructor[$track](changeTree, fieldIndex, exports.OPERATION.ADD);
|
|
2951
2945
|
}
|
|
2952
|
-
// flag the change for encoding.
|
|
2953
|
-
this.constructor[$track](changeTree, fieldIndex, exports.OPERATION.ADD);
|
|
2954
2946
|
//
|
|
2955
2947
|
// call setParent() recursively for this and its child
|
|
2956
2948
|
// structures.
|
|
@@ -3747,16 +3739,33 @@ class Root {
|
|
|
3747
3739
|
}
|
|
3748
3740
|
else {
|
|
3749
3741
|
this.refCount[changeTree.refId] = refCount;
|
|
3742
|
+
//
|
|
3743
|
+
// When losing a reference to an instance, it is best to move the
|
|
3744
|
+
// ChangeTree to the end of the encoding queue.
|
|
3745
|
+
//
|
|
3746
|
+
// This way, at decoding time, the instance that contains the
|
|
3747
|
+
// ChangeTree will be available before the ChangeTree itself. If the
|
|
3748
|
+
// containing instance is not available, the Decoder will throw
|
|
3749
|
+
// "refId not found" error.
|
|
3750
|
+
//
|
|
3751
|
+
if (changeTree.filteredChanges !== undefined) {
|
|
3752
|
+
this.removeChangeFromChangeSet("filteredChanges", changeTree);
|
|
3753
|
+
enqueueChangeTree(this, changeTree, "filteredChanges");
|
|
3754
|
+
}
|
|
3755
|
+
else {
|
|
3756
|
+
this.removeChangeFromChangeSet("changes", changeTree);
|
|
3757
|
+
enqueueChangeTree(this, changeTree, "changes");
|
|
3758
|
+
}
|
|
3750
3759
|
}
|
|
3751
3760
|
changeTree.forEachChild((child, _) => this.remove(child));
|
|
3752
3761
|
return refCount;
|
|
3753
3762
|
}
|
|
3754
3763
|
removeChangeFromChangeSet(changeSetName, changeTree) {
|
|
3755
3764
|
const changeSet = this[changeSetName];
|
|
3756
|
-
|
|
3757
|
-
|
|
3758
|
-
spliceOne(changeSet, index);
|
|
3765
|
+
if (spliceOne(changeSet, changeSet.indexOf(changeTree))) {
|
|
3766
|
+
changeTree[changeSetName].queueRootIndex = -1;
|
|
3759
3767
|
// changeSet[index] = undefined;
|
|
3768
|
+
return true;
|
|
3760
3769
|
}
|
|
3761
3770
|
}
|
|
3762
3771
|
clear() {
|
|
@@ -3792,12 +3801,6 @@ class Encoder {
|
|
|
3792
3801
|
const changeTrees = this.root[changeSetName];
|
|
3793
3802
|
for (let i = 0, numChangeTrees = changeTrees.length; i < numChangeTrees; i++) {
|
|
3794
3803
|
const changeTree = changeTrees[i];
|
|
3795
|
-
const operations = changeTree[changeSetName];
|
|
3796
|
-
const ref = changeTree.ref;
|
|
3797
|
-
const ctor = ref.constructor;
|
|
3798
|
-
const encoder = ctor[$encoder];
|
|
3799
|
-
const filter = ctor[$filter];
|
|
3800
|
-
const metadata = ctor[Symbol.metadata];
|
|
3801
3804
|
if (hasView) {
|
|
3802
3805
|
if (!view.items.has(changeTree)) {
|
|
3803
3806
|
view.invisible.add(changeTree);
|
|
@@ -3807,13 +3810,24 @@ class Encoder {
|
|
|
3807
3810
|
view.invisible.delete(changeTree); // remove from invisible list
|
|
3808
3811
|
}
|
|
3809
3812
|
}
|
|
3813
|
+
const operations = changeTree[changeSetName];
|
|
3814
|
+
const ref = changeTree.ref;
|
|
3815
|
+
// TODO: avoid iterating over change tree if no changes were made
|
|
3816
|
+
const numChanges = operations.operations.length;
|
|
3817
|
+
if (numChanges === 0) {
|
|
3818
|
+
continue;
|
|
3819
|
+
}
|
|
3820
|
+
const ctor = ref.constructor;
|
|
3821
|
+
const encoder = ctor[$encoder];
|
|
3822
|
+
const filter = ctor[$filter];
|
|
3823
|
+
const metadata = ctor[Symbol.metadata];
|
|
3810
3824
|
// skip root `refId` if it's the first change tree
|
|
3811
3825
|
// (unless it "hasView", which will need to revisit the root)
|
|
3812
3826
|
if (hasView || it.offset > initialOffset || changeTree !== rootChangeTree) {
|
|
3813
3827
|
buffer[it.offset++] = SWITCH_TO_STRUCTURE & 255;
|
|
3814
3828
|
encode.number(buffer, changeTree.refId, it);
|
|
3815
3829
|
}
|
|
3816
|
-
for (let j = 0
|
|
3830
|
+
for (let j = 0; j < numChanges; j++) {
|
|
3817
3831
|
const fieldIndex = operations.operations[j];
|
|
3818
3832
|
const operation = (fieldIndex < 0)
|
|
3819
3833
|
? Math.abs(fieldIndex) // "pure" operation without fieldIndex (e.g. CLEAR, REVERSE, etc.)
|
|
@@ -3910,14 +3924,16 @@ class Encoder {
|
|
|
3910
3924
|
encodeView(view, sharedOffset, it, bytes = this.sharedBuffer) {
|
|
3911
3925
|
const viewOffset = it.offset;
|
|
3912
3926
|
// encode visibility changes (add/remove for this view)
|
|
3913
|
-
const
|
|
3914
|
-
for (let i = 0, numRefIds = refIds.length; i < numRefIds; i++) {
|
|
3915
|
-
const refId = refIds[i];
|
|
3916
|
-
const changes = view.changes[refId];
|
|
3927
|
+
for (const [refId, changes] of view.changes) {
|
|
3917
3928
|
const changeTree = this.root.changeTrees[refId];
|
|
3918
|
-
if (changeTree === undefined
|
|
3919
|
-
|
|
3920
|
-
|
|
3929
|
+
if (changeTree === undefined) {
|
|
3930
|
+
// detached instance, remove from view and skip.
|
|
3931
|
+
view.changes.delete(refId);
|
|
3932
|
+
continue;
|
|
3933
|
+
}
|
|
3934
|
+
const keys = Object.keys(changes);
|
|
3935
|
+
if (keys.length === 0) {
|
|
3936
|
+
// FIXME: avoid having empty changes if no changes were made
|
|
3921
3937
|
// console.log("changes.size === 0, skip", changeTree.ref.constructor.name);
|
|
3922
3938
|
continue;
|
|
3923
3939
|
}
|
|
@@ -3927,7 +3943,6 @@ class Encoder {
|
|
|
3927
3943
|
const metadata = ctor[Symbol.metadata];
|
|
3928
3944
|
bytes[it.offset++] = SWITCH_TO_STRUCTURE & 255;
|
|
3929
3945
|
encode.number(bytes, changeTree.refId, it);
|
|
3930
|
-
const keys = Object.keys(changes);
|
|
3931
3946
|
for (let i = 0, numChanges = keys.length; i < numChanges; i++) {
|
|
3932
3947
|
const key = keys[i];
|
|
3933
3948
|
const operation = changes[key];
|
|
@@ -3941,7 +3956,7 @@ class Encoder {
|
|
|
3941
3956
|
// (to allow re-using StateView's for multiple clients)
|
|
3942
3957
|
//
|
|
3943
3958
|
// clear "view" changes after encoding
|
|
3944
|
-
view.changes
|
|
3959
|
+
view.changes.clear();
|
|
3945
3960
|
// try to encode "filtered" changes
|
|
3946
3961
|
this.encode(it, view, bytes, "filteredChanges", false, viewOffset);
|
|
3947
3962
|
return Buffer.concat([
|
|
@@ -3949,20 +3964,6 @@ class Encoder {
|
|
|
3949
3964
|
bytes.subarray(viewOffset, it.offset)
|
|
3950
3965
|
]);
|
|
3951
3966
|
}
|
|
3952
|
-
onEndEncode(changeTrees = this.root.changes) {
|
|
3953
|
-
// changeTrees.forEach(function(changeTree) {
|
|
3954
|
-
// changeTree.endEncode();
|
|
3955
|
-
// });
|
|
3956
|
-
// for (const refId in changeTrees) {
|
|
3957
|
-
// const changeTree = this.root.changeTrees[refId];
|
|
3958
|
-
// changeTree.endEncode();
|
|
3959
|
-
// // changeTree.changes.clear();
|
|
3960
|
-
// // // ArraySchema and MapSchema have a custom "encode end" method
|
|
3961
|
-
// // changeTree.ref[$onEncodeEnd]?.();
|
|
3962
|
-
// // // Not a new instance anymore
|
|
3963
|
-
// // delete changeTree[$isNew];
|
|
3964
|
-
// }
|
|
3965
|
-
}
|
|
3966
3967
|
discardChanges() {
|
|
3967
3968
|
// discard shared changes
|
|
3968
3969
|
let length = this.root.changes.length;
|
|
@@ -4694,7 +4695,8 @@ class StateView {
|
|
|
4694
4695
|
* Manual "ADD" operations for changes per ChangeTree, specific to this view.
|
|
4695
4696
|
* (This is used to force encoding a property, even if it was not changed)
|
|
4696
4697
|
*/
|
|
4697
|
-
|
|
4698
|
+
// TODO: use map here!? may fix encode ordering issue
|
|
4699
|
+
this.changes = new Map();
|
|
4698
4700
|
}
|
|
4699
4701
|
// TODO: allow to set multiple tags at once
|
|
4700
4702
|
add(obj, tag = DEFAULT_VIEW_TAG, checkIncludeParent = true) {
|
|
@@ -4710,16 +4712,16 @@ class StateView {
|
|
|
4710
4712
|
// - if it was invisible to this view
|
|
4711
4713
|
// - if it were previously filtered out
|
|
4712
4714
|
if (checkIncludeParent && changeTree.parent) {
|
|
4713
|
-
this.
|
|
4715
|
+
this.addParentOf(changeTree, tag);
|
|
4714
4716
|
}
|
|
4715
4717
|
//
|
|
4716
4718
|
// TODO: when adding an item of a MapSchema, the changes may not
|
|
4717
4719
|
// be set (only the parent's changes are set)
|
|
4718
4720
|
//
|
|
4719
|
-
let changes = this.changes
|
|
4721
|
+
let changes = this.changes.get(changeTree.refId);
|
|
4720
4722
|
if (changes === undefined) {
|
|
4721
4723
|
changes = {};
|
|
4722
|
-
this.changes
|
|
4724
|
+
this.changes.set(changeTree.refId, changes);
|
|
4723
4725
|
}
|
|
4724
4726
|
// set tag
|
|
4725
4727
|
if (tag !== DEFAULT_VIEW_TAG) {
|
|
@@ -4775,24 +4777,29 @@ class StateView {
|
|
|
4775
4777
|
});
|
|
4776
4778
|
return this;
|
|
4777
4779
|
}
|
|
4778
|
-
|
|
4780
|
+
addParentOf(childChangeTree, tag) {
|
|
4781
|
+
const changeTree = childChangeTree.parent[$changes];
|
|
4782
|
+
const parentIndex = childChangeTree.parentIndex;
|
|
4779
4783
|
// view must have all "changeTree" parent tree
|
|
4780
4784
|
this.items.add(changeTree);
|
|
4781
4785
|
// add parent's parent
|
|
4782
4786
|
const parentChangeTree = changeTree.parent?.[$changes];
|
|
4783
4787
|
if (parentChangeTree && (parentChangeTree.filteredChanges !== undefined)) {
|
|
4784
|
-
this.
|
|
4788
|
+
this.addParentOf(changeTree, tag);
|
|
4785
4789
|
}
|
|
4790
|
+
if (
|
|
4786
4791
|
// parent is already available, no need to add it!
|
|
4787
|
-
|
|
4792
|
+
!this.invisible.has(changeTree) &&
|
|
4793
|
+
// item is being replaced, no need to add parent
|
|
4794
|
+
changeTree.indexedOperations[parentIndex] !== exports.OPERATION.DELETE_AND_ADD) {
|
|
4788
4795
|
return;
|
|
4789
4796
|
}
|
|
4790
4797
|
// add parent's tag properties
|
|
4791
4798
|
if (changeTree.getChange(parentIndex) !== exports.OPERATION.DELETE) {
|
|
4792
|
-
let changes = this.changes
|
|
4799
|
+
let changes = this.changes.get(changeTree.refId);
|
|
4793
4800
|
if (changes === undefined) {
|
|
4794
4801
|
changes = {};
|
|
4795
|
-
this.changes
|
|
4802
|
+
this.changes.set(changeTree.refId, changes);
|
|
4796
4803
|
}
|
|
4797
4804
|
if (!this.tags) {
|
|
4798
4805
|
this.tags = new WeakMap();
|
|
@@ -4818,20 +4825,20 @@ class StateView {
|
|
|
4818
4825
|
this.items.delete(changeTree);
|
|
4819
4826
|
const ref = changeTree.ref;
|
|
4820
4827
|
const metadata = ref.constructor[Symbol.metadata];
|
|
4821
|
-
let changes = this.changes
|
|
4828
|
+
let changes = this.changes.get(changeTree.refId);
|
|
4822
4829
|
if (changes === undefined) {
|
|
4823
4830
|
changes = {};
|
|
4824
|
-
this.changes
|
|
4831
|
+
this.changes.set(changeTree.refId, changes);
|
|
4825
4832
|
}
|
|
4826
4833
|
if (tag === DEFAULT_VIEW_TAG) {
|
|
4827
4834
|
// parent is collection (Map/Array)
|
|
4828
4835
|
const parent = changeTree.parent;
|
|
4829
4836
|
if (!Metadata.isValidInstance(parent)) {
|
|
4830
4837
|
const parentChangeTree = parent[$changes];
|
|
4831
|
-
let changes = this.changes
|
|
4838
|
+
let changes = this.changes.get(parentChangeTree.refId);
|
|
4832
4839
|
if (changes === undefined) {
|
|
4833
4840
|
changes = {};
|
|
4834
|
-
this.changes
|
|
4841
|
+
this.changes.set(parentChangeTree.refId, changes);
|
|
4835
4842
|
}
|
|
4836
4843
|
// DELETE / DELETE BY REF ID
|
|
4837
4844
|
changes[changeTree.parentIndex] = exports.OPERATION.DELETE;
|