@colyseus/schema 3.0.75 → 4.0.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.
Files changed (157) hide show
  1. package/build/cjs/index.js +780 -429
  2. package/build/cjs/index.js.map +1 -1
  3. package/build/esm/index.mjs +778 -430
  4. package/build/esm/index.mjs.map +1 -1
  5. package/build/umd/index.js +780 -429
  6. package/lib/Reflection.d.ts +50 -17
  7. package/lib/Reflection.js +151 -202
  8. package/lib/Reflection.js.map +1 -1
  9. package/lib/Schema.d.ts +13 -1
  10. package/lib/Schema.js +73 -9
  11. package/lib/Schema.js.map +1 -1
  12. package/lib/annotations.d.ts +6 -1
  13. package/lib/annotations.js +8 -34
  14. package/lib/annotations.js.map +1 -1
  15. package/lib/bench_encode.js +34 -1
  16. package/lib/bench_encode.js.map +1 -1
  17. package/lib/codegen/api.js +35 -2
  18. package/lib/codegen/api.js.map +1 -1
  19. package/lib/codegen/cli.js +4 -1
  20. package/lib/codegen/cli.js.map +1 -1
  21. package/lib/codegen/parser.js +35 -2
  22. package/lib/codegen/parser.js.map +1 -1
  23. package/lib/codegen/types.js +34 -1
  24. package/lib/codegen/types.js.map +1 -1
  25. package/lib/decoder/DecodeOperation.d.ts +2 -2
  26. package/lib/decoder/DecodeOperation.js +3 -3
  27. package/lib/decoder/DecodeOperation.js.map +1 -1
  28. package/lib/decoder/Decoder.d.ts +3 -3
  29. package/lib/decoder/Decoder.js +2 -2
  30. package/lib/decoder/Decoder.js.map +1 -1
  31. package/lib/decoder/ReferenceTracker.d.ts +0 -1
  32. package/lib/decoder/ReferenceTracker.js +9 -7
  33. package/lib/decoder/ReferenceTracker.js.map +1 -1
  34. package/lib/decoder/strategy/Callbacks.d.ts +154 -0
  35. package/lib/decoder/strategy/Callbacks.js +340 -0
  36. package/lib/decoder/strategy/Callbacks.js.map +1 -0
  37. package/lib/decoder/strategy/{StateCallbacks.d.ts → getDecoderStateCallbacks.d.ts} +6 -0
  38. package/lib/decoder/strategy/{StateCallbacks.js → getDecoderStateCallbacks.js} +17 -10
  39. package/lib/decoder/strategy/getDecoderStateCallbacks.js.map +1 -0
  40. package/lib/encoder/ChangeTree.d.ts +2 -2
  41. package/lib/encoder/ChangeTree.js.map +1 -1
  42. package/lib/encoder/EncodeOperation.d.ts +2 -2
  43. package/lib/encoder/EncodeOperation.js +3 -3
  44. package/lib/encoder/EncodeOperation.js.map +1 -1
  45. package/lib/encoder/Encoder.d.ts +6 -6
  46. package/lib/encoder/Encoder.js +19 -18
  47. package/lib/encoder/Encoder.js.map +1 -1
  48. package/lib/encoder/Root.js +17 -14
  49. package/lib/encoder/Root.js.map +1 -1
  50. package/lib/encoder/StateView.js +13 -12
  51. package/lib/encoder/StateView.js.map +1 -1
  52. package/lib/encoding/decode.d.ts +2 -2
  53. package/lib/encoding/encode.d.ts +3 -1
  54. package/lib/encoding/encode.js.map +1 -1
  55. package/lib/index.d.ts +3 -2
  56. package/lib/index.js +7 -3
  57. package/lib/index.js.map +1 -1
  58. package/lib/types/HelperTypes.d.ts +7 -14
  59. package/lib/types/HelperTypes.js.map +1 -1
  60. package/lib/types/custom/ArraySchema.d.ts +2 -1
  61. package/lib/types/custom/ArraySchema.js.map +1 -1
  62. package/lib/types/custom/CollectionSchema.d.ts +2 -1
  63. package/lib/types/custom/CollectionSchema.js.map +1 -1
  64. package/lib/types/custom/MapSchema.d.ts +3 -2
  65. package/lib/types/custom/MapSchema.js.map +1 -1
  66. package/lib/types/custom/SetSchema.d.ts +2 -1
  67. package/lib/types/custom/SetSchema.js.map +1 -1
  68. package/lib/types/symbols.d.ts +1 -0
  69. package/lib/types/symbols.js +2 -1
  70. package/lib/types/symbols.js.map +1 -1
  71. package/lib/utils.js +1 -1
  72. package/lib/utils.js.map +1 -1
  73. package/package.json +12 -16
  74. package/src/Reflection.ts +185 -174
  75. package/src/Schema.ts +81 -13
  76. package/src/annotations.ts +14 -40
  77. package/src/codegen/parser.ts +1 -1
  78. package/src/decoder/DecodeOperation.ts +9 -9
  79. package/src/decoder/Decoder.ts +6 -6
  80. package/src/decoder/ReferenceTracker.ts +10 -8
  81. package/src/decoder/strategy/Callbacks.ts +547 -0
  82. package/src/decoder/strategy/{StateCallbacks.ts → getDecoderStateCallbacks.ts} +17 -11
  83. package/src/encoder/ChangeTree.ts +4 -7
  84. package/src/encoder/EncodeOperation.ts +9 -9
  85. package/src/encoder/Encoder.ts +26 -18
  86. package/src/encoder/Root.ts +20 -15
  87. package/src/encoder/StateView.ts +15 -13
  88. package/src/encoding/encode.ts +1 -1
  89. package/src/index.ts +3 -2
  90. package/src/types/HelperTypes.ts +13 -11
  91. package/src/types/custom/ArraySchema.ts +2 -1
  92. package/src/types/custom/CollectionSchema.ts +4 -2
  93. package/src/types/custom/MapSchema.ts +4 -2
  94. package/src/types/custom/SetSchema.ts +3 -1
  95. package/src/types/symbols.ts +1 -0
  96. package/src/utils.ts +2 -2
  97. package/lib/Decoder.d.ts +0 -16
  98. package/lib/Decoder.js +0 -182
  99. package/lib/Decoder.js.map +0 -1
  100. package/lib/Encoder.d.ts +0 -13
  101. package/lib/Encoder.js +0 -79
  102. package/lib/Encoder.js.map +0 -1
  103. package/lib/changes/ChangeSet.d.ts +0 -12
  104. package/lib/changes/ChangeSet.js +0 -35
  105. package/lib/changes/ChangeSet.js.map +0 -1
  106. package/lib/changes/ChangeTree.d.ts +0 -53
  107. package/lib/changes/ChangeTree.js +0 -202
  108. package/lib/changes/ChangeTree.js.map +0 -1
  109. package/lib/changes/DecodeOperation.d.ts +0 -15
  110. package/lib/changes/DecodeOperation.js +0 -186
  111. package/lib/changes/DecodeOperation.js.map +0 -1
  112. package/lib/changes/EncodeOperation.d.ts +0 -18
  113. package/lib/changes/EncodeOperation.js +0 -130
  114. package/lib/changes/EncodeOperation.js.map +0 -1
  115. package/lib/changes/ReferenceTracker.d.ts +0 -14
  116. package/lib/changes/ReferenceTracker.js +0 -83
  117. package/lib/changes/ReferenceTracker.js.map +0 -1
  118. package/lib/changes/consts.d.ts +0 -14
  119. package/lib/changes/consts.js +0 -18
  120. package/lib/changes/consts.js.map +0 -1
  121. package/lib/decoder/strategy/StateCallbacks.js.map +0 -1
  122. package/lib/decoding/decode.d.ts +0 -48
  123. package/lib/decoding/decode.js +0 -267
  124. package/lib/decoding/decode.js.map +0 -1
  125. package/lib/ecs.d.ts +0 -11
  126. package/lib/ecs.js +0 -160
  127. package/lib/ecs.js.map +0 -1
  128. package/lib/filters/index.d.ts +0 -8
  129. package/lib/filters/index.js +0 -24
  130. package/lib/filters/index.js.map +0 -1
  131. package/lib/spec.d.ts +0 -13
  132. package/lib/spec.js +0 -42
  133. package/lib/spec.js.map +0 -1
  134. package/lib/types/ArraySchema.d.ts +0 -238
  135. package/lib/types/ArraySchema.js +0 -555
  136. package/lib/types/ArraySchema.js.map +0 -1
  137. package/lib/types/CollectionSchema.d.ts +0 -35
  138. package/lib/types/CollectionSchema.js +0 -150
  139. package/lib/types/CollectionSchema.js.map +0 -1
  140. package/lib/types/MapSchema.d.ts +0 -38
  141. package/lib/types/MapSchema.js +0 -215
  142. package/lib/types/MapSchema.js.map +0 -1
  143. package/lib/types/SetSchema.d.ts +0 -32
  144. package/lib/types/SetSchema.js +0 -162
  145. package/lib/types/SetSchema.js.map +0 -1
  146. package/lib/types/typeRegistry.d.ts +0 -5
  147. package/lib/types/typeRegistry.js +0 -13
  148. package/lib/types/typeRegistry.js.map +0 -1
  149. package/lib/usage.d.ts +0 -1
  150. package/lib/usage.js +0 -22
  151. package/lib/usage.js.map +0 -1
  152. package/lib/v3.d.ts +0 -1
  153. package/lib/v3.js +0 -427
  154. package/lib/v3.js.map +0 -1
  155. package/lib/v3_experiment.d.ts +0 -1
  156. package/lib/v3_experiment.js +0 -407
  157. package/lib/v3_experiment.js.map +0 -1
