reactronic 0.22.306 → 0.22.309

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 (45) hide show
  1. package/build/dist/source/Buffer.d.ts +8 -0
  2. package/build/dist/source/Buffer.js +8 -0
  3. package/build/dist/source/Controller.d.ts +12 -0
  4. package/build/dist/source/Controller.js +6 -0
  5. package/build/dist/source/Logging.d.ts +38 -0
  6. package/build/dist/source/Logging.js +113 -0
  7. package/build/dist/source/Options.d.ts +38 -0
  8. package/build/dist/source/Options.js +21 -0
  9. package/build/dist/source/Ref.d.ts +34 -0
  10. package/build/dist/source/Ref.js +90 -0
  11. package/build/dist/source/Rx.d.ts +27 -0
  12. package/build/dist/source/Rx.js +58 -0
  13. package/build/dist/source/Worker.d.ts +8 -0
  14. package/build/dist/source/Worker.js +2 -0
  15. package/build/dist/source/api.d.ts +14 -0
  16. package/build/dist/source/api.js +42 -0
  17. package/build/dist/source/impl/Changeset.d.ts +60 -0
  18. package/build/dist/source/impl/Changeset.js +361 -0
  19. package/build/dist/source/impl/Data.d.ts +60 -0
  20. package/build/dist/source/impl/Data.js +51 -0
  21. package/build/dist/source/impl/Hooks.d.ts +96 -0
  22. package/build/dist/source/impl/Hooks.js +310 -0
  23. package/build/dist/source/impl/Journal.d.ts +34 -0
  24. package/build/dist/source/impl/Journal.js +149 -0
  25. package/build/dist/source/impl/Meta.d.ts +13 -0
  26. package/build/dist/source/impl/Meta.js +33 -0
  27. package/build/dist/source/impl/Monitor.d.ts +32 -0
  28. package/build/dist/source/impl/Monitor.js +97 -0
  29. package/build/dist/source/impl/Operation.d.ts +93 -0
  30. package/build/dist/source/impl/Operation.js +722 -0
  31. package/build/dist/source/impl/Transaction.d.ts +30 -0
  32. package/build/dist/source/impl/Transaction.js +313 -0
  33. package/build/dist/source/util/Dbg.d.ts +15 -0
  34. package/build/dist/source/util/Dbg.js +96 -0
  35. package/build/dist/source/util/Sealant.d.ts +14 -0
  36. package/build/dist/source/util/Sealant.js +30 -0
  37. package/build/dist/source/util/SealedArray.d.ts +16 -0
  38. package/build/dist/source/util/SealedArray.js +28 -0
  39. package/build/dist/source/util/SealedMap.d.ts +13 -0
  40. package/build/dist/source/util/SealedMap.js +21 -0
  41. package/build/dist/source/util/SealedSet.d.ts +13 -0
  42. package/build/dist/source/util/SealedSet.js +21 -0
  43. package/build/dist/source/util/Utils.d.ts +9 -0
  44. package/build/dist/source/util/Utils.js +62 -0
  45. package/package.json +1 -1