package/lib/Decoder.js DELETED
@@ -1,182 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Decoder = void 0;
4
- const annotations_1 = require("./annotations");
5
- const consts_1 = require("./changes/consts");
6
- const decode = require("./encoding/decode");
7
- const spec_1 = require("./spec");
8
- const ReferenceTracker_1 = require("./changes/ReferenceTracker");
9
- const DecodeOperation_1 = require("./changes/DecodeOperation");
10
- class Decoder {
11
- constructor(root, context) {
12
- this.currentRefId = 0;
13
- this.setRoot(root);
14
- this.context = context || new annotations_1.TypeContext(root.constructor);
15
- // console.log(">>>>>>>>>>>>>>>> Decoder types");
16
- // this.context.schemas.forEach((id, schema) => {
17
- // console.log("type:", id, schema.name, Object.keys(schema[Symbol.metadata]));
18
- // });
19
- }
20
- setRoot(root) {
21
- this.root = root;
22
- this.refs = new ReferenceTracker_1.ReferenceTracker();
23
- this.refs.addRef(0, root);
24
- }
25
- decode(bytes, it = { offset: 0 }, ref = this.root) {
26
- // console.log("------------------- DECODE -------------------");
27
- const allChanges = [];
28
- const $root = this.refs;
29
- const totalBytes = bytes.length;
30
- this.currentRefId = 0;
31
- while (it.offset < totalBytes) {
32
- //
33
- // Peek ahead, check if it's a switch to a different structure
34
- //
35
- if (bytes[it.offset] == spec_1.SWITCH_TO_STRUCTURE) {
36
- it.offset++;
37
- this.currentRefId = decode.number(bytes, it);
38
- const nextRef = $root.refs.get(this.currentRefId);
39
- //
40
- // Trying to access a reference that haven't been decoded yet.
41
- //
42
- if (!nextRef) {
43
- throw new Error(`"refId" not found: ${this.currentRefId}`);
44
- }
45
- ref = nextRef;
46
- continue;
47
- }
48
- const decoder = ref['constructor'][consts_1.$decoder];
49
- const result = decoder(this, bytes, it, ref, allChanges);
50
- if (result === DecodeOperation_1.DecodeState.DEFINITION_MISMATCH) {
51
- console.warn("@colyseus/schema: definition mismatch");
52
- //
53
- // keep skipping next bytes until reaches a known structure
54
- // by local decoder.
55
- //
56
- const nextIterator = { offset: it.offset };
57
- while (it.offset < totalBytes) {
58
- if (decode.switchStructureCheck(bytes, it)) {
59
- nextIterator.offset = it.offset + 1;
60
- if ($root.refs.has(decode.number(bytes, nextIterator))) {
61
- break;
62
- }
63
- }
64
- it.offset++;
65
- }
66
- continue;
67
- }
68
- }
69
- // FIXME: trigger callbacks
70
- // this._triggerChanges(allChanges);
71
- // drop references of unused schemas
72
- $root.garbageCollectDeletedRefs();
73
- return allChanges;
74
- }
75
- /*
76
- private _triggerChanges(changes: DataChange[]) {
77
- const uniqueRefIds = new Set<number>();
78
- const $refs = this.refs.refs;
79
-
80
- for (let i = 0; i < changes.length; i++) {
81
- const change = changes[i];
82
- const refId = change.refId;
83
- const ref = $refs.get(refId);
84
- const $callbacks: Schema['$callbacks'] | SchemaDecoderCallbacks['$callbacks'] = ref['$callbacks'];
85
-
86
- //
87
- // trigger onRemove on child structure.
88
- //
89
- if (
90
- (change.op & OPERATION.DELETE) === OPERATION.DELETE &&
91
- change.previousValue instanceof Schema
92
- ) {
93
- change.previousValue['$callbacks']?.[OPERATION.DELETE]?.forEach(callback => callback());
94
- }
95
-
96
- // no callbacks defined, skip this structure!
97
- if (!$callbacks) { continue; }
98
-
99
- if (ref instanceof Schema) {
100
- if (!uniqueRefIds.has(refId)) {
101
- try {
102
- // trigger onChange
103
- ($callbacks as Schema['$callbacks'])?.[OPERATION.REPLACE]?.forEach(callback =>
104
- callback());
105
-
106
- } catch (e) {
107
- Schema.onError(e);
108
- }
109
- }
110
-
111
- try {
112
- if ($callbacks.hasOwnProperty(change.field)) {
113
- $callbacks[change.field]?.forEach((callback) =>
114
- callback(change.value, change.previousValue));
115
- }
116
-
117
- } catch (e) {
118
- Schema.onError(e);
119
- }
120
-
121
- } else {
122
- // is a collection of items
123
-
124
- if (change.op === OPERATION.ADD && change.previousValue === undefined) {
125
- // triger onAdd
126
- $callbacks[OPERATION.ADD]?.forEach(callback =>
127
- callback(change.value, change.dynamicIndex ?? change.field));
128
-
129
- } else if (change.op === OPERATION.DELETE) {
130
- //
131
- // FIXME: `previousValue` should always be available.
132
- // ADD + DELETE operations are still encoding DELETE operation.
133
- //
134
- if (change.previousValue !== undefined) {
135
- // triger onRemove
136
- $callbacks[OPERATION.DELETE]?.forEach(callback =>
137
- callback(change.previousValue, change.dynamicIndex ?? change.field));
138
- }
139
-
140
- } else if (change.op === OPERATION.DELETE_AND_ADD) {
141
- // triger onRemove
142
- if (change.previousValue !== undefined) {
143
- $callbacks[OPERATION.DELETE]?.forEach(callback =>
144
- callback(change.previousValue, change.dynamicIndex ?? change.field));
145
- }
146
-
147
- // triger onAdd
148
- $callbacks[OPERATION.ADD]?.forEach(callback =>
149
- callback(change.value, change.dynamicIndex ?? change.field));
150
- }
151
-
152
- // trigger onChange
153
- if (change.value !== change.previousValue) {
154
- $callbacks[OPERATION.REPLACE]?.forEach(callback =>
155
- callback(change.value, change.dynamicIndex ?? change.field));
156
- }
157
- }
158
-
159
- uniqueRefIds.add(refId);
160
- }
161
-
162
- }
163
- */
164
- getInstanceType(bytes, it, defaultType) {
165
- let type;
166
- if (bytes[it.offset] === spec_1.TYPE_ID) {
167
- it.offset++;
168
- const type_id = decode.number(bytes, it);
169
- type = this.context.get(type_id);
170
- }
171
- return type || defaultType;
172
- }
173
- createInstanceOfType(type) {
174
- // let instance: Schema = new (type as any)();
175
- // // assign root on $changes
176
- // instance[$changes].root = this.root[$changes].root;
177
- // return instance;
178
- return new type();
179
- }
180
- }
181
- exports.Decoder = Decoder;
182
- //# sourceMappingURL=Decoder.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"Decoder.js","sourceRoot":"","sources":["../src/Decoder.ts"],"names":[],"mappings":"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","sourcesContent":["import { Metadata } from \"./Metadata\";\nimport { TypeContext } from \"./annotations\";\nimport { $childType, $decoder } from \"./changes/consts\";\nimport { DataChange, Schema, SchemaDecoderCallbacks } from \"./Schema\";\nimport { CollectionSchema } from \"./types/CollectionSchema\";\nimport { MapSchema } from \"./types/MapSchema\";\nimport { SetSchema } from \"./types/SetSchema\";\nimport { ArraySchema } from \"./types/ArraySchema\";\n\nimport * as decode from \"./encoding/decode\";\nimport { getType } from './types/typeRegistry';\nimport { SWITCH_TO_STRUCTURE, TYPE_ID, OPERATION } from './spec';\nimport { Ref } from \"./changes/ChangeTree\";\nimport { Iterator } from \"./encoding/decode\";\nimport { ReferenceTracker } from \"./changes/ReferenceTracker\";\nimport { DecodeState } from \"./changes/DecodeOperation\";\n\nexport class Decoder<T extends Schema = any> {\n context: TypeContext;\n\n root: T;\n refs: ReferenceTracker;\n\n currentRefId: number = 0;\n\n constructor(root: T, context?: TypeContext) {\n this.setRoot(root);\n this.context = context || new TypeContext(root.constructor as typeof Schema);\n\n // console.log(\">>>>>>>>>>>>>>>> Decoder types\");\n // this.context.schemas.forEach((id, schema) => {\n // console.log(\"type:\", id, schema.name, Object.keys(schema[Symbol.metadata]));\n // });\n }\n\n protected setRoot(root: T) {\n this.root = root;\n this.refs = new ReferenceTracker();\n this.refs.addRef(0, root);\n }\n\n decode(\n bytes: number[],\n it: Iterator = { offset: 0 },\n ref: Ref = this.root,\n ) {\n // console.log(\"------------------- DECODE -------------------\");\n const allChanges: DataChange[] = [];\n\n const $root = this.refs;\n const totalBytes = bytes.length;\n\n this.currentRefId = 0;\n\n while (it.offset < totalBytes) {\n //\n // Peek ahead, check if it's a switch to a different structure\n //\n if (bytes[it.offset] == SWITCH_TO_STRUCTURE) {\n it.offset++;\n\n this.currentRefId = decode.number(bytes, it);\n const nextRef = $root.refs.get(this.currentRefId) as Schema;\n\n //\n // Trying to access a reference that haven't been decoded yet.\n //\n if (!nextRef) { throw new Error(`\"refId\" not found: ${this.currentRefId}`); }\n ref = nextRef;\n\n continue;\n }\n\n const decoder = ref['constructor'][$decoder];\n const result = decoder(this, bytes, it, ref, allChanges);\n\n if (result === DecodeState.DEFINITION_MISMATCH) {\n console.warn(\"@colyseus/schema: definition mismatch\");\n\n //\n // keep skipping next bytes until reaches a known structure\n // by local decoder.\n //\n const nextIterator: decode.Iterator = { offset: it.offset };\n while (it.offset < totalBytes) {\n if (decode.switchStructureCheck(bytes, it)) {\n nextIterator.offset = it.offset + 1;\n if ($root.refs.has(decode.number(bytes, nextIterator))) {\n break;\n }\n }\n\n it.offset++;\n }\n continue;\n }\n }\n\n // FIXME: trigger callbacks\n // this._triggerChanges(allChanges);\n\n // drop references of unused schemas\n $root.garbageCollectDeletedRefs();\n\n return allChanges;\n }\n\n /*\n private _triggerChanges(changes: DataChange[]) {\n const uniqueRefIds = new Set<number>();\n const $refs = this.refs.refs;\n\n for (let i = 0; i < changes.length; i++) {\n const change = changes[i];\n const refId = change.refId;\n const ref = $refs.get(refId);\n const $callbacks: Schema['$callbacks'] | SchemaDecoderCallbacks['$callbacks'] = ref['$callbacks'];\n\n //\n // trigger onRemove on child structure.\n //\n if (\n (change.op & OPERATION.DELETE) === OPERATION.DELETE &&\n change.previousValue instanceof Schema\n ) {\n change.previousValue['$callbacks']?.[OPERATION.DELETE]?.forEach(callback => callback());\n }\n\n // no callbacks defined, skip this structure!\n if (!$callbacks) { continue; }\n\n if (ref instanceof Schema) {\n if (!uniqueRefIds.has(refId)) {\n try {\n // trigger onChange\n ($callbacks as Schema['$callbacks'])?.[OPERATION.REPLACE]?.forEach(callback =>\n callback());\n\n } catch (e) {\n Schema.onError(e);\n }\n }\n\n try {\n if ($callbacks.hasOwnProperty(change.field)) {\n $callbacks[change.field]?.forEach((callback) =>\n callback(change.value, change.previousValue));\n }\n\n } catch (e) {\n Schema.onError(e);\n }\n\n } else {\n // is a collection of items\n\n if (change.op === OPERATION.ADD && change.previousValue === undefined) {\n // triger onAdd\n $callbacks[OPERATION.ADD]?.forEach(callback =>\n callback(change.value, change.dynamicIndex ?? change.field));\n\n } else if (change.op === OPERATION.DELETE) {\n //\n // FIXME: `previousValue` should always be available.\n // ADD + DELETE operations are still encoding DELETE operation.\n //\n if (change.previousValue !== undefined) {\n // triger onRemove\n $callbacks[OPERATION.DELETE]?.forEach(callback =>\n callback(change.previousValue, change.dynamicIndex ?? change.field));\n }\n\n } else if (change.op === OPERATION.DELETE_AND_ADD) {\n // triger onRemove\n if (change.previousValue !== undefined) {\n $callbacks[OPERATION.DELETE]?.forEach(callback =>\n callback(change.previousValue, change.dynamicIndex ?? change.field));\n }\n\n // triger onAdd\n $callbacks[OPERATION.ADD]?.forEach(callback =>\n callback(change.value, change.dynamicIndex ?? change.field));\n }\n\n // trigger onChange\n if (change.value !== change.previousValue) {\n $callbacks[OPERATION.REPLACE]?.forEach(callback =>\n callback(change.value, change.dynamicIndex ?? change.field));\n }\n }\n\n uniqueRefIds.add(refId);\n }\n\n }\n */\n\n getInstanceType(bytes: number[], it: Iterator, defaultType: typeof Schema): typeof Schema {\n let type: typeof Schema;\n\n if (bytes[it.offset] === TYPE_ID) {\n it.offset++;\n const type_id = decode.number(bytes, it);\n type = this.context.get(type_id);\n }\n\n return type || defaultType;\n }\n\n createInstanceOfType (type: typeof Schema): Schema {\n // let instance: Schema = new (type as any)();\n\n // // assign root on $changes\n // instance[$changes].root = this.root[$changes].root;\n\n // return instance;\n return new (type as any)();\n }\n\n}\n\n"]}
package/lib/Encoder.d.ts DELETED
@@ -1,13 +0,0 @@
1
- import type { Schema } from "./Schema";
2
- import { TypeContext } from "./annotations";
3
- import { Root } from "./changes/ChangeTree";
4
- export declare class Encoder<T extends Schema = any> {
5
- context: TypeContext;
6
- root: T;
7
- $root: Root;
8
- constructor(root: T);
9
- protected setRoot(root: T): void;
10
- encode(encodeAll?: boolean, bytes?: number[], useFilters?: boolean): number[];
11
- encodeAll(useFilters?: boolean): number[];
12
- tryEncodeTypeId(bytes: number[], baseType: typeof Schema, targetType: typeof Schema): void;
13
- }
package/lib/Encoder.js DELETED
@@ -1,79 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Encoder = void 0;
4
- const annotations_1 = require("./annotations");
5
- const consts_1 = require("./changes/consts");
6
- const encode = require("./encoding/encode");
7
- const spec_1 = require("./spec");
8
- const ChangeTree_1 = require("./changes/ChangeTree");
9
- class Encoder {
10
- constructor(root) {
11
- this.setRoot(root);
12
- //
13
- // TODO: cache and restore "Context" based on root schema
14
- // (to avoid creating a new context for each new room)
15
- //
16
- this.context = new annotations_1.TypeContext(root.constructor);
17
- // console.log(">>>>>>>>>>>>>>>> Encoder types");
18
- // this.context.schemas.forEach((id, schema) => {
19
- // console.log("type:", id, schema.name, Object.keys(schema[Symbol.metadata]));
20
- // });
21
- }
22
- setRoot(root) {
23
- this.$root = new ChangeTree_1.Root();
24
- this.root = root;
25
- root[consts_1.$changes].setRoot(this.$root);
26
- }
27
- encode(encodeAll = false, bytes = [], useFilters = false) {
28
- const rootChangeTree = this.root[consts_1.$changes];
29
- // const changeTrees: ChangeTracker[] = Array.from(this.$root['currentQueue']);
30
- const changeTrees = this.$root.changes;
31
- const numChangeTrees = changeTrees.length;
32
- // let numChangeTrees = 1;
33
- // console.log("--------------------- ENCODE ----------------");
34
- // console.log("Encode order:", changeTrees.map((c) => c.ref['constructor'].name));
35
- for (let i = 0; i < numChangeTrees; i++) {
36
- const changeTree = changeTrees[i];
37
- const ref = changeTree.ref;
38
- // Generate unique refId for the ChangeTree.
39
- changeTree.ensureRefId();
40
- // root `refId` is skipped.
41
- if (changeTree !== rootChangeTree &&
42
- (changeTree.changed || encodeAll)) {
43
- encode.uint8(bytes, spec_1.SWITCH_TO_STRUCTURE);
44
- encode.number(bytes, changeTree.refId);
45
- }
46
- const changes = (encodeAll)
47
- ? changeTree.allChanges.values()
48
- : changeTree.changes.values();
49
- let change;
50
- while (!(change = changes.next()).done) {
51
- const operation = (encodeAll)
52
- ? spec_1.OPERATION.ADD
53
- : change.value.op;
54
- const fieldIndex = (encodeAll)
55
- ? change.value
56
- : change.value.index;
57
- const encoder = ref['constructor'][consts_1.$encoder];
58
- encoder(this, bytes, changeTree, fieldIndex, operation);
59
- }
60
- if (!encodeAll && !useFilters) {
61
- changeTree.discard();
62
- }
63
- }
64
- return bytes;
65
- }
66
- encodeAll(useFilters) {
67
- return this.encode(true, [], useFilters);
68
- }
69
- tryEncodeTypeId(bytes, baseType, targetType) {
70
- const baseTypeId = this.context.getTypeId(baseType);
71
- const targetTypeId = this.context.getTypeId(targetType);
72
- if (baseTypeId !== targetTypeId) {
73
- encode.uint8(bytes, spec_1.TYPE_ID);
74
- encode.number(bytes, targetTypeId);
75
- }
76
- }
77
- }
78
- exports.Encoder = Encoder;
79
- //# sourceMappingURL=Encoder.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"Encoder.js","sourceRoot":"","sources":["../src/Encoder.ts"],"names":[],"mappings":"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","sourcesContent":["import type { Schema } from \"./Schema\";\nimport { TypeContext } from \"./annotations\";\nimport { $changes, $encoder } from \"./changes/consts\";\n\nimport * as encode from \"./encoding/encode\";\nimport { SWITCH_TO_STRUCTURE, TYPE_ID, OPERATION } from './spec';\nimport { ChangeOperation, ChangeTracker, Root } from \"./changes/ChangeTree\";\nimport { encodeKeyValueOperation, encodeSchemaOperation } from \"./changes/EncodeOperation\";\n\nexport class Encoder<T extends Schema = any> {\n context: TypeContext;\n\n root: T;\n $root: Root;\n\n constructor(root: T) {\n this.setRoot(root);\n\n //\n // TODO: cache and restore \"Context\" based on root schema\n // (to avoid creating a new context for each new room)\n //\n this.context = new TypeContext(root.constructor as typeof Schema);\n\n // console.log(\">>>>>>>>>>>>>>>> Encoder types\");\n // this.context.schemas.forEach((id, schema) => {\n // console.log(\"type:\", id, schema.name, Object.keys(schema[Symbol.metadata]));\n // });\n }\n\n protected setRoot(root: T) {\n this.$root = new Root();\n this.root = root;\n root[$changes].setRoot(this.$root);\n }\n\n encode(\n encodeAll = false,\n bytes: number[] = [],\n useFilters: boolean = false,\n ) {\n const rootChangeTree = this.root[$changes];\n\n // const changeTrees: ChangeTracker[] = Array.from(this.$root['currentQueue']);\n const changeTrees: ChangeTracker[] = this.$root.changes;\n const numChangeTrees = changeTrees.length;\n // let numChangeTrees = 1;\n\n // console.log(\"--------------------- ENCODE ----------------\");\n // console.log(\"Encode order:\", changeTrees.map((c) => c.ref['constructor'].name));\n for (let i = 0; i < numChangeTrees; i++) {\n const changeTree = changeTrees[i];\n const ref = changeTree.ref;\n\n // Generate unique refId for the ChangeTree.\n changeTree.ensureRefId();\n\n // root `refId` is skipped.\n if (\n changeTree !== rootChangeTree &&\n (changeTree.changed || encodeAll)\n ) {\n encode.uint8(bytes, SWITCH_TO_STRUCTURE);\n encode.number(bytes, changeTree.refId);\n }\n\n const changes: IterableIterator<ChangeOperation | number> = (encodeAll)\n ? changeTree.allChanges.values()\n : changeTree.changes.values();\n\n let change: IteratorResult<ChangeOperation | number>;\n while (!(change = changes.next()).done) {\n const operation = (encodeAll)\n ? OPERATION.ADD\n : change.value.op;\n\n const fieldIndex = (encodeAll)\n ? change.value\n : change.value.index;\n\n const encoder = ref['constructor'][$encoder];\n encoder(this, bytes, changeTree, fieldIndex, operation);\n }\n\n if (!encodeAll && !useFilters) {\n changeTree.discard();\n }\n }\n\n return bytes;\n }\n\n encodeAll (useFilters?: boolean) {\n return this.encode(true, [], useFilters);\n }\n\n tryEncodeTypeId (bytes: number[], baseType: typeof Schema, targetType: typeof Schema) {\n const baseTypeId = this.context.getTypeId(baseType);\n const targetTypeId = this.context.getTypeId(targetType);\n\n if (baseTypeId !== targetTypeId) {\n encode.uint8(bytes, TYPE_ID);\n encode.number(bytes, targetTypeId);\n }\n }\n\n}"]}
@@ -1,12 +0,0 @@
1
- import { OPERATION } from "../spec";
2
- import { ChangeOperation } from "./ChangeTree";
3
- export declare class ChangeSet {
4
- changes: {
5
- [index: number]: ChangeOperation;
6
- };
7
- changed: boolean;
8
- allChanges: Set<number>;
9
- change(index: number, operation?: OPERATION): void;
10
- discardAll(): void;
11
- setParent(...args: any[]): void;
12
- }
@@ -1,35 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.ChangeSet = void 0;
4
- const spec_1 = require("../spec");
5
- class ChangeSet {
6
- changes = {};
7
- changed = false;
8
- allChanges = new Set();
9
- // definition: SchemaDefinition;
10
- change(index, operation = spec_1.OPERATION.ADD) {
11
- const previousChange = this.changes[index];
12
- if (!previousChange ||
13
- previousChange.op === spec_1.OPERATION.DELETE ||
14
- previousChange.op === spec_1.OPERATION.TOUCH // (mazmorra.io's BattleAction issue)
15
- ) {
16
- this.changes[index] = {
17
- op: (!previousChange)
18
- ? operation
19
- : (previousChange.op === spec_1.OPERATION.DELETE)
20
- ? spec_1.OPERATION.DELETE_AND_ADD
21
- : operation,
22
- index
23
- };
24
- }
25
- this.allChanges.add(index);
26
- this.changed = true;
27
- }
28
- discardAll() {
29
- this.changes = {};
30
- }
31
- setParent(...args) {
32
- }
33
- }
34
- exports.ChangeSet = ChangeSet;
35
- //# sourceMappingURL=ChangeSet.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"ChangeSet.js","sourceRoot":"","sources":["../../src/changes/ChangeSet.ts"],"names":[],"mappings":";;;AAAA,kCAAoC;AAIpC,MAAa,SAAS;IAClB,OAAO,GAAyC,EAAE,CAAC;IACnD,OAAO,GAAY,KAAK,CAAC;IACzB,UAAU,GAAgB,IAAI,GAAG,EAAE,CAAC;IACpC,gCAAgC;IAEhC,MAAM,CAAC,KAAa,EAAE,YAAuB,gBAAS,CAAC,GAAG;QACtD,MAAM,cAAc,GAAG,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;QAE3C,IACI,CAAC,cAAc;YACf,cAAc,CAAC,EAAE,KAAK,gBAAS,CAAC,MAAM;YACtC,cAAc,CAAC,EAAE,KAAK,gBAAS,CAAC,KAAK,CAAC,qCAAqC;UAC7E,CAAC;YACC,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,GAAG;gBAClB,EAAE,EAAE,CAAC,CAAC,cAAc,CAAC;oBACjB,CAAC,CAAC,SAAS;oBACX,CAAC,CAAC,CAAC,cAAc,CAAC,EAAE,KAAK,gBAAS,CAAC,MAAM,CAAC;wBACtC,CAAC,CAAC,gBAAS,CAAC,cAAc;wBAC1B,CAAC,CAAC,SAAS;gBACnB,KAAK;aACR,CAAC;QACN,CAAC;QAED,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,KAAK,CAAC,CAAC;QAE3B,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC;IACxB,CAAC;IAED,UAAU;QACN,IAAI,CAAC,OAAO,GAAG,EAAE,CAAC;IACtB,CAAC;IAED,SAAS,CAAC,GAAG,IAAW;IACxB,CAAC;CAEJ;AApCD,8BAoCC","sourcesContent":["import { OPERATION } from \"../spec\";\nimport { SchemaDefinition } from \"../annotations\";\nimport { ChangeOperation, Ref } from \"./ChangeTree\";\n\nexport class ChangeSet {\n changes: { [index: number]: ChangeOperation } = {};\n changed: boolean = false;\n allChanges: Set<number> = new Set();\n // definition: SchemaDefinition;\n\n change(index: number, operation: OPERATION = OPERATION.ADD) {\n const previousChange = this.changes[index];\n\n if (\n !previousChange ||\n previousChange.op === OPERATION.DELETE ||\n previousChange.op === OPERATION.TOUCH // (mazmorra.io's BattleAction issue)\n ) {\n this.changes[index] = {\n op: (!previousChange)\n ? operation\n : (previousChange.op === OPERATION.DELETE)\n ? OPERATION.DELETE_AND_ADD\n : operation,\n index\n };\n }\n\n this.allChanges.add(index);\n\n this.changed = true;\n }\n\n discardAll() {\n this.changes = {};\n }\n\n setParent(...args: any[]) {\n }\n\n}"]}
@@ -1,53 +0,0 @@
1
- import { OPERATION } from "../spec";
2
- import { Schema } from "../Schema";
3
- import { FilterChildrenCallback } from "../annotations";
4
- import { MapSchema } from "../types/MapSchema";
5
- import { ArraySchema } from "../types/ArraySchema";
6
- import { CollectionSchema } from "../types/CollectionSchema";
7
- import { SetSchema } from "../types/SetSchema";
8
- import { ReferenceTracker } from "./ReferenceTracker";
9
- export type Ref = Schema | ArraySchema | MapSchema | CollectionSchema | SetSchema;
10
- export interface ChangeOperation {
11
- op: OPERATION;
12
- index: number;
13
- }
14
- export interface FieldCache {
15
- beginIndex: number;
16
- endIndex: number;
17
- }
18
- export declare class ChangeTree {
19
- ref: Ref;
20
- refId: number;
21
- root?: ReferenceTracker;
22
- parent?: Ref;
23
- parentIndex?: number;
24
- indexes: {
25
- [index: string]: any;
26
- };
27
- changed: boolean;
28
- changes: Map<number, ChangeOperation>;
29
- allChanges: Set<number>;
30
- caches: {
31
- [field: number]: number[];
32
- };
33
- currentCustomOperation: number;
34
- constructor(ref: Ref, parent?: Ref, root?: ReferenceTracker);
35
- setParent(parent: Ref, root?: ReferenceTracker, parentIndex?: number): void;
36
- operation(op: ChangeOperation): void;
37
- change(fieldName: string | number, operation?: OPERATION): void;
38
- touch(fieldName: string | number): void;
39
- touchParents(): void;
40
- getType(index?: number): any;
41
- getChildrenFilter(): FilterChildrenCallback;
42
- getValue(index: number): any;
43
- delete(fieldName: string | number): void;
44
- discard(changed?: boolean, discardAll?: boolean): void;
45
- /**
46
- * Recursively discard all changes from this, and child structures.
47
- */
48
- discardAll(): void;
49
- cache(field: number, cachedBytes: number[]): void;
50
- clone(): ChangeTree;
51
- ensureRefId(): void;
52
- protected assertValidIndex(index: number, fieldName: string | number): void;
53
- }
@@ -1,202 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.ChangeTree = void 0;
4
- const spec_1 = require("../spec");
5
- const Schema_1 = require("../Schema");
6
- class ChangeTree {
7
- constructor(ref, parent, root) {
8
- this.changed = false;
9
- this.changes = new Map();
10
- this.allChanges = new Set();
11
- // cached indexes for filtering
12
- this.caches = {};
13
- this.currentCustomOperation = 0;
14
- this.ref = ref;
15
- this.setParent(parent, root);
16
- }
17
- setParent(parent, root, parentIndex) {
18
- if (!this.indexes) {
19
- this.indexes = (this.ref instanceof Schema_1.Schema)
20
- ? this.ref['_definition'].indexes
21
- : {};
22
- }
23
- this.parent = parent;
24
- this.parentIndex = parentIndex;
25
- // avoid setting parents with empty `root`
26
- if (!root) {
27
- return;
28
- }
29
- this.root = root;
30
- //
31
- // assign same parent on child structures
32
- //
33
- if (this.ref instanceof Schema_1.Schema) {
34
- const definition = this.ref['_definition'];
35
- for (let field in definition.schema) {
36
- const value = this.ref[field];
37
- if (value && value['$changes']) {
38
- const parentIndex = definition.indexes[field];
39
- value['$changes'].setParent(this.ref, root, parentIndex);
40
- }
41
- }
42
- }
43
- else if (typeof (this.ref) === "object") {
44
- this.ref.forEach((value, key) => {
45
- if (value instanceof Schema_1.Schema) {
46
- const changeTreee = value['$changes'];
47
- const parentIndex = this.ref['$changes'].indexes[key];
48
- changeTreee.setParent(this.ref, this.root, parentIndex);
49
- }
50
- });
51
- }
52
- }
53
- operation(op) {
54
- this.changes.set(--this.currentCustomOperation, op);
55
- }
56
- change(fieldName, operation = spec_1.OPERATION.ADD) {
57
- const index = (typeof (fieldName) === "number")
58
- ? fieldName
59
- : this.indexes[fieldName];
60
- this.assertValidIndex(index, fieldName);
61
- const previousChange = this.changes.get(index);
62
- if (!previousChange ||
63
- previousChange.op === spec_1.OPERATION.DELETE ||
64
- previousChange.op === spec_1.OPERATION.TOUCH // (mazmorra.io's BattleAction issue)
65
- ) {
66
- this.changes.set(index, {
67
- op: (!previousChange)
68
- ? operation
69
- : (previousChange.op === spec_1.OPERATION.DELETE)
70
- ? spec_1.OPERATION.DELETE_AND_ADD
71
- : operation,
72
- // : OPERATION.REPLACE,
73
- index
74
- });
75
- }
76
- this.allChanges.add(index);
77
- this.changed = true;
78
- this.touchParents();
79
- }
80
- touch(fieldName) {
81
- const index = (typeof (fieldName) === "number")
82
- ? fieldName
83
- : this.indexes[fieldName];
84
- this.assertValidIndex(index, fieldName);
85
- if (!this.changes.has(index)) {
86
- this.changes.set(index, { op: spec_1.OPERATION.TOUCH, index });
87
- }
88
- this.allChanges.add(index);
89
- // ensure touch is placed until the $root is found.
90
- this.touchParents();
91
- }
92
- touchParents() {
93
- if (this.parent) {
94
- this.parent['$changes'].touch(this.parentIndex);
95
- }
96
- }
97
- getType(index) {
98
- if (this.ref['_definition']) {
99
- const definition = this.ref['_definition'];
100
- return definition.schema[definition.fieldsByIndex[index]];
101
- }
102
- else {
103
- const definition = this.parent['_definition'];
104
- const parentType = definition.schema[definition.fieldsByIndex[this.parentIndex]];
105
- //
106
- // Get the child type from parent structure.
107
- // - ["string"] => "string"
108
- // - { map: "string" } => "string"
109
- // - { set: "string" } => "string"
110
- //
111
- return Object.values(parentType)[0];
112
- }
113
- }
114
- getChildrenFilter() {
115
- const childFilters = this.parent['_definition'].childFilters;
116
- return childFilters && childFilters[this.parentIndex];
117
- }
118
- //
119
- // used during `.encode()`
120
- //
121
- getValue(index) {
122
- return this.ref['getByIndex'](index);
123
- }
124
- delete(fieldName) {
125
- const index = (typeof (fieldName) === "number")
126
- ? fieldName
127
- : this.indexes[fieldName];
128
- if (index === undefined) {
129
- console.warn(`@colyseus/schema ${this.ref.constructor.name}: trying to delete non-existing index: ${fieldName} (${index})`);
130
- return;
131
- }
132
- const previousValue = this.getValue(index);
133
- // console.log("$changes.delete =>", { fieldName, index, previousValue });
134
- this.changes.set(index, { op: spec_1.OPERATION.DELETE, index });
135
- this.allChanges.delete(index);
136
- // delete cache
137
- delete this.caches[index];
138
- // remove `root` reference
139
- if (previousValue && previousValue['$changes']) {
140
- previousValue['$changes'].parent = undefined;
141
- }
142
- this.changed = true;
143
- this.touchParents();
144
- }
145
- discard(changed = false, discardAll = false) {
146
- //
147
- // Map, Array, etc:
148
- // Remove cached key to ensure ADD operations is unsed instead of
149
- // REPLACE in case same key is used on next patches.
150
- //
151
- // TODO: refactor this. this is not relevant for Collection and Set.
152
- //
153
- if (!(this.ref instanceof Schema_1.Schema)) {
154
- this.changes.forEach((change) => {
155
- if (change.op === spec_1.OPERATION.DELETE) {
156
- const index = this.ref['getIndex'](change.index);
157
- delete this.indexes[index];
158
- }
159
- });
160
- }
161
- this.changes.clear();
162
- this.changed = changed;
163
- if (discardAll) {
164
- this.allChanges.clear();
165
- }
166
- // re-set `currentCustomOperation`
167
- this.currentCustomOperation = 0;
168
- }
169
- /**
170
- * Recursively discard all changes from this, and child structures.
171
- */
172
- discardAll() {
173
- this.changes.forEach((change) => {
174
- const value = this.getValue(change.index);
175
- if (value && value['$changes']) {
176
- value['$changes'].discardAll();
177
- }
178
- });
179
- this.discard();
180
- }
181
- // cache(field: number, beginIndex: number, endIndex: number) {
182
- cache(field, cachedBytes) {
183
- this.caches[field] = cachedBytes;
184
- }
185
- clone() {
186
- return new ChangeTree(this.ref, this.parent, this.root);
187
- }
188
- ensureRefId() {
189
- // skip if refId is already set.
190
- if (this.refId !== undefined) {
191
- return;
192
- }
193
- this.refId = this.root.getNextUniqueId();
194
- }
195
- assertValidIndex(index, fieldName) {
196
- if (index === undefined) {
197
- throw new Error(`ChangeTree: missing index for field "${fieldName}"`);
198
- }
199
- }
200
- }
201
- exports.ChangeTree = ChangeTree;
202
- //# sourceMappingURL=ChangeTree.js.map