@@ -0,0 +1,310 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.Hooks = exports.OptionsImpl = exports.ReactiveMap = exports.ReactiveArray = exports.ReactiveObject = void 0;
4
+ const Utils_1 = require("../util/Utils");
5
+ const Sealant_1 = require("../util/Sealant");
6
+ const Dbg_1 = require("../util/Dbg");
7
+ const Options_1 = require("../Options");
8
+ const Data_1 = require("./Data");
9
+ const Changeset_1 = require("./Changeset");
10
+ class ReactiveObject {
11
+ constructor() {
12
+ const proto = new.target.prototype;
13
+ const initial = Data_1.Meta.getFrom(proto, Data_1.Meta.Initial);
14
+ const h = Hooks.createHandleForReactiveObject(proto, this, initial, new.target.name);
15
+ return h.proxy;
16
+ }
17
+ [Symbol.toStringTag]() {
18
+ const h = Data_1.Meta.get(this, Data_1.Meta.Handle);
19
+ return Changeset_1.Dump.obj(h);
20
+ }
21
+ }
22
+ exports.ReactiveObject = ReactiveObject;
23
+ class ReactiveArray extends ReactiveObject {
24
+ constructor() {
25
+ super(...arguments);
26
+ this.a = new Array();
27
+ }
28
+ get length() { return this.a.length; }
29
+ set length(n) { this.a.length = n; }
30
+ get(n) { return this.a[n]; }
31
+ set(n, item) { this.mutable[n] = item; }
32
+ toString() { return this.a.toString(); }
33
+ toLocaleString() { return this.a.toLocaleString(); }
34
+ pop() { return this.mutable.pop(); }
35
+ push(...items) { return this.mutable.push(...items); }
36
+ concat(...items) { return this.a.concat(...items); }
37
+ join(separator) { return this.a.join(separator); }
38
+ reverse() { return this.mutable.reverse(); }
39
+ shift() { return this.mutable.shift(); }
40
+ slice(start, end) { return this.a.slice(start, end); }
41
+ sort(compareFn) { this.mutable.sort(compareFn); return this; }
42
+ splice(start, deleteCount, ...items) { return this.mutable.splice(start, deleteCount, ...items); }
43
+ unshift(...items) { return this.mutable.unshift(...items); }
44
+ indexOf(searchElement, fromIndex) { return this.a.indexOf(searchElement, fromIndex); }
45
+ lastIndexOf(searchElement, fromIndex) { return this.a.lastIndexOf(searchElement, fromIndex); }
46
+ every(predicate, thisArg) { return this.a.every(predicate, thisArg); }
47
+ some(predicate, thisArg) { return this.a.some(predicate, thisArg); }
48
+ forEach(callbackfn, thisArg) { return this.a.forEach(callbackfn, thisArg); }
49
+ map(callbackfn, thisArg) { return this.a.map(callbackfn, thisArg); }
50
+ filter(predicate, thisArg) { return this.a.filter(predicate, thisArg); }
51
+ reduce(callbackfn, initialValue) { return this.a.reduce(callbackfn, initialValue); }
52
+ reduceRight(callbackfn, initialValue) { return this.a.reduceRight(callbackfn, initialValue); }
53
+ entries() { return this.a.entries(); }
54
+ keys() { return this.a.keys(); }
55
+ values() { return this.a.values(); }
56
+ get mutable() {
57
+ const createCopy = this.a[Sealant_1.Sealant.CreateCopy];
58
+ if (createCopy)
59
+ return this.a = createCopy.call(this.a);
60
+ return this.a;
61
+ }
62
+ }
63
+ exports.ReactiveArray = ReactiveArray;
64
+ class ReactiveMap extends ReactiveObject {
65
+ constructor() {
66
+ super(...arguments);
67
+ this.m = new Map();
68
+ }
69
+ clear() { this.mutable.clear(); }
70
+ delete(key) { return this.mutable.delete(key); }
71
+ forEach(callbackfn, thisArg) { this.m.forEach(callbackfn, thisArg); }
72
+ get(key) { return this.m.get(key); }
73
+ has(key) { return this.m.has(key); }
74
+ set(key, value) { this.mutable.set(key, value); return this; }
75
+ get size() { return this.m.size; }
76
+ entries() { return this.m.entries(); }
77
+ keys() { return this.m.keys(); }
78
+ values() { return this.m.values(); }
79
+ get mutable() {
80
+ const createCopy = this.m[Sealant_1.Sealant.CreateCopy];
81
+ if (createCopy)
82
+ return this.m = createCopy.call(this.m);
83
+ return this.m;
84
+ }
85
+ }
86
+ exports.ReactiveMap = ReactiveMap;
87
+ const DEFAULT_OPTIONS = Object.freeze({
88
+ kind: Options_1.Kind.Plain,
89
+ standalone: false,
90
+ order: 0,
91
+ noSideEffects: false,
92
+ triggeringArgs: false,
93
+ throttling: Number.MAX_SAFE_INTEGER,
94
+ reentrance: Options_1.Reentrance.PreventWithError,
95
+ journal: undefined,
96
+ monitor: null,
97
+ logging: undefined,
98
+ });
99
+ class OptionsImpl {
100
+ constructor(getter, setter, existing, patch, implicit) {
101
+ this.getter = getter !== undefined ? getter : existing.getter;
102
+ this.setter = setter !== undefined ? setter : existing.setter;
103
+ this.kind = merge(DEFAULT_OPTIONS.kind, existing.kind, patch.kind, implicit);
104
+ this.standalone = merge(DEFAULT_OPTIONS.standalone, existing.standalone, patch.standalone, implicit);
105
+ this.order = merge(DEFAULT_OPTIONS.order, existing.order, patch.order, implicit);
106
+ this.noSideEffects = merge(DEFAULT_OPTIONS.noSideEffects, existing.noSideEffects, patch.noSideEffects, implicit);
107
+ this.triggeringArgs = merge(DEFAULT_OPTIONS.triggeringArgs, existing.triggeringArgs, patch.triggeringArgs, implicit);
108
+ this.throttling = merge(DEFAULT_OPTIONS.throttling, existing.throttling, patch.throttling, implicit);
109
+ this.reentrance = merge(DEFAULT_OPTIONS.reentrance, existing.reentrance, patch.reentrance, implicit);
110
+ this.journal = merge(DEFAULT_OPTIONS.journal, existing.journal, patch.journal, implicit);
111
+ this.monitor = merge(DEFAULT_OPTIONS.monitor, existing.monitor, patch.monitor, implicit);
112
+ this.logging = merge(DEFAULT_OPTIONS.logging, existing.logging, patch.logging, implicit);
113
+ if (Dbg_1.Log.isOn)
114
+ Object.freeze(this);
115
+ }
116
+ }
117
+ exports.OptionsImpl = OptionsImpl;
118
+ OptionsImpl.INITIAL = Object.freeze(new OptionsImpl(Utils_1.UNDEF, Utils_1.UNDEF, Object.assign({ getter: Utils_1.UNDEF, setter: Utils_1.UNDEF }, DEFAULT_OPTIONS), {}, false));
119
+ function merge(def, existing, patch, implicit) {
120
+ return patch !== undefined && (existing === def || !implicit) ? patch : existing;
121
+ }
122
+ class Hooks {
123
+ getPrototypeOf(h) {
124
+ return Reflect.getPrototypeOf(h.data);
125
+ }
126
+ get(h, m, receiver) {
127
+ let result;
128
+ if (m !== Data_1.Meta.Handle) {
129
+ const cs = Changeset_1.Changeset.current();
130
+ const os = cs.getRelevantSnapshot(h, m);
131
+ result = os.data[m];
132
+ if (result instanceof Data_1.Subscription && !result.isOperation) {
133
+ Changeset_1.Changeset.markUsed(result, os, m, h, Options_1.Kind.Plain, false);
134
+ result = result.content;
135
+ }
136
+ else
137
+ result = Reflect.get(h.data, m, receiver);
138
+ }
139
+ else
140
+ result = h;
141
+ return result;
142
+ }
143
+ set(h, m, value, receiver) {
144
+ const os = Changeset_1.Changeset.edit().getEditableSnapshot(h, m, value);
145
+ if (os !== Changeset_1.EMPTY_SNAPSHOT) {
146
+ let curr = os.data[m];
147
+ if (curr !== undefined || (os.former.snapshot.changeset === Changeset_1.EMPTY_SNAPSHOT.changeset && (m in h.data) === false)) {
148
+ if (curr === undefined || curr.content !== value || Hooks.sensitivity) {
149
+ const existing = curr === null || curr === void 0 ? void 0 : curr.content;
150
+ if (os.former.snapshot.data[m] === curr) {
151
+ curr = os.data[m] = new Data_1.Subscription(value);
152
+ Changeset_1.Changeset.markEdited(existing, value, true, os, m, h);
153
+ }
154
+ else {
155
+ curr.content = value;
156
+ Changeset_1.Changeset.markEdited(existing, value, true, os, m, h);
157
+ }
158
+ }
159
+ }
160
+ else
161
+ Reflect.set(h.data, m, value, receiver);
162
+ }
163
+ else
164
+ h.data[m] = value;
165
+ return true;
166
+ }
167
+ has(h, m) {
168
+ const os = Changeset_1.Changeset.current().getRelevantSnapshot(h, m);
169
+ return m in os.data || m in h.data;
170
+ }
171
+ getOwnPropertyDescriptor(h, m) {
172
+ const os = Changeset_1.Changeset.current().getRelevantSnapshot(h, m);
173
+ const pd = Reflect.getOwnPropertyDescriptor(os.data, m);
174
+ if (pd)
175
+ pd.configurable = pd.writable = true;
176
+ return pd;
177
+ }
178
+ ownKeys(h) {
179
+ const os = Changeset_1.Changeset.current().getRelevantSnapshot(h, Data_1.Meta.Handle);
180
+ const result = [];
181
+ for (const m of Object.getOwnPropertyNames(os.data)) {
182
+ const value = os.data[m];
183
+ if (!(value instanceof Data_1.Subscription) || !value.isOperation)
184
+ result.push(m);
185
+ }
186
+ return result;
187
+ }
188
+ static decorateData(reactive, proto, m) {
189
+ if (reactive) {
190
+ const get = function () {
191
+ const h = Hooks.acquireHandle(this);
192
+ return Hooks.handler.get(h, m, this);
193
+ };
194
+ const set = function (value) {
195
+ const h = Hooks.acquireHandle(this);
196
+ return Hooks.handler.set(h, m, value, this);
197
+ };
198
+ const enumerable = true;
199
+ const configurable = false;
200
+ return Object.defineProperty(proto, m, { get, set, enumerable, configurable });
201
+ }
202
+ else
203
+ Data_1.Meta.acquire(proto, Data_1.Meta.Initial)[m] = Data_1.Meta.Nonreactive;
204
+ }
205
+ static decorateOperation(implicit, decorator, options, proto, member, pd) {
206
+ var _a, _b, _c, _d;
207
+ if (pd === undefined || pd === proto)
208
+ pd = EMPTY_PROP_DESCRIPTOR;
209
+ const enumerable = (_a = pd.enumerable) !== null && _a !== void 0 ? _a : true;
210
+ const configurable = (_b = pd.configurable) !== null && _b !== void 0 ? _b : true;
211
+ const opts = Hooks.rememberOperationOptions(proto, member, (_c = pd.value) !== null && _c !== void 0 ? _c : pd.get, (_d = pd.value) !== null && _d !== void 0 ? _d : pd.set, true, configurable, options, implicit);
212
+ if (opts.getter === opts.setter) {
213
+ const bootstrap = function () {
214
+ const h = Hooks.acquireHandle(this);
215
+ const operation = Hooks.createOperation(h, member, opts);
216
+ Object.defineProperty(h.data, member, { value: operation, enumerable, configurable });
217
+ return operation;
218
+ };
219
+ return Object.defineProperty(proto, member, { get: bootstrap, enumerable, configurable: true });
220
+ }
221
+ else if (opts.setter === Utils_1.UNDEF) {
222
+ const bootstrap = function () {
223
+ const h = Hooks.acquireHandle(this);
224
+ const operation = Hooks.createOperation(h, member, opts);
225
+ Object.defineProperty(h.data, member, { get: operation, enumerable, configurable });
226
+ return operation.call(this);
227
+ };
228
+ return Object.defineProperty(proto, member, { get: bootstrap, enumerable, configurable: true });
229
+ }
230
+ else
231
+ throw (0, Dbg_1.misuse)(`${proto.constructor.name}.${member.toString()} has setter and cannot be decorated with @${decorator.name}`);
232
+ }
233
+ static decorateOperationParametrized(decorator, options) {
234
+ return function (proto, prop, pd) {
235
+ return Hooks.decorateOperation(false, decorator, options, proto, prop, pd);
236
+ };
237
+ }
238
+ static acquireHandle(obj) {
239
+ let h = obj[Data_1.Meta.Handle];
240
+ if (!h) {
241
+ if (obj !== Object(obj) || Array.isArray(obj))
242
+ throw (0, Dbg_1.misuse)('only objects can be reactive');
243
+ const initial = Data_1.Meta.getFrom(Object.getPrototypeOf(obj), Data_1.Meta.Initial);
244
+ const os = new Data_1.ObjectSnapshot(Changeset_1.EMPTY_SNAPSHOT.changeset, Changeset_1.EMPTY_SNAPSHOT, Object.assign({}, initial));
245
+ h = new Data_1.ObjectHandle(obj, obj, Hooks.handler, os, obj.constructor.name);
246
+ Data_1.Meta.set(os.data, Data_1.Meta.Handle, h);
247
+ Data_1.Meta.set(obj, Data_1.Meta.Handle, h);
248
+ Data_1.Meta.set(os.data, Data_1.Meta.Revision, new Data_1.Subscription(1));
249
+ }
250
+ return h;
251
+ }
252
+ static createHandleForReactiveObject(proto, data, blank, hint) {
253
+ const ctx = Changeset_1.Changeset.edit();
254
+ const h = new Data_1.ObjectHandle(data, undefined, Hooks.handler, Changeset_1.EMPTY_SNAPSHOT, hint);
255
+ ctx.getEditableSnapshot(h, Data_1.Meta.Handle, blank);
256
+ if (!Hooks.reactionsAutoStartDisabled)
257
+ for (const m in Data_1.Meta.getFrom(proto, Data_1.Meta.Reactions))
258
+ h.proxy[m][Data_1.Meta.Controller].markObsolete();
259
+ return h;
260
+ }
261
+ static setProfilingMode(isOn, options) {
262
+ if (isOn) {
263
+ Hooks.repetitiveUsageWarningThreshold = options && options.repetitiveUsageWarningThreshold !== undefined ? options.repetitiveUsageWarningThreshold : 10;
264
+ Hooks.mainThreadBlockingWarningThreshold = options && options.mainThreadBlockingWarningThreshold !== undefined ? options.mainThreadBlockingWarningThreshold : 14;
265
+ Hooks.asyncActionDurationWarningThreshold = options && options.asyncActionDurationWarningThreshold !== undefined ? options.asyncActionDurationWarningThreshold : 300;
266
+ Changeset_1.Changeset.garbageCollectionSummaryInterval = options && options.garbageCollectionSummaryInterval !== undefined ? options.garbageCollectionSummaryInterval : 100;
267
+ }
268
+ else {
269
+ Hooks.repetitiveUsageWarningThreshold = Number.MAX_SAFE_INTEGER;
270
+ Hooks.mainThreadBlockingWarningThreshold = Number.MAX_SAFE_INTEGER;
271
+ Hooks.asyncActionDurationWarningThreshold = Number.MAX_SAFE_INTEGER;
272
+ Changeset_1.Changeset.garbageCollectionSummaryInterval = Number.MAX_SAFE_INTEGER;
273
+ }
274
+ }
275
+ static sensitive(sensitivity, func, ...args) {
276
+ const restore = Hooks.sensitivity;
277
+ Hooks.sensitivity = sensitivity;
278
+ try {
279
+ return func(...args);
280
+ }
281
+ finally {
282
+ Hooks.sensitivity = restore;
283
+ }
284
+ }
285
+ static setHint(obj, hint) {
286
+ if (hint) {
287
+ const h = Hooks.acquireHandle(obj);
288
+ h.hint = hint;
289
+ }
290
+ return obj;
291
+ }
292
+ }
293
+ exports.Hooks = Hooks;
294
+ Hooks.reactionsAutoStartDisabled = false;
295
+ Hooks.repetitiveUsageWarningThreshold = Number.MAX_SAFE_INTEGER;
296
+ Hooks.mainThreadBlockingWarningThreshold = Number.MAX_SAFE_INTEGER;
297
+ Hooks.asyncActionDurationWarningThreshold = Number.MAX_SAFE_INTEGER;
298
+ Hooks.sensitivity = false;
299
+ Hooks.handler = new Hooks();
300
+ Hooks.createOperation = function (h, m, options) {
301
+ throw (0, Dbg_1.misuse)('createOperation should never be called');
302
+ };
303
+ Hooks.rememberOperationOptions = function (proto, m, getter, setter, enumerable, configurable, options, implicit) {
304
+ throw (0, Dbg_1.misuse)('rememberOperationOptions should never be called');
305
+ };
306
+ const EMPTY_PROP_DESCRIPTOR = {
307
+ configurable: true,
308
+ enumerable: true,
309
+ value: undefined,
310
+ };
@@ -0,0 +1,34 @@
1
+ import { ReactiveObject } from './Hooks';
2
+ import { ObjectHandle, ObjectSnapshot, PatchSet } from './Data';
3
+ export declare type Saver = (patch: PatchSet) => Promise<void>;
4
+ export declare abstract class Journal extends ReactiveObject {
5
+ abstract capacity: number;
6
+ abstract readonly edits: ReadonlyArray<PatchSet>;
7
+ abstract readonly unsaved: PatchSet;
8
+ abstract readonly canUndo: boolean;
9
+ abstract readonly canRedo: boolean;
10
+ abstract edited(patch: PatchSet): void;
11
+ abstract saved(patch: PatchSet): void;
12
+ abstract undo(count?: number): void;
13
+ abstract redo(count?: number): void;
14
+ static create(): Journal;
15
+ }
16
+ export declare class JournalImpl extends Journal {
17
+ private _capacity;
18
+ private _edits;
19
+ private _unsaved;
20
+ private _position;
21
+ get capacity(): number;
22
+ set capacity(value: number);
23
+ get edits(): ReadonlyArray<PatchSet>;
24
+ get unsaved(): PatchSet;
25
+ get canUndo(): boolean;
26
+ get canRedo(): boolean;
27
+ edited(p: PatchSet): void;
28
+ saved(patch: PatchSet): void;
29
+ undo(count?: number): void;
30
+ redo(count?: number): void;
31
+ static buildPatch(hint: string, items: Map<ObjectHandle, ObjectSnapshot>): PatchSet;
32
+ static applyPatch(patch: PatchSet, undoing: boolean): void;
33
+ mergePatchToUnsaved(patch: PatchSet, undoing: boolean): void;
34
+ }
@@ -0,0 +1,149 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.JournalImpl = exports.Journal = void 0;
4
+ const Hooks_1 = require("./Hooks");
5
+ const Data_1 = require("./Data");
6
+ const Changeset_1 = require("./Changeset");
7
+ const Transaction_1 = require("./Transaction");
8
+ const Sealant_1 = require("../util/Sealant");
9
+ class Journal extends Hooks_1.ReactiveObject {
10
+ static create() { return new JournalImpl(); }
11
+ }
12
+ exports.Journal = Journal;
13
+ class JournalImpl extends Journal {
14
+ constructor() {
15
+ super(...arguments);
16
+ this._capacity = 5;
17
+ this._edits = [];
18
+ this._unsaved = new Map();
19
+ this._position = 0;
20
+ }
21
+ get capacity() { return this._capacity; }
22
+ set capacity(value) { this._capacity = value; if (value < this._edits.length)
23
+ this._edits.splice(0, this._edits.length - value); }
24
+ get edits() { return this._edits; }
25
+ get unsaved() { return this._unsaved; }
26
+ get canUndo() { return this._edits.length > 0 && this._position > 0; }
27
+ get canRedo() { return this._position < this._edits.length; }
28
+ edited(p) {
29
+ Transaction_1.Transaction.run({ hint: 'EditJournal.edited', standalone: 'isolated' }, () => {
30
+ const items = this._edits = this._edits.toMutable();
31
+ if (items.length >= this._capacity)
32
+ items.shift();
33
+ else
34
+ items.splice(this._position);
35
+ this.mergePatchToUnsaved(p, false);
36
+ items.push(p);
37
+ this._position = items.length;
38
+ });
39
+ }
40
+ saved(patch) {
41
+ if (this._unsaved === patch)
42
+ this._unsaved = new Map();
43
+ else
44
+ throw new Error('not implemented');
45
+ }
46
+ undo(count = 1) {
47
+ Transaction_1.Transaction.run({ hint: 'Journal.undo', standalone: 'isolated' }, () => {
48
+ let i = this._position - 1;
49
+ while (i >= 0 && count > 0) {
50
+ const patch = this._edits[i];
51
+ JournalImpl.applyPatch(patch, true);
52
+ this.mergePatchToUnsaved(patch, true);
53
+ i--, count--;
54
+ }
55
+ this._position = i + 1;
56
+ });
57
+ }
58
+ redo(count = 1) {
59
+ Transaction_1.Transaction.run({ hint: 'Journal.redo', standalone: 'isolated' }, () => {
60
+ let i = this._position;
61
+ while (i < this._edits.length && count > 0) {
62
+ const patch = this._edits[i];
63
+ JournalImpl.applyPatch(patch, false);
64
+ this.mergePatchToUnsaved(patch, false);
65
+ i++, count--;
66
+ }
67
+ this._position = i;
68
+ });
69
+ }
70
+ static buildPatch(hint, items) {
71
+ const patch = new Map();
72
+ items.forEach((os, h) => {
73
+ const op = new Map();
74
+ const former = os.former.snapshot !== Changeset_1.EMPTY_SNAPSHOT ? os.former.snapshot.data : undefined;
75
+ os.changes.forEach(m => {
76
+ const vp = {
77
+ memberName: m, patchKind: 'update',
78
+ freshValue: unseal(os.data[m]), formerValue: undefined,
79
+ };
80
+ if (former)
81
+ vp.formerValue = unseal(former[m]);
82
+ op.set(m, vp);
83
+ });
84
+ if (!former) {
85
+ const vp = {
86
+ memberName: Data_1.Meta.Revision, patchKind: 'remove',
87
+ freshValue: Data_1.Meta.Undefined, formerValue: undefined,
88
+ };
89
+ op.set(Data_1.Meta.Revision, vp);
90
+ }
91
+ patch.set(h.proxy, op);
92
+ });
93
+ return patch;
94
+ }
95
+ static applyPatch(patch, undoing) {
96
+ const ctx = Changeset_1.Changeset.edit();
97
+ patch.forEach((op, obj) => {
98
+ const h = Data_1.Meta.get(obj, Data_1.Meta.Handle);
99
+ const rev = op.get(Data_1.Meta.Revision);
100
+ const disposed = rev && (undoing ? rev.formerValue : rev.freshValue) === Data_1.Meta.Undefined;
101
+ if (!disposed) {
102
+ op.forEach((vp, m) => {
103
+ const value = undoing ? vp.formerValue : vp.freshValue;
104
+ const os = ctx.getEditableSnapshot(h, m, value);
105
+ if (os.changeset === ctx) {
106
+ os.data[m] = new Data_1.Subscription(value);
107
+ const existing = os.former.snapshot.data[m];
108
+ Changeset_1.Changeset.markEdited(existing, value, existing !== value, os, m, h);
109
+ }
110
+ });
111
+ }
112
+ else
113
+ Changeset_1.Changeset.doDispose(ctx, h);
114
+ });
115
+ }
116
+ mergePatchToUnsaved(patch, undoing) {
117
+ const unsaved = this._unsaved = this._unsaved.toMutable();
118
+ patch.forEach((op, obj) => {
119
+ let result = unsaved.get(obj);
120
+ if (!result)
121
+ unsaved.set(obj, result = new Map());
122
+ op.forEach((vp, m) => {
123
+ let merged = result.get(m);
124
+ if (!merged)
125
+ result.set(m, merged = {
126
+ memberName: m, patchKind: 'update',
127
+ freshValue: undefined, formerValue: undefined,
128
+ });
129
+ const value = undoing ? vp.formerValue : vp.freshValue;
130
+ const former = undoing ? vp.freshValue : vp.formerValue;
131
+ if (value !== merged.formerValue) {
132
+ merged.freshValue = value;
133
+ merged.formerValue = former;
134
+ }
135
+ else {
136
+ result.delete(m);
137
+ if (result.size === 0)
138
+ unsaved.delete(obj);
139
+ }
140
+ });
141
+ });
142
+ }
143
+ }
144
+ exports.JournalImpl = JournalImpl;
145
+ function unseal(subscription) {
146
+ const result = subscription.content;
147
+ const createCopy = result === null || result === void 0 ? void 0 : result[Sealant_1.Sealant.CreateCopy];
148
+ return createCopy !== undefined ? createCopy.call(result) : result;
149
+ }
@@ -0,0 +1,13 @@
1
+ export declare abstract class Meta {
2
+ static readonly Handle: unique symbol;
3
+ static readonly Revision: unique symbol;
4
+ static readonly Controller: unique symbol;
5
+ static readonly Initial: unique symbol;
6
+ static readonly Reactions: unique symbol;
7
+ static readonly Nonreactive: unique symbol;
8
+ static readonly Undefined: unique symbol;
9
+ static get<T>(obj: any, sym: symbol): T;
10
+ static set(obj: any, sym: symbol, value: any): any;
11
+ static acquire(proto: any, sym: symbol): any;
12
+ static getFrom<T = any>(proto: any, sym: symbol): T;
13
+ }
@@ -0,0 +1,33 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.Meta = void 0;
4
+ const EMPTY_META = Object.freeze({});
5
+ class Meta {
6
+ static get(obj, sym) {
7
+ return obj[sym];
8
+ }
9
+ static set(obj, sym, value) {
10
+ Object.defineProperty(obj, sym, { value, configurable: false, enumerable: false });
11
+ return obj;
12
+ }
13
+ static acquire(proto, sym) {
14
+ let meta = proto[sym];
15
+ if (!proto.hasOwnProperty(sym)) {
16
+ meta = Object.assign({}, meta);
17
+ Meta.set(proto, sym, meta);
18
+ }
19
+ return meta;
20
+ }
21
+ static getFrom(proto, sym) {
22
+ var _a;
23
+ return (_a = proto[sym]) !== null && _a !== void 0 ? _a : EMPTY_META;
24
+ }
25
+ }
26
+ exports.Meta = Meta;
27
+ Meta.Handle = Symbol('rx-handle');
28
+ Meta.Revision = Symbol('rx-revision');
29
+ Meta.Controller = Symbol('rx-controller');
30
+ Meta.Initial = Symbol('rx-initial');
31
+ Meta.Reactions = Symbol('rx-reactions');
32
+ Meta.Nonreactive = Symbol('rx-nonreactive');
33
+ Meta.Undefined = Symbol('rx-undefined');
@@ -0,0 +1,32 @@
1
+ import { Worker } from '../Worker';
2
+ import { ReactiveObject } from './Hooks';
3
+ export declare abstract class Monitor extends ReactiveObject {
4
+ abstract readonly isActive: boolean;
5
+ abstract readonly counter: number;
6
+ abstract readonly workers: ReadonlySet<Worker>;
7
+ abstract readonly duration: number;
8
+ static create(hint: string, activationDelay: number, deactivationDelay: number, durationResolution: number): Monitor;
9
+ }
10
+ export declare class MonitorImpl extends Monitor {
11
+ isActive: boolean;
12
+ counter: number;
13
+ workers: Set<Worker>;
14
+ duration: number;
15
+ internals: {
16
+ started: number;
17
+ activationDelay: number;
18
+ activationTimeout: undefined;
19
+ deactivationDelay: number;
20
+ deactivationTimeout: undefined;
21
+ durationResolution: number;
22
+ };
23
+ enter(worker: Worker): void;
24
+ leave(worker: Worker): void;
25
+ static create(hint: string, activationDelay: number, deactivationDelay: number, durationResolution: number): MonitorImpl;
26
+ static enter(mon: MonitorImpl, worker: Worker): void;
27
+ static leave(mon: MonitorImpl, worker: Worker): void;
28
+ private static doCreate;
29
+ private static activate;
30
+ private static deactivate;
31
+ private static tick;
32
+ }
@@ -0,0 +1,97 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.MonitorImpl = exports.Monitor = void 0;
4
+ const Hooks_1 = require("./Hooks");
5
+ const Transaction_1 = require("./Transaction");
6
+ class Monitor extends Hooks_1.ReactiveObject {
7
+ static create(hint, activationDelay, deactivationDelay, durationResolution) {
8
+ return MonitorImpl.create(hint, activationDelay, deactivationDelay, durationResolution);
9
+ }
10
+ }
11
+ exports.Monitor = Monitor;
12
+ class MonitorImpl extends Monitor {
13
+ constructor() {
14
+ super(...arguments);
15
+ this.isActive = false;
16
+ this.counter = 0;
17
+ this.workers = new Set();
18
+ this.duration = 0;
19
+ this.internals = {
20
+ started: 0,
21
+ activationDelay: -1,
22
+ activationTimeout: undefined,
23
+ deactivationDelay: -1,
24
+ deactivationTimeout: undefined,
25
+ durationResolution: 1,
26
+ };
27
+ }
28
+ enter(worker) {
29
+ this.counter++;
30
+ const workers = this.workers = this.workers.toMutable();
31
+ workers.add(worker);
32
+ MonitorImpl.activate(this, this.internals.activationDelay);
33
+ }
34
+ leave(worker) {
35
+ this.counter--;
36
+ const workers = this.workers = this.workers.toMutable();
37
+ workers.delete(worker);
38
+ MonitorImpl.deactivate(this, this.internals.deactivationDelay);
39
+ }
40
+ static create(hint, activationDelay, deactivationDelay, durationResolution) {
41
+ return Transaction_1.Transaction.run({ hint: 'Monitor.create' }, MonitorImpl.doCreate, hint, activationDelay, deactivationDelay, durationResolution);
42
+ }
43
+ static enter(mon, worker) {
44
+ mon.enter(worker);
45
+ }
46
+ static leave(mon, worker) {
47
+ mon.leave(worker);
48
+ }
49
+ static doCreate(hint, activationDelay, deactivationDelay, durationResolution) {
50
+ const m = new MonitorImpl();
51
+ Hooks_1.Hooks.setHint(m, hint);
52
+ m.internals.activationDelay = activationDelay;
53
+ m.internals.deactivationDelay = deactivationDelay;
54
+ m.internals.durationResolution = durationResolution;
55
+ return m;
56
+ }
57
+ static activate(mon, delay) {
58
+ if (mon.internals.started === 0) {
59
+ mon.duration = 0;
60
+ mon.internals.started = performance.now();
61
+ MonitorImpl.tick(mon);
62
+ }
63
+ if (delay >= 0) {
64
+ if (mon.internals.activationTimeout === undefined)
65
+ mon.internals.activationTimeout = setTimeout(() => Transaction_1.Transaction.run({ hint: 'Monitor.activate', standalone: 'isolated' }, MonitorImpl.activate, mon, -1), delay);
66
+ }
67
+ else if (mon.counter > 0)
68
+ mon.isActive = true;
69
+ }
70
+ static deactivate(mon, delay) {
71
+ if (delay >= 0) {
72
+ clearTimeout(mon.internals.deactivationTimeout);
73
+ mon.internals.deactivationTimeout = setTimeout(() => Transaction_1.Transaction.run({ hint: 'Monitor.deactivate', standalone: 'isolated' }, MonitorImpl.deactivate, mon, -1), delay);
74
+ }
75
+ else if (mon.counter <= 0) {
76
+ mon.isActive = false;
77
+ mon.internals.activationTimeout = undefined;
78
+ }
79
+ if (mon.counter === 0 && mon.internals.started !== 0) {
80
+ const resolution = mon.internals.durationResolution;
81
+ mon.duration = Math.round(resolution * (performance.now() - mon.internals.started)) / resolution;
82
+ mon.internals.started = 0;
83
+ }
84
+ }
85
+ static tick(mon) {
86
+ if (mon.internals.started !== 0) {
87
+ Transaction_1.Transaction.run(null, () => {
88
+ const resolution = mon.internals.durationResolution;
89
+ mon.duration = Math.round(resolution * (performance.now() - mon.internals.started)) / resolution;
90
+ });
91
+ const t = globalThis !== null && globalThis !== void 0 ? globalThis : global;
92
+ if (t.requestAnimationFrame)
93
+ requestAnimationFrame(() => MonitorImpl.tick(mon));
94
+ }
95
+ }
96
+ }
97
+ exports.MonitorImpl = MonitorImpl;