@oimdb/core 1.4.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +396 -63
- package/dist/index.cjs +1706 -799
- package/dist/index.d.cts +456 -292
- package/dist/index.d.ts +456 -292
- package/dist/index.js +1694 -790
- package/package.json +4 -1
package/dist/index.js
CHANGED
|
@@ -15,6 +15,11 @@ var OIMEventEmitter = class {
|
|
|
15
15
|
constructor() {
|
|
16
16
|
this.buckets = {};
|
|
17
17
|
}
|
|
18
|
+
hasHandlers(event) {
|
|
19
|
+
const bucket = this.buckets[event];
|
|
20
|
+
if (!bucket) return false;
|
|
21
|
+
return bucket.indexByHandler.size > 0;
|
|
22
|
+
}
|
|
18
23
|
getOrCreateBucket(event) {
|
|
19
24
|
let bucket = this.buckets[event];
|
|
20
25
|
if (!bucket) {
|
|
@@ -145,58 +150,75 @@ var EOIMIndexEventType = /* @__PURE__ */ ((EOIMIndexEventType2) => {
|
|
|
145
150
|
var OIMIndexStoreMapDrivenSetBased = class extends OIMIndexStoreSetBased {
|
|
146
151
|
constructor() {
|
|
147
152
|
super(...arguments);
|
|
148
|
-
this.
|
|
153
|
+
this.slots = /* @__PURE__ */ new Map();
|
|
149
154
|
}
|
|
150
|
-
setOneByKey(key,
|
|
151
|
-
this.
|
|
155
|
+
setOneByKey(key, slots) {
|
|
156
|
+
this.slots.set(key, slots);
|
|
152
157
|
}
|
|
153
158
|
removeOneByKey(key) {
|
|
154
|
-
this.
|
|
159
|
+
this.slots.delete(key);
|
|
155
160
|
}
|
|
156
161
|
removeManyByKeys(keys) {
|
|
157
162
|
for (const key of keys) {
|
|
158
|
-
this.
|
|
163
|
+
this.slots.delete(key);
|
|
159
164
|
}
|
|
160
165
|
}
|
|
161
166
|
getOneByKey(key) {
|
|
162
|
-
return this.
|
|
167
|
+
return this.slots.get(key);
|
|
163
168
|
}
|
|
164
169
|
getManyByKeys(keys) {
|
|
165
170
|
const result = /* @__PURE__ */ new Map();
|
|
166
171
|
for (const key of keys) {
|
|
167
|
-
const
|
|
168
|
-
if (
|
|
169
|
-
result.set(key,
|
|
172
|
+
const slots = this.getOneByKey(key);
|
|
173
|
+
if (slots !== void 0) {
|
|
174
|
+
result.set(key, slots);
|
|
170
175
|
}
|
|
171
176
|
}
|
|
172
177
|
return result;
|
|
173
178
|
}
|
|
174
179
|
getAllKeys() {
|
|
175
|
-
return Array.from(this.
|
|
180
|
+
return Array.from(this.slots.keys());
|
|
176
181
|
}
|
|
177
182
|
getAll() {
|
|
178
|
-
return new Map(this.
|
|
183
|
+
return new Map(this.slots);
|
|
179
184
|
}
|
|
180
185
|
countAll() {
|
|
181
|
-
return this.
|
|
186
|
+
return this.slots.size;
|
|
182
187
|
}
|
|
183
188
|
clear() {
|
|
184
|
-
this.
|
|
189
|
+
this.slots.clear();
|
|
185
190
|
}
|
|
186
191
|
};
|
|
187
192
|
|
|
188
193
|
// src/abstract/OIMIndexSetBased.ts
|
|
189
194
|
var OIMIndexSetBased = class {
|
|
190
195
|
constructor(options = {}) {
|
|
196
|
+
this.fallbackSlots = /* @__PURE__ */ new Map();
|
|
191
197
|
this.emitter = new OIMEventEmitter();
|
|
192
198
|
this.comparePks = options.comparePks;
|
|
193
199
|
this.store = options.store ?? new OIMIndexStoreMapDrivenSetBased();
|
|
200
|
+
this.resolveSlot = options.resolveSlot;
|
|
194
201
|
}
|
|
195
202
|
/**
|
|
196
203
|
* Get primary keys for multiple index keys
|
|
197
204
|
*/
|
|
198
205
|
getPksByKeys(keys) {
|
|
199
|
-
|
|
206
|
+
const result = /* @__PURE__ */ new Map();
|
|
207
|
+
const slotsByKey = this.store.getManyByKeys(keys);
|
|
208
|
+
for (const [key, slots] of slotsByKey) {
|
|
209
|
+
result.set(key, this.slotsToPks(slots));
|
|
210
|
+
}
|
|
211
|
+
return result;
|
|
212
|
+
}
|
|
213
|
+
setSlotResolver(resolveSlot) {
|
|
214
|
+
this.resolveSlot = resolveSlot;
|
|
215
|
+
const allSlots = this.store.getAll();
|
|
216
|
+
for (const [key, slots] of allSlots) {
|
|
217
|
+
this.store.setOneByKey(
|
|
218
|
+
key,
|
|
219
|
+
this.resolveSlots(this.slotsToPks(slots))
|
|
220
|
+
);
|
|
221
|
+
}
|
|
200
222
|
}
|
|
201
223
|
/**
|
|
202
224
|
* @deprecated Use getPksByKey instead
|
|
@@ -209,8 +231,15 @@ var OIMIndexSetBased = class {
|
|
|
209
231
|
* Get primary keys for a specific index key
|
|
210
232
|
*/
|
|
211
233
|
getPksByKey(key) {
|
|
212
|
-
const
|
|
213
|
-
return
|
|
234
|
+
const slotsSet = this.store.getOneByKey(key);
|
|
235
|
+
return slotsSet ? this.slotsToPks(slotsSet) : /* @__PURE__ */ new Set();
|
|
236
|
+
}
|
|
237
|
+
getSlotsByKey(key) {
|
|
238
|
+
const slotsSet = this.store.getOneByKey(key);
|
|
239
|
+
return slotsSet ? slotsSet : /* @__PURE__ */ new Set();
|
|
240
|
+
}
|
|
241
|
+
getSlotsByKeys(keys) {
|
|
242
|
+
return this.store.getManyByKeys(keys);
|
|
214
243
|
}
|
|
215
244
|
/**
|
|
216
245
|
* Check if an index key exists
|
|
@@ -228,8 +257,8 @@ var OIMIndexSetBased = class {
|
|
|
228
257
|
* Get the number of primary keys for a specific index key
|
|
229
258
|
*/
|
|
230
259
|
getKeySize(key) {
|
|
231
|
-
const
|
|
232
|
-
return
|
|
260
|
+
const slotsSet = this.store.getOneByKey(key);
|
|
261
|
+
return slotsSet ? slotsSet.size : 0;
|
|
233
262
|
}
|
|
234
263
|
/**
|
|
235
264
|
* Get total number of index keys
|
|
@@ -251,10 +280,10 @@ var OIMIndexSetBased = class {
|
|
|
251
280
|
let maxBucketSize = 0;
|
|
252
281
|
let minBucketSize = Infinity;
|
|
253
282
|
const allPks = this.store.getAll();
|
|
254
|
-
for (const
|
|
255
|
-
totalPks +=
|
|
256
|
-
maxBucketSize = Math.max(maxBucketSize,
|
|
257
|
-
minBucketSize = Math.min(minBucketSize,
|
|
283
|
+
for (const slotsSet of allPks.values()) {
|
|
284
|
+
totalPks += slotsSet.size;
|
|
285
|
+
maxBucketSize = Math.max(maxBucketSize, slotsSet.size);
|
|
286
|
+
minBucketSize = Math.min(minBucketSize, slotsSet.size);
|
|
258
287
|
}
|
|
259
288
|
return {
|
|
260
289
|
totalKeys: allPks.size,
|
|
@@ -276,92 +305,147 @@ var OIMIndexSetBased = class {
|
|
|
276
305
|
* If comparator is provided and returns true (no changes), skip the update.
|
|
277
306
|
*/
|
|
278
307
|
setPksWithComparison(key, newPks) {
|
|
308
|
+
return this.setSlotsWithComparison(key, this.resolveSlots(newPks));
|
|
309
|
+
}
|
|
310
|
+
setSlotsWithComparison(key, newSlots) {
|
|
279
311
|
if (this.comparePks) {
|
|
280
|
-
const
|
|
281
|
-
if (
|
|
282
|
-
const existingPksArray =
|
|
283
|
-
|
|
312
|
+
const existingSlotsSet = this.store.getOneByKey(key);
|
|
313
|
+
if (existingSlotsSet && existingSlotsSet.size === newSlots.size) {
|
|
314
|
+
const existingPksArray = Array.from(
|
|
315
|
+
this.slotsToPks(existingSlotsSet)
|
|
316
|
+
);
|
|
317
|
+
const newPksArray = Array.from(this.slotsToPks(newSlots));
|
|
284
318
|
if (this.comparePks(existingPksArray, newPksArray)) {
|
|
285
319
|
return false;
|
|
286
320
|
}
|
|
287
|
-
} else if (!
|
|
321
|
+
} else if (!existingSlotsSet && newSlots.size === 0) {
|
|
288
322
|
return false;
|
|
289
323
|
}
|
|
290
324
|
}
|
|
291
|
-
this.store.setOneByKey(key,
|
|
325
|
+
this.store.setOneByKey(key, newSlots);
|
|
292
326
|
return true;
|
|
293
327
|
}
|
|
328
|
+
resolveSlots(pks) {
|
|
329
|
+
const slots = /* @__PURE__ */ new Set();
|
|
330
|
+
for (const pk of pks) slots.add(this.getOrCreateSlot(pk));
|
|
331
|
+
return slots;
|
|
332
|
+
}
|
|
333
|
+
getOrCreateSlot(pk) {
|
|
334
|
+
const resolved = this.resolveSlot?.(pk);
|
|
335
|
+
if (resolved) return resolved;
|
|
336
|
+
let fallback = this.fallbackSlots.get(pk);
|
|
337
|
+
if (!fallback) {
|
|
338
|
+
fallback = { pk, item: void 0 };
|
|
339
|
+
this.fallbackSlots.set(pk, fallback);
|
|
340
|
+
}
|
|
341
|
+
return fallback;
|
|
342
|
+
}
|
|
343
|
+
slotsToPks(slots) {
|
|
344
|
+
const pks = /* @__PURE__ */ new Set();
|
|
345
|
+
for (const slot of slots) pks.add(slot.pk);
|
|
346
|
+
return pks;
|
|
347
|
+
}
|
|
294
348
|
/**
|
|
295
349
|
* Emit update event with changed keys
|
|
296
350
|
*/
|
|
297
351
|
emitUpdate(keys) {
|
|
298
352
|
this.emitter.emit(0 /* UPDATE */, { keys });
|
|
299
353
|
}
|
|
354
|
+
/**
|
|
355
|
+
* Emit update event for a single key (fast-path override point).
|
|
356
|
+
*/
|
|
357
|
+
emitUpdateOne(key) {
|
|
358
|
+
this.emitUpdate([key]);
|
|
359
|
+
}
|
|
300
360
|
};
|
|
301
361
|
|
|
302
362
|
// src/core/OIMIndexStoreMapDrivenArrayBased.ts
|
|
303
363
|
var OIMIndexStoreMapDrivenArrayBased = class extends OIMIndexStoreArrayBased {
|
|
304
364
|
constructor() {
|
|
305
365
|
super(...arguments);
|
|
306
|
-
this.
|
|
366
|
+
this.slots = /* @__PURE__ */ new Map();
|
|
307
367
|
}
|
|
308
|
-
setOneByKey(key,
|
|
309
|
-
this.
|
|
368
|
+
setOneByKey(key, slots) {
|
|
369
|
+
this.slots.set(key, slots);
|
|
310
370
|
}
|
|
311
371
|
removeOneByKey(key) {
|
|
312
|
-
this.
|
|
372
|
+
this.slots.delete(key);
|
|
313
373
|
}
|
|
314
374
|
removeManyByKeys(keys) {
|
|
315
375
|
for (const key of keys) {
|
|
316
|
-
this.
|
|
376
|
+
this.slots.delete(key);
|
|
317
377
|
}
|
|
318
378
|
}
|
|
319
379
|
getOneByKey(key) {
|
|
320
|
-
return this.
|
|
380
|
+
return this.slots.get(key);
|
|
321
381
|
}
|
|
322
382
|
getManyByKeys(keys) {
|
|
323
383
|
const result = /* @__PURE__ */ new Map();
|
|
324
384
|
for (const key of keys) {
|
|
325
|
-
const
|
|
326
|
-
if (
|
|
327
|
-
result.set(key,
|
|
385
|
+
const slots = this.getOneByKey(key);
|
|
386
|
+
if (slots !== void 0) {
|
|
387
|
+
result.set(key, slots);
|
|
328
388
|
}
|
|
329
389
|
}
|
|
330
390
|
return result;
|
|
331
391
|
}
|
|
332
392
|
getAllKeys() {
|
|
333
|
-
return Array.from(this.
|
|
393
|
+
return Array.from(this.slots.keys());
|
|
334
394
|
}
|
|
335
395
|
getAll() {
|
|
336
|
-
return new Map(this.
|
|
396
|
+
return new Map(this.slots);
|
|
337
397
|
}
|
|
338
398
|
countAll() {
|
|
339
|
-
return this.
|
|
399
|
+
return this.slots.size;
|
|
340
400
|
}
|
|
341
401
|
clear() {
|
|
342
|
-
this.
|
|
402
|
+
this.slots.clear();
|
|
343
403
|
}
|
|
344
404
|
};
|
|
345
405
|
|
|
346
406
|
// src/abstract/OIMIndexArrayBased.ts
|
|
347
407
|
var OIMIndexArrayBased = class {
|
|
348
408
|
constructor(options = {}) {
|
|
409
|
+
this.fallbackSlots = /* @__PURE__ */ new Map();
|
|
349
410
|
this.emitter = new OIMEventEmitter();
|
|
350
411
|
this.comparePks = options.comparePks;
|
|
351
412
|
this.store = options.store ?? new OIMIndexStoreMapDrivenArrayBased();
|
|
413
|
+
this.resolveSlot = options.resolveSlot;
|
|
352
414
|
}
|
|
353
415
|
/**
|
|
354
416
|
* Get primary keys for multiple index keys
|
|
355
417
|
*/
|
|
356
418
|
getPksByKeys(keys) {
|
|
357
|
-
|
|
419
|
+
const result = /* @__PURE__ */ new Map();
|
|
420
|
+
const slotsByKey = this.store.getManyByKeys(keys);
|
|
421
|
+
for (const [key, slots] of slotsByKey) {
|
|
422
|
+
result.set(key, this.slotsToPks(slots));
|
|
423
|
+
}
|
|
424
|
+
return result;
|
|
425
|
+
}
|
|
426
|
+
setSlotResolver(resolveSlot) {
|
|
427
|
+
this.resolveSlot = resolveSlot;
|
|
428
|
+
const allSlots = this.store.getAll();
|
|
429
|
+
for (const [key, slots] of allSlots) {
|
|
430
|
+
this.store.setOneByKey(
|
|
431
|
+
key,
|
|
432
|
+
slots.map((slot) => this.getOrCreateSlot(slot.pk))
|
|
433
|
+
);
|
|
434
|
+
}
|
|
358
435
|
}
|
|
359
436
|
/**
|
|
360
437
|
* Get primary keys for a specific index key
|
|
361
438
|
*/
|
|
362
439
|
getPksByKey(key) {
|
|
363
|
-
const
|
|
364
|
-
return
|
|
440
|
+
const slotsArray = this.store.getOneByKey(key);
|
|
441
|
+
return slotsArray ? this.slotsToPks(slotsArray) : [];
|
|
442
|
+
}
|
|
443
|
+
getSlotsByKey(key) {
|
|
444
|
+
const slotsArray = this.store.getOneByKey(key);
|
|
445
|
+
return slotsArray ? slotsArray : [];
|
|
446
|
+
}
|
|
447
|
+
getSlotsByKeys(keys) {
|
|
448
|
+
return this.store.getManyByKeys(keys);
|
|
365
449
|
}
|
|
366
450
|
/**
|
|
367
451
|
* Check if an index key exists
|
|
@@ -379,8 +463,8 @@ var OIMIndexArrayBased = class {
|
|
|
379
463
|
* Get the number of primary keys for a specific index key
|
|
380
464
|
*/
|
|
381
465
|
getKeySize(key) {
|
|
382
|
-
const
|
|
383
|
-
return
|
|
466
|
+
const slotsArray = this.store.getOneByKey(key);
|
|
467
|
+
return slotsArray ? slotsArray.length : 0;
|
|
384
468
|
}
|
|
385
469
|
/**
|
|
386
470
|
* Get total number of index keys
|
|
@@ -402,10 +486,10 @@ var OIMIndexArrayBased = class {
|
|
|
402
486
|
let maxBucketSize = 0;
|
|
403
487
|
let minBucketSize = Infinity;
|
|
404
488
|
const allPks = this.store.getAll();
|
|
405
|
-
for (const
|
|
406
|
-
totalPks +=
|
|
407
|
-
maxBucketSize = Math.max(maxBucketSize,
|
|
408
|
-
minBucketSize = Math.min(minBucketSize,
|
|
489
|
+
for (const slotsArray of allPks.values()) {
|
|
490
|
+
totalPks += slotsArray.length;
|
|
491
|
+
maxBucketSize = Math.max(maxBucketSize, slotsArray.length);
|
|
492
|
+
minBucketSize = Math.min(minBucketSize, slotsArray.length);
|
|
409
493
|
}
|
|
410
494
|
return {
|
|
411
495
|
totalKeys: allPks.size,
|
|
@@ -427,64 +511,83 @@ var OIMIndexArrayBased = class {
|
|
|
427
511
|
* If comparator is provided and returns true (no changes), skip the update.
|
|
428
512
|
*/
|
|
429
513
|
setPksWithComparison(key, newPks) {
|
|
514
|
+
return this.setSlotsWithComparison(key, this.resolveSlots(newPks));
|
|
515
|
+
}
|
|
516
|
+
setSlotsWithComparison(key, newSlots) {
|
|
430
517
|
if (this.comparePks) {
|
|
431
|
-
const
|
|
432
|
-
if (
|
|
433
|
-
if (this.comparePks(
|
|
518
|
+
const existingSlotsArray = this.store.getOneByKey(key);
|
|
519
|
+
if (existingSlotsArray && existingSlotsArray.length === newSlots.length) {
|
|
520
|
+
if (this.comparePks(
|
|
521
|
+
this.slotsToPks(existingSlotsArray),
|
|
522
|
+
this.slotsToPks(newSlots)
|
|
523
|
+
)) {
|
|
434
524
|
return false;
|
|
435
525
|
}
|
|
436
|
-
} else if (!
|
|
526
|
+
} else if (!existingSlotsArray && newSlots.length === 0) {
|
|
437
527
|
return false;
|
|
438
528
|
}
|
|
439
529
|
}
|
|
440
|
-
this.store.setOneByKey(key,
|
|
530
|
+
this.store.setOneByKey(key, newSlots);
|
|
441
531
|
return true;
|
|
442
532
|
}
|
|
533
|
+
resolveSlots(pks) {
|
|
534
|
+
const slots = [];
|
|
535
|
+
slots.length = pks.length;
|
|
536
|
+
for (let i = 0; i < pks.length; i++) {
|
|
537
|
+
slots[i] = this.getOrCreateSlot(pks[i]);
|
|
538
|
+
}
|
|
539
|
+
return slots;
|
|
540
|
+
}
|
|
541
|
+
getOrCreateSlot(pk) {
|
|
542
|
+
const resolved = this.resolveSlot?.(pk);
|
|
543
|
+
if (resolved) return resolved;
|
|
544
|
+
let fallback = this.fallbackSlots.get(pk);
|
|
545
|
+
if (!fallback) {
|
|
546
|
+
fallback = { pk, item: void 0 };
|
|
547
|
+
this.fallbackSlots.set(pk, fallback);
|
|
548
|
+
}
|
|
549
|
+
return fallback;
|
|
550
|
+
}
|
|
551
|
+
slotsToPks(slots) {
|
|
552
|
+
const pks = [];
|
|
553
|
+
pks.length = slots.length;
|
|
554
|
+
for (let i = 0; i < slots.length; i++) pks[i] = slots[i].pk;
|
|
555
|
+
return pks;
|
|
556
|
+
}
|
|
443
557
|
/**
|
|
444
558
|
* Emit update event with changed keys
|
|
445
559
|
*/
|
|
446
560
|
emitUpdate(keys) {
|
|
447
561
|
this.emitter.emit(0 /* UPDATE */, { keys });
|
|
448
562
|
}
|
|
563
|
+
/**
|
|
564
|
+
* Emit update event for a single key (fast-path override point).
|
|
565
|
+
*/
|
|
566
|
+
emitUpdateOne(key) {
|
|
567
|
+
this.emitUpdate([key]);
|
|
568
|
+
}
|
|
449
569
|
};
|
|
450
570
|
|
|
451
|
-
// src/enum/
|
|
452
|
-
var
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
})(EOIMUpdateEventCoalescerEventType || {});
|
|
571
|
+
// src/enum/EOIMEventQueueEventType.ts
|
|
572
|
+
var EOIMEventQueueEventType = /* @__PURE__ */ ((EOIMEventQueueEventType2) => {
|
|
573
|
+
EOIMEventQueueEventType2[EOIMEventQueueEventType2["AFTER_FLUSH"] = 0] = "AFTER_FLUSH";
|
|
574
|
+
EOIMEventQueueEventType2[EOIMEventQueueEventType2["BEFORE_FLUSH"] = 1] = "BEFORE_FLUSH";
|
|
575
|
+
return EOIMEventQueueEventType2;
|
|
576
|
+
})(EOIMEventQueueEventType || {});
|
|
458
577
|
|
|
459
578
|
// src/core/OIMUpdateEventEmitter.ts
|
|
460
579
|
var OIMUpdateEventEmitter = class {
|
|
461
|
-
constructor(
|
|
462
|
-
this.keyHandlersBeforeFlush = /* @__PURE__ */ new Map();
|
|
580
|
+
constructor(queue, deliveryMode = "queue") {
|
|
463
581
|
this.keyHandlers = /* @__PURE__ */ new Map();
|
|
464
|
-
this.isDestroyed = false;
|
|
465
|
-
this.isDispatching = false;
|
|
466
|
-
this.isInPrePhase = false;
|
|
467
|
-
this.hasPendingDuringPrePhase = false;
|
|
468
582
|
this.isFlushEnqueued = false;
|
|
469
|
-
this.
|
|
470
|
-
|
|
471
|
-
this.hasPendingDuringPrePhase = true;
|
|
472
|
-
return;
|
|
473
|
-
}
|
|
474
|
-
if (this.isFlushEnqueued) return;
|
|
475
|
-
this.isFlushEnqueued = true;
|
|
476
|
-
this.queue.enqueue(this.onFlush);
|
|
477
|
-
};
|
|
583
|
+
this.updatedKeys = /* @__PURE__ */ new Set();
|
|
584
|
+
this.isAfterFlushDeliveryScheduled = false;
|
|
478
585
|
// Stable handler reference to avoid allocating a new closure on every HAS_CHANGES.
|
|
479
586
|
this.onFlush = () => {
|
|
480
587
|
this.isFlushEnqueued = false;
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
this.
|
|
484
|
-
return;
|
|
485
|
-
}
|
|
486
|
-
if (this.keyHandlers.size === 0 && this.keyHandlersBeforeFlush.size === 0) {
|
|
487
|
-
this.coalescer.clearUpdatedKeys();
|
|
588
|
+
this.dequeueFlush = void 0;
|
|
589
|
+
if (this.keyHandlers.size === 0) {
|
|
590
|
+
this.updatedKeys.clear();
|
|
488
591
|
return;
|
|
489
592
|
}
|
|
490
593
|
const makeHandlerSnapshot = (handlers) => {
|
|
@@ -492,95 +595,133 @@ var OIMUpdateEventEmitter = class {
|
|
|
492
595
|
handlers.forEach((h) => snapshot.push(h));
|
|
493
596
|
return snapshot;
|
|
494
597
|
};
|
|
495
|
-
|
|
496
|
-
this.isDispatching = true;
|
|
497
|
-
this.isInPrePhase = true;
|
|
498
|
-
this.hasPendingDuringPrePhase = false;
|
|
499
|
-
const allKeysForNormalPhase = this.runPrePhaseDrain(makeHandlerSnapshot);
|
|
500
|
-
this.isInPrePhase = false;
|
|
501
|
-
this.runHandlersPhase(allKeysForNormalPhase, makeHandlerSnapshot);
|
|
502
|
-
} finally {
|
|
503
|
-
this.isInPrePhase = false;
|
|
504
|
-
this.isDispatching = false;
|
|
505
|
-
}
|
|
598
|
+
this.runSinglePass(makeHandlerSnapshot);
|
|
506
599
|
};
|
|
507
|
-
this.
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
this.
|
|
511
|
-
|
|
512
|
-
this.queue =
|
|
600
|
+
this.onAfterFlush = () => {
|
|
601
|
+
if (!this.isAfterFlushDeliveryScheduled) return;
|
|
602
|
+
this.isAfterFlushDeliveryScheduled = false;
|
|
603
|
+
this.deliverImmediate();
|
|
604
|
+
};
|
|
605
|
+
this.queue = queue;
|
|
606
|
+
this.deliveryMode = deliveryMode;
|
|
607
|
+
if (this.deliveryMode === "after_flush") {
|
|
608
|
+
this.unsubscribeAfterFlushDelivery = this.queue.emitter.on(
|
|
609
|
+
0 /* AFTER_FLUSH */,
|
|
610
|
+
this.onAfterFlush
|
|
611
|
+
);
|
|
612
|
+
}
|
|
513
613
|
}
|
|
514
614
|
/**
|
|
515
|
-
*
|
|
615
|
+
* Mark keys as updated and schedule delivery.
|
|
616
|
+
*
|
|
617
|
+
* If there are no subscriptions, this is a no-op and does not allocate or retain keys.
|
|
516
618
|
*/
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
619
|
+
markUpdatedKeys(keys) {
|
|
620
|
+
if (keys.length === 0) return;
|
|
621
|
+
if (this.deliveryMode === "queue" && this.queue.isInFlush) {
|
|
622
|
+
throw new Error(
|
|
623
|
+
"OIMUpdateEventEmitter: updates during queue.flush() are not allowed. Finish all writes before calling queue.flush()."
|
|
624
|
+
);
|
|
625
|
+
}
|
|
626
|
+
if (this.keyHandlers.size === 0) return;
|
|
627
|
+
let didAddAny = false;
|
|
628
|
+
for (let i = 0; i < keys.length; i++) {
|
|
629
|
+
const key = keys[i];
|
|
630
|
+
const handlers = this.keyHandlers.get(key);
|
|
631
|
+
if (!handlers || handlers.size === 0) continue;
|
|
632
|
+
this.updatedKeys.add(key);
|
|
633
|
+
didAddAny = true;
|
|
634
|
+
}
|
|
635
|
+
if (!didAddAny) return;
|
|
636
|
+
if (this.deliveryMode === "immediate") {
|
|
637
|
+
this.deliverImmediate();
|
|
638
|
+
return;
|
|
639
|
+
}
|
|
640
|
+
if (this.deliveryMode === "after_flush") {
|
|
641
|
+
this.isAfterFlushDeliveryScheduled = true;
|
|
642
|
+
return;
|
|
643
|
+
}
|
|
644
|
+
if (this.isFlushEnqueued) return;
|
|
645
|
+
this.isFlushEnqueued = true;
|
|
646
|
+
this.dequeueFlush = this.queue.enqueue(this.onFlush);
|
|
647
|
+
}
|
|
648
|
+
markUpdatedKey(key) {
|
|
649
|
+
if (this.deliveryMode === "queue" && this.queue.isInFlush) {
|
|
650
|
+
throw new Error(
|
|
651
|
+
"OIMUpdateEventEmitter: updates during queue.flush() are not allowed. Finish all writes before calling queue.flush()."
|
|
652
|
+
);
|
|
653
|
+
}
|
|
654
|
+
if (this.keyHandlers.size === 0) return;
|
|
655
|
+
const handlers = this.keyHandlers.get(key);
|
|
656
|
+
if (!handlers || handlers.size === 0) return;
|
|
657
|
+
this.updatedKeys.add(key);
|
|
658
|
+
if (this.deliveryMode === "immediate") {
|
|
659
|
+
this.deliverImmediate();
|
|
660
|
+
return;
|
|
661
|
+
}
|
|
662
|
+
if (this.deliveryMode === "after_flush") {
|
|
663
|
+
this.isAfterFlushDeliveryScheduled = true;
|
|
664
|
+
return;
|
|
558
665
|
}
|
|
559
|
-
return
|
|
666
|
+
if (this.isFlushEnqueued) return;
|
|
667
|
+
this.isFlushEnqueued = true;
|
|
668
|
+
this.dequeueFlush = this.queue.enqueue(this.onFlush);
|
|
560
669
|
}
|
|
561
|
-
|
|
562
|
-
if (this.
|
|
670
|
+
markAllUpdated() {
|
|
671
|
+
if (this.deliveryMode === "queue" && this.queue.isInFlush) {
|
|
672
|
+
throw new Error(
|
|
673
|
+
"OIMUpdateEventEmitter: updates during queue.flush() are not allowed. Finish all writes before calling queue.flush()."
|
|
674
|
+
);
|
|
675
|
+
}
|
|
676
|
+
if (this.keyHandlers.size === 0) return;
|
|
677
|
+
this.keyHandlers.forEach((_handlers, key) => {
|
|
678
|
+
this.updatedKeys.add(key);
|
|
679
|
+
});
|
|
680
|
+
if (this.deliveryMode === "immediate") {
|
|
681
|
+
this.deliverImmediate();
|
|
682
|
+
return;
|
|
683
|
+
}
|
|
684
|
+
if (this.deliveryMode === "after_flush") {
|
|
685
|
+
this.isAfterFlushDeliveryScheduled = true;
|
|
563
686
|
return;
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
687
|
+
}
|
|
688
|
+
if (this.isFlushEnqueued) return;
|
|
689
|
+
this.isFlushEnqueued = true;
|
|
690
|
+
this.dequeueFlush = this.queue.enqueue(this.onFlush);
|
|
691
|
+
}
|
|
692
|
+
deliverImmediate() {
|
|
693
|
+
const makeHandlerSnapshot = (handlers) => {
|
|
694
|
+
const snapshot = [];
|
|
695
|
+
handlers.forEach((h) => snapshot.push(h));
|
|
696
|
+
return snapshot;
|
|
697
|
+
};
|
|
698
|
+
this.runSinglePass(makeHandlerSnapshot);
|
|
699
|
+
}
|
|
700
|
+
/**
|
|
701
|
+
* Deliver updated keys and notify handlers once.
|
|
702
|
+
* Re-entrant updates during delivery are forbidden and will throw in markUpdatedKeys().
|
|
703
|
+
*/
|
|
704
|
+
runSinglePass(makeHandlerSnapshot) {
|
|
705
|
+
if (this.updatedKeys.size === 0) return;
|
|
706
|
+
const flushingKeys = this.updatedKeys;
|
|
707
|
+
this.updatedKeys = /* @__PURE__ */ new Set();
|
|
708
|
+
if (this.keyHandlers.size === 0 || flushingKeys.size === 0) return;
|
|
709
|
+
if (flushingKeys.size * 2 < this.keyHandlers.size) {
|
|
710
|
+
flushingKeys.forEach((key) => {
|
|
567
711
|
const handlers = this.keyHandlers.get(key);
|
|
568
712
|
if (!handlers || handlers.size === 0) return;
|
|
569
713
|
const handlerSnapshot = makeHandlerSnapshot(handlers);
|
|
570
714
|
for (let i = 0; i < handlerSnapshot.length; i++) {
|
|
571
|
-
if (this.isDestroyed) return;
|
|
572
715
|
const handler = handlerSnapshot[i];
|
|
573
716
|
if (handlers.has(handler)) handler();
|
|
574
717
|
}
|
|
575
718
|
});
|
|
576
719
|
} else {
|
|
577
720
|
this.keyHandlers.forEach((handlers, key) => {
|
|
578
|
-
if (
|
|
579
|
-
if (!allKeysForNormalPhase.has(key)) return;
|
|
721
|
+
if (!flushingKeys.has(key)) return;
|
|
580
722
|
if (!handlers || handlers.size === 0) return;
|
|
581
723
|
const handlerSnapshot = makeHandlerSnapshot(handlers);
|
|
582
724
|
for (let i = 0; i < handlerSnapshot.length; i++) {
|
|
583
|
-
if (this.isDestroyed) return;
|
|
584
725
|
const handler = handlerSnapshot[i];
|
|
585
726
|
if (handlers.has(handler)) handler();
|
|
586
727
|
}
|
|
@@ -588,14 +729,17 @@ var OIMUpdateEventEmitter = class {
|
|
|
588
729
|
}
|
|
589
730
|
}
|
|
590
731
|
destroy() {
|
|
591
|
-
if (this.
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
732
|
+
if (this.dequeueFlush) {
|
|
733
|
+
this.dequeueFlush();
|
|
734
|
+
this.dequeueFlush = void 0;
|
|
735
|
+
}
|
|
736
|
+
if (this.unsubscribeAfterFlushDelivery) {
|
|
737
|
+
this.unsubscribeAfterFlushDelivery();
|
|
738
|
+
this.unsubscribeAfterFlushDelivery = void 0;
|
|
739
|
+
}
|
|
740
|
+
this.keyHandlers.forEach((handlers) => handlers.clear());
|
|
598
741
|
this.keyHandlers.clear();
|
|
742
|
+
this.updatedKeys.clear();
|
|
599
743
|
}
|
|
600
744
|
/**
|
|
601
745
|
* Get performance metrics for monitoring and debugging
|
|
@@ -616,32 +760,13 @@ var OIMUpdateEventEmitter = class {
|
|
|
616
760
|
* Check if there are any active subscriptions
|
|
617
761
|
*/
|
|
618
762
|
hasSubscriptions() {
|
|
619
|
-
return this.keyHandlers.size > 0
|
|
763
|
+
return this.keyHandlers.size > 0;
|
|
620
764
|
}
|
|
621
765
|
/**
|
|
622
766
|
* Get the number of handlers for a specific key
|
|
623
767
|
*/
|
|
624
768
|
getHandlerCount(key) {
|
|
625
|
-
return
|
|
626
|
-
}
|
|
627
|
-
subscribeOnKeyBeforeFlush(key, handler) {
|
|
628
|
-
let handlers = this.keyHandlersBeforeFlush.get(key);
|
|
629
|
-
if (!handlers) {
|
|
630
|
-
handlers = /* @__PURE__ */ new Set();
|
|
631
|
-
this.keyHandlersBeforeFlush.set(key, handlers);
|
|
632
|
-
}
|
|
633
|
-
handlers.add(handler);
|
|
634
|
-
return () => {
|
|
635
|
-
this.unsubscribeFromKeyBeforeFlush(key, handler);
|
|
636
|
-
};
|
|
637
|
-
}
|
|
638
|
-
unsubscribeFromKeyBeforeFlush(key, handler) {
|
|
639
|
-
const handlers = this.keyHandlersBeforeFlush.get(key);
|
|
640
|
-
if (!handlers) return;
|
|
641
|
-
handlers.delete(handler);
|
|
642
|
-
if (handlers.size === 0) {
|
|
643
|
-
this.keyHandlersBeforeFlush.delete(key);
|
|
644
|
-
}
|
|
769
|
+
return this.keyHandlers.get(key)?.size ?? 0;
|
|
645
770
|
}
|
|
646
771
|
subscribeOnKey(key, handler) {
|
|
647
772
|
let handlers = this.keyHandlers.get(key);
|
|
@@ -660,6 +785,15 @@ var OIMUpdateEventEmitter = class {
|
|
|
660
785
|
handlers.delete(handler);
|
|
661
786
|
if (handlers.size === 0) {
|
|
662
787
|
this.keyHandlers.delete(key);
|
|
788
|
+
this.updatedKeys.delete(key);
|
|
789
|
+
}
|
|
790
|
+
if (this.keyHandlers.size === 0) {
|
|
791
|
+
this.updatedKeys.clear();
|
|
792
|
+
if (this.dequeueFlush) {
|
|
793
|
+
this.dequeueFlush();
|
|
794
|
+
this.dequeueFlush = void 0;
|
|
795
|
+
}
|
|
796
|
+
this.isFlushEnqueued = false;
|
|
663
797
|
}
|
|
664
798
|
}
|
|
665
799
|
subscribeOnKeys(keys, handler) {
|
|
@@ -681,30 +815,6 @@ var OIMUpdateEventEmitter = class {
|
|
|
681
815
|
}
|
|
682
816
|
};
|
|
683
817
|
}
|
|
684
|
-
subscribeOnKeysBeforeFlush(keys, handler) {
|
|
685
|
-
const subscribedKeys = [];
|
|
686
|
-
for (const key of keys) {
|
|
687
|
-
let handlers = this.keyHandlersBeforeFlush.get(key);
|
|
688
|
-
if (!handlers) {
|
|
689
|
-
handlers = /* @__PURE__ */ new Set();
|
|
690
|
-
this.keyHandlersBeforeFlush.set(key, handlers);
|
|
691
|
-
}
|
|
692
|
-
if (!handlers.has(handler)) {
|
|
693
|
-
handlers.add(handler);
|
|
694
|
-
subscribedKeys.push(key);
|
|
695
|
-
}
|
|
696
|
-
}
|
|
697
|
-
return () => {
|
|
698
|
-
for (const key of subscribedKeys) {
|
|
699
|
-
this.unsubscribeFromKeyBeforeFlush(key, handler);
|
|
700
|
-
}
|
|
701
|
-
};
|
|
702
|
-
}
|
|
703
|
-
unsubscribeFromKeysBeforeFlush(keys, handler) {
|
|
704
|
-
for (const key of keys) {
|
|
705
|
-
this.unsubscribeFromKeyBeforeFlush(key, handler);
|
|
706
|
-
}
|
|
707
|
-
}
|
|
708
818
|
unsubscribeFromKeys(keys, handler) {
|
|
709
819
|
for (const key of keys) {
|
|
710
820
|
this.unsubscribeFromKey(key, handler);
|
|
@@ -712,203 +822,11 @@ var OIMUpdateEventEmitter = class {
|
|
|
712
822
|
}
|
|
713
823
|
};
|
|
714
824
|
|
|
715
|
-
// src/core/OIMIndexManualSetBased.ts
|
|
716
|
-
var OIMIndexManualSetBased = class extends OIMIndexSetBased {
|
|
717
|
-
constructor(options = {}) {
|
|
718
|
-
super(options);
|
|
719
|
-
}
|
|
720
|
-
/**
|
|
721
|
-
* Set primary keys for a specific index key, replacing any existing values.
|
|
722
|
-
* Uses optional comparator to skip updates if PKs haven't actually changed.
|
|
723
|
-
*/
|
|
724
|
-
setPks(key, pks) {
|
|
725
|
-
const hasChanges = this.setPksWithComparison(key, new Set(pks));
|
|
726
|
-
if (hasChanges) {
|
|
727
|
-
this.emitUpdate([key]);
|
|
728
|
-
}
|
|
729
|
-
}
|
|
730
|
-
/**
|
|
731
|
-
* Add primary keys to a specific index key
|
|
732
|
-
*/
|
|
733
|
-
addPks(key, pks) {
|
|
734
|
-
if (pks.length === 0) return;
|
|
735
|
-
let pksSet = this.store.getOneByKey(key);
|
|
736
|
-
if (!pksSet) {
|
|
737
|
-
pksSet = /* @__PURE__ */ new Set();
|
|
738
|
-
this.store.setOneByKey(key, pksSet);
|
|
739
|
-
}
|
|
740
|
-
let hasChanges = false;
|
|
741
|
-
for (const pk of pks) {
|
|
742
|
-
if (!pksSet.has(pk)) {
|
|
743
|
-
pksSet.add(pk);
|
|
744
|
-
hasChanges = true;
|
|
745
|
-
}
|
|
746
|
-
}
|
|
747
|
-
if (hasChanges) {
|
|
748
|
-
this.store.setOneByKey(key, pksSet);
|
|
749
|
-
this.emitUpdate([key]);
|
|
750
|
-
}
|
|
751
|
-
}
|
|
752
|
-
/**
|
|
753
|
-
* Remove primary keys from a specific index key
|
|
754
|
-
*/
|
|
755
|
-
removePks(key, pks) {
|
|
756
|
-
if (pks.length === 0) return;
|
|
757
|
-
const pksSet = this.store.getOneByKey(key);
|
|
758
|
-
if (!pksSet) return;
|
|
759
|
-
let hasChanges = false;
|
|
760
|
-
for (const pk of pks) {
|
|
761
|
-
if (pksSet.delete(pk)) {
|
|
762
|
-
hasChanges = true;
|
|
763
|
-
}
|
|
764
|
-
}
|
|
765
|
-
if (pksSet.size === 0) {
|
|
766
|
-
this.store.removeOneByKey(key);
|
|
767
|
-
hasChanges = true;
|
|
768
|
-
} else if (hasChanges) {
|
|
769
|
-
this.store.setOneByKey(key, pksSet);
|
|
770
|
-
}
|
|
771
|
-
if (hasChanges) {
|
|
772
|
-
this.emitUpdate([key]);
|
|
773
|
-
}
|
|
774
|
-
}
|
|
775
|
-
/**
|
|
776
|
-
* Clear all primary keys for a specific index key, or all keys if no key specified
|
|
777
|
-
*/
|
|
778
|
-
clear(key) {
|
|
779
|
-
if (key === void 0) {
|
|
780
|
-
const allKeys = this.store.getAllKeys();
|
|
781
|
-
if (allKeys.length > 0) {
|
|
782
|
-
this.store.clear();
|
|
783
|
-
this.emitUpdate(allKeys);
|
|
784
|
-
}
|
|
785
|
-
} else {
|
|
786
|
-
if (this.store.getOneByKey(key) !== void 0) {
|
|
787
|
-
this.store.removeOneByKey(key);
|
|
788
|
-
this.emitUpdate([key]);
|
|
789
|
-
}
|
|
790
|
-
}
|
|
791
|
-
}
|
|
792
|
-
};
|
|
793
|
-
|
|
794
|
-
// src/const/OIMDBSettings.ts
|
|
795
|
-
var OIMDBSettings = class {
|
|
796
|
-
};
|
|
797
|
-
/**
|
|
798
|
-
* Fixed key used in the manual index to store updated keys set in coalescers.
|
|
799
|
-
* This constant is exported so users can create their own indexes and pass them to coalescers.
|
|
800
|
-
*/
|
|
801
|
-
OIMDBSettings.UPDATED_KEYS_INDEX_KEY = "__updatedKeys__";
|
|
802
|
-
OIMDBSettings.FLUSHING_KEYS_INDEX_KEY = "__flushingKeys__";
|
|
803
|
-
|
|
804
|
-
// src/core/OIMUpdateEventCoalescer.ts
|
|
805
|
-
var OIMUpdateEventCoalescer = class {
|
|
806
|
-
constructor(index, flushingIndex) {
|
|
807
|
-
this.emitter = new OIMEventEmitter();
|
|
808
|
-
this.hasEmittedChanges = false;
|
|
809
|
-
this.updatedKeysIndex = index ?? new OIMIndexManualSetBased({
|
|
810
|
-
store: new OIMIndexStoreMapDrivenSetBased()
|
|
811
|
-
});
|
|
812
|
-
this.flushingUpdatedKeysIndex = flushingIndex ?? new OIMIndexManualSetBased({
|
|
813
|
-
store: new OIMIndexStoreMapDrivenSetBased()
|
|
814
|
-
});
|
|
815
|
-
if (!this.updatedKeysIndex.hasKey(OIMDBSettings.UPDATED_KEYS_INDEX_KEY)) {
|
|
816
|
-
this.updatedKeysIndex.setPks(
|
|
817
|
-
OIMDBSettings.UPDATED_KEYS_INDEX_KEY,
|
|
818
|
-
[]
|
|
819
|
-
);
|
|
820
|
-
}
|
|
821
|
-
}
|
|
822
|
-
/**
|
|
823
|
-
* Get the set of keys that have been updated since last clear
|
|
824
|
-
*/
|
|
825
|
-
getUpdatedKeys() {
|
|
826
|
-
return this.updatedKeysIndex.getPksByKey(
|
|
827
|
-
OIMDBSettings.UPDATED_KEYS_INDEX_KEY
|
|
828
|
-
);
|
|
829
|
-
}
|
|
830
|
-
getFlushingUpdatedKeys() {
|
|
831
|
-
return this.flushingUpdatedKeysIndex.getPksByKey(
|
|
832
|
-
OIMDBSettings.FLUSHING_KEYS_INDEX_KEY
|
|
833
|
-
);
|
|
834
|
-
}
|
|
835
|
-
markUpdatedKeysAsFlushing() {
|
|
836
|
-
this.flushingUpdatedKeysIndex.setPks(
|
|
837
|
-
OIMDBSettings.FLUSHING_KEYS_INDEX_KEY,
|
|
838
|
-
Array.from(this.getUpdatedKeys())
|
|
839
|
-
);
|
|
840
|
-
this.clearUpdatedKeys();
|
|
841
|
-
}
|
|
842
|
-
/**
|
|
843
|
-
* Clear all updated keys and reset the changed state
|
|
844
|
-
*/
|
|
845
|
-
clearUpdatedKeys() {
|
|
846
|
-
this.emitter.emit(
|
|
847
|
-
1 /* BEFORE_FLUSH */,
|
|
848
|
-
void 0
|
|
849
|
-
);
|
|
850
|
-
this.updatedKeysIndex.setPks(OIMDBSettings.UPDATED_KEYS_INDEX_KEY, []);
|
|
851
|
-
this.hasEmittedChanges = false;
|
|
852
|
-
this.emitter.emit(
|
|
853
|
-
2 /* AFTER_FLUSH */,
|
|
854
|
-
void 0
|
|
855
|
-
);
|
|
856
|
-
}
|
|
857
|
-
clearFlushingUpdatedKeys() {
|
|
858
|
-
this.flushingUpdatedKeysIndex.setPks(
|
|
859
|
-
OIMDBSettings.FLUSHING_KEYS_INDEX_KEY,
|
|
860
|
-
[]
|
|
861
|
-
);
|
|
862
|
-
}
|
|
863
|
-
/**
|
|
864
|
-
* Add keys to the updated set and emit HAS_CHANGES event if needed
|
|
865
|
-
*/
|
|
866
|
-
addUpdatedKeys(keys) {
|
|
867
|
-
this.updatedKeysIndex.addPks(
|
|
868
|
-
OIMDBSettings.UPDATED_KEYS_INDEX_KEY,
|
|
869
|
-
keys
|
|
870
|
-
);
|
|
871
|
-
if (!this.hasEmittedChanges) {
|
|
872
|
-
this.hasEmittedChanges = true;
|
|
873
|
-
this.emitter.emit(
|
|
874
|
-
0 /* HAS_CHANGES */,
|
|
875
|
-
void 0
|
|
876
|
-
);
|
|
877
|
-
}
|
|
878
|
-
}
|
|
879
|
-
};
|
|
880
|
-
|
|
881
|
-
// src/core/OIMUpdateEventCoalescerIndex.ts
|
|
882
|
-
var OIMUpdateEventCoalescerIndex = class extends OIMUpdateEventCoalescer {
|
|
883
|
-
constructor(indexEmitter) {
|
|
884
|
-
super();
|
|
885
|
-
this.indexEmitter = indexEmitter;
|
|
886
|
-
/**
|
|
887
|
-
* When the index is updated, we keep track of the updated keys.
|
|
888
|
-
*/
|
|
889
|
-
this.handleUpdate = (payload) => {
|
|
890
|
-
this.addUpdatedKeys(payload.keys);
|
|
891
|
-
};
|
|
892
|
-
this.indexEmitter.on(0 /* UPDATE */, this.handleUpdate);
|
|
893
|
-
}
|
|
894
|
-
destroy() {
|
|
895
|
-
this.indexEmitter.off(0 /* UPDATE */, this.handleUpdate);
|
|
896
|
-
this.emitter.offAll();
|
|
897
|
-
this.clearUpdatedKeys();
|
|
898
|
-
}
|
|
899
|
-
};
|
|
900
|
-
|
|
901
825
|
// src/abstract/OIMReactiveIndexSetBased.ts
|
|
902
826
|
var OIMReactiveIndexSetBased = class {
|
|
903
|
-
constructor(queue,
|
|
904
|
-
this.
|
|
905
|
-
this.
|
|
906
|
-
this.index.emitter
|
|
907
|
-
);
|
|
908
|
-
this.updateEventEmitter = new OIMUpdateEventEmitter({
|
|
909
|
-
coalescer: this.coalescer,
|
|
910
|
-
queue
|
|
911
|
-
});
|
|
827
|
+
constructor(queue, createIndex) {
|
|
828
|
+
this.updateEmitter = new OIMUpdateEventEmitter(queue);
|
|
829
|
+
this.index = createIndex(this.updateEmitter);
|
|
912
830
|
}
|
|
913
831
|
getPksByKey(key) {
|
|
914
832
|
return this.index.getPksByKey(key);
|
|
@@ -916,6 +834,12 @@ var OIMReactiveIndexSetBased = class {
|
|
|
916
834
|
getPksByKeys(keys) {
|
|
917
835
|
return this.index.getPksByKeys(keys);
|
|
918
836
|
}
|
|
837
|
+
getSlotsByKey(key) {
|
|
838
|
+
return this.index.getSlotsByKey(key);
|
|
839
|
+
}
|
|
840
|
+
getSlotsByKeys(keys) {
|
|
841
|
+
return this.index.getSlotsByKeys(keys);
|
|
842
|
+
}
|
|
919
843
|
hasKey(key) {
|
|
920
844
|
return this.index.hasKey(key);
|
|
921
845
|
}
|
|
@@ -934,24 +858,38 @@ var OIMReactiveIndexSetBased = class {
|
|
|
934
858
|
getMetrics() {
|
|
935
859
|
return this.index.getMetrics();
|
|
936
860
|
}
|
|
937
|
-
|
|
938
|
-
this.
|
|
939
|
-
this.coalescer.destroy();
|
|
940
|
-
this.index.destroy();
|
|
861
|
+
subscribeOnKey(key, handler) {
|
|
862
|
+
return this.updateEmitter.subscribeOnKey(key, handler);
|
|
941
863
|
}
|
|
942
|
-
|
|
943
|
-
|
|
864
|
+
subscribeOnKeys(keys, handler) {
|
|
865
|
+
return this.updateEmitter.subscribeOnKeys(keys, handler);
|
|
866
|
+
}
|
|
867
|
+
unsubscribeFromKey(key, handler) {
|
|
868
|
+
this.updateEmitter.unsubscribeFromKey(key, handler);
|
|
869
|
+
}
|
|
870
|
+
unsubscribeFromKeys(keys, handler) {
|
|
871
|
+
this.updateEmitter.unsubscribeFromKeys(keys, handler);
|
|
872
|
+
}
|
|
873
|
+
hasSubscriptions() {
|
|
874
|
+
return this.updateEmitter.hasSubscriptions();
|
|
875
|
+
}
|
|
876
|
+
getHandlerCount(key) {
|
|
877
|
+
return this.updateEmitter.getHandlerCount(key);
|
|
878
|
+
}
|
|
879
|
+
getSubscriptionMetrics() {
|
|
880
|
+
return this.updateEmitter.getMetrics();
|
|
881
|
+
}
|
|
882
|
+
destroy() {
|
|
883
|
+
this.updateEmitter.destroy();
|
|
884
|
+
this.index.destroy();
|
|
885
|
+
}
|
|
886
|
+
};
|
|
887
|
+
|
|
944
888
|
// src/abstract/OIMReactiveIndexArrayBased.ts
|
|
945
889
|
var OIMReactiveIndexArrayBased = class {
|
|
946
|
-
constructor(queue,
|
|
947
|
-
this.
|
|
948
|
-
this.
|
|
949
|
-
this.index.emitter
|
|
950
|
-
);
|
|
951
|
-
this.updateEventEmitter = new OIMUpdateEventEmitter({
|
|
952
|
-
coalescer: this.coalescer,
|
|
953
|
-
queue
|
|
954
|
-
});
|
|
890
|
+
constructor(queue, createIndex) {
|
|
891
|
+
this.updateEmitter = new OIMUpdateEventEmitter(queue);
|
|
892
|
+
this.index = createIndex(this.updateEmitter);
|
|
955
893
|
}
|
|
956
894
|
getPksByKey(key) {
|
|
957
895
|
return this.index.getPksByKey(key);
|
|
@@ -959,6 +897,12 @@ var OIMReactiveIndexArrayBased = class {
|
|
|
959
897
|
getPksByKeys(keys) {
|
|
960
898
|
return this.index.getPksByKeys(keys);
|
|
961
899
|
}
|
|
900
|
+
getSlotsByKey(key) {
|
|
901
|
+
return this.index.getSlotsByKey(key);
|
|
902
|
+
}
|
|
903
|
+
getSlotsByKeys(keys) {
|
|
904
|
+
return this.index.getSlotsByKeys(keys);
|
|
905
|
+
}
|
|
962
906
|
hasKey(key) {
|
|
963
907
|
return this.index.hasKey(key);
|
|
964
908
|
}
|
|
@@ -977,9 +921,29 @@ var OIMReactiveIndexArrayBased = class {
|
|
|
977
921
|
getMetrics() {
|
|
978
922
|
return this.index.getMetrics();
|
|
979
923
|
}
|
|
924
|
+
subscribeOnKey(key, handler) {
|
|
925
|
+
return this.updateEmitter.subscribeOnKey(key, handler);
|
|
926
|
+
}
|
|
927
|
+
subscribeOnKeys(keys, handler) {
|
|
928
|
+
return this.updateEmitter.subscribeOnKeys(keys, handler);
|
|
929
|
+
}
|
|
930
|
+
unsubscribeFromKey(key, handler) {
|
|
931
|
+
this.updateEmitter.unsubscribeFromKey(key, handler);
|
|
932
|
+
}
|
|
933
|
+
unsubscribeFromKeys(keys, handler) {
|
|
934
|
+
this.updateEmitter.unsubscribeFromKeys(keys, handler);
|
|
935
|
+
}
|
|
936
|
+
hasSubscriptions() {
|
|
937
|
+
return this.updateEmitter.hasSubscriptions();
|
|
938
|
+
}
|
|
939
|
+
getHandlerCount(key) {
|
|
940
|
+
return this.updateEmitter.getHandlerCount(key);
|
|
941
|
+
}
|
|
942
|
+
getSubscriptionMetrics() {
|
|
943
|
+
return this.updateEmitter.getMetrics();
|
|
944
|
+
}
|
|
980
945
|
destroy() {
|
|
981
|
-
this.
|
|
982
|
-
this.coalescer.destroy();
|
|
946
|
+
this.updateEmitter.destroy();
|
|
983
947
|
this.index.destroy();
|
|
984
948
|
}
|
|
985
949
|
};
|
|
@@ -999,26 +963,52 @@ var OIMPkSelectorFactory = class {
|
|
|
999
963
|
var OIMCollectionStoreMapDriven = class extends OIMCollectionStore {
|
|
1000
964
|
constructor() {
|
|
1001
965
|
super(...arguments);
|
|
1002
|
-
this.
|
|
966
|
+
this.slots = /* @__PURE__ */ new Map();
|
|
1003
967
|
}
|
|
1004
968
|
setOneByPk(pk, entity) {
|
|
1005
|
-
this.
|
|
969
|
+
const slot = this.slots.get(pk);
|
|
970
|
+
if (slot) {
|
|
971
|
+
slot.item = entity;
|
|
972
|
+
} else {
|
|
973
|
+
this.slots.set(pk, { pk, item: entity });
|
|
974
|
+
}
|
|
1006
975
|
}
|
|
1007
976
|
setManyByPks(pks, entities) {
|
|
1008
977
|
for (let i = 0; i < pks.length; i++) {
|
|
1009
|
-
this.
|
|
978
|
+
this.setOneByPk(pks[i], entities[i]);
|
|
979
|
+
}
|
|
980
|
+
}
|
|
981
|
+
getSlotByPk(pk) {
|
|
982
|
+
return this.slots.get(pk);
|
|
983
|
+
}
|
|
984
|
+
getSlotsByPks(pks) {
|
|
985
|
+
const result = [];
|
|
986
|
+
result.length = pks.length;
|
|
987
|
+
let writeIndex = 0;
|
|
988
|
+
for (let i = 0; i < pks.length; i++) {
|
|
989
|
+
const slot = this.slots.get(pks[i]);
|
|
990
|
+
if (slot !== void 0) {
|
|
991
|
+
result[writeIndex++] = slot;
|
|
992
|
+
}
|
|
1010
993
|
}
|
|
994
|
+
result.length = writeIndex;
|
|
995
|
+
return result;
|
|
996
|
+
}
|
|
997
|
+
getAllSlots() {
|
|
998
|
+
return Array.from(this.slots.values());
|
|
1011
999
|
}
|
|
1012
1000
|
removeOneByPk(pk) {
|
|
1013
|
-
this.
|
|
1001
|
+
const slot = this.slots.get(pk);
|
|
1002
|
+
if (slot) slot.item = void 0;
|
|
1003
|
+
this.slots.delete(pk);
|
|
1014
1004
|
}
|
|
1015
1005
|
removeManyByPks(pks) {
|
|
1016
1006
|
for (const pk of pks) {
|
|
1017
|
-
this.
|
|
1007
|
+
this.removeOneByPk(pk);
|
|
1018
1008
|
}
|
|
1019
1009
|
}
|
|
1020
1010
|
getOneByPk(pk) {
|
|
1021
|
-
return this.
|
|
1011
|
+
return this.slots.get(pk)?.item;
|
|
1022
1012
|
}
|
|
1023
1013
|
getManyByPks(pks) {
|
|
1024
1014
|
const result = [];
|
|
@@ -1034,16 +1024,23 @@ var OIMCollectionStoreMapDriven = class extends OIMCollectionStore {
|
|
|
1034
1024
|
return result;
|
|
1035
1025
|
}
|
|
1036
1026
|
getAll() {
|
|
1037
|
-
|
|
1027
|
+
const result = [];
|
|
1028
|
+
for (const slot of this.slots.values()) {
|
|
1029
|
+
if (slot.item !== void 0) result.push(slot.item);
|
|
1030
|
+
}
|
|
1031
|
+
return result;
|
|
1038
1032
|
}
|
|
1039
1033
|
countAll() {
|
|
1040
|
-
return this.
|
|
1034
|
+
return this.slots.size;
|
|
1041
1035
|
}
|
|
1042
1036
|
clear() {
|
|
1043
|
-
this.
|
|
1037
|
+
for (const slot of this.slots.values()) {
|
|
1038
|
+
slot.item = void 0;
|
|
1039
|
+
}
|
|
1040
|
+
this.slots.clear();
|
|
1044
1041
|
}
|
|
1045
1042
|
getAllPks() {
|
|
1046
|
-
return Array.from(this.
|
|
1043
|
+
return Array.from(this.slots.keys());
|
|
1047
1044
|
}
|
|
1048
1045
|
destroy() {
|
|
1049
1046
|
this.clear();
|
|
@@ -1079,6 +1076,15 @@ var OIMCollection = class {
|
|
|
1079
1076
|
getManyByPks(pks) {
|
|
1080
1077
|
return this.store.getManyByPks(pks);
|
|
1081
1078
|
}
|
|
1079
|
+
getSlotByPk(pk) {
|
|
1080
|
+
return this.store.getSlotByPk(pk);
|
|
1081
|
+
}
|
|
1082
|
+
getSlotsByPks(pks) {
|
|
1083
|
+
return this.store.getSlotsByPks(pks);
|
|
1084
|
+
}
|
|
1085
|
+
getAllSlots() {
|
|
1086
|
+
return this.store.getAllSlots();
|
|
1087
|
+
}
|
|
1082
1088
|
upsertOneByPk(pk, entity) {
|
|
1083
1089
|
this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1084
1090
|
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
@@ -1151,47 +1157,139 @@ var OIMCollection = class {
|
|
|
1151
1157
|
}
|
|
1152
1158
|
};
|
|
1153
1159
|
|
|
1154
|
-
// src/core/OIMUpdateEventCoalescerCollection.ts
|
|
1155
|
-
var OIMUpdateEventCoalescerCollection = class extends OIMUpdateEventCoalescer {
|
|
1156
|
-
constructor(collectionEmitter) {
|
|
1157
|
-
super();
|
|
1158
|
-
this.collectionEmitter = collectionEmitter;
|
|
1159
|
-
/**
|
|
1160
|
-
* When the collection is updated, we keep track of the updated pks.
|
|
1161
|
-
*/
|
|
1162
|
-
this.handleUpdate = (payload) => {
|
|
1163
|
-
this.addUpdatedKeys(payload.pks);
|
|
1164
|
-
};
|
|
1165
|
-
this.collectionEmitter.on(
|
|
1166
|
-
0 /* UPDATE */,
|
|
1167
|
-
this.handleUpdate
|
|
1168
|
-
);
|
|
1169
|
-
}
|
|
1170
|
-
destroy() {
|
|
1171
|
-
this.collectionEmitter.off(
|
|
1172
|
-
0 /* UPDATE */,
|
|
1173
|
-
this.handleUpdate
|
|
1174
|
-
);
|
|
1175
|
-
this.emitter.offAll();
|
|
1176
|
-
this.clearUpdatedKeys();
|
|
1177
|
-
}
|
|
1178
|
-
};
|
|
1179
|
-
|
|
1180
1160
|
// src/core/OIMReactiveCollection.ts
|
|
1181
1161
|
var OIMReactiveCollection = class extends OIMCollection {
|
|
1182
1162
|
constructor(queue, opts) {
|
|
1183
1163
|
super(opts);
|
|
1184
|
-
this.
|
|
1185
|
-
|
|
1164
|
+
this.anyUpdateHandlers = /* @__PURE__ */ new Set();
|
|
1165
|
+
this.pendingAnyUpdatePks = /* @__PURE__ */ new Set();
|
|
1166
|
+
this.isAnyUpdateClearPending = false;
|
|
1167
|
+
this.isAnyUpdateScheduled = false;
|
|
1168
|
+
this.runAnyUpdate = () => {
|
|
1169
|
+
if (!this.isAnyUpdateScheduled) return;
|
|
1170
|
+
this.isAnyUpdateScheduled = false;
|
|
1171
|
+
this.dequeueAnyUpdate = void 0;
|
|
1172
|
+
const pks = this.isAnyUpdateClearPending ? [] : Array.from(this.pendingAnyUpdatePks);
|
|
1173
|
+
this.pendingAnyUpdatePks.clear();
|
|
1174
|
+
this.isAnyUpdateClearPending = false;
|
|
1175
|
+
const snapshot = Array.from(this.anyUpdateHandlers);
|
|
1176
|
+
for (let i = 0; i < snapshot.length; i++) snapshot[i](pks);
|
|
1177
|
+
};
|
|
1178
|
+
this.queue = queue;
|
|
1179
|
+
this.updateEmitter = new OIMUpdateEventEmitter(queue, "queue");
|
|
1180
|
+
}
|
|
1181
|
+
subscribeOnKey(pk, handler) {
|
|
1182
|
+
return this.updateEmitter.subscribeOnKey(pk, handler);
|
|
1183
|
+
}
|
|
1184
|
+
subscribeOnKeys(pks, handler) {
|
|
1185
|
+
return this.updateEmitter.subscribeOnKeys(pks, handler);
|
|
1186
|
+
}
|
|
1187
|
+
unsubscribeFromKey(pk, handler) {
|
|
1188
|
+
this.updateEmitter.unsubscribeFromKey(pk, handler);
|
|
1189
|
+
}
|
|
1190
|
+
unsubscribeFromKeys(pks, handler) {
|
|
1191
|
+
this.updateEmitter.unsubscribeFromKeys(pks, handler);
|
|
1192
|
+
}
|
|
1193
|
+
destroySubscriptions() {
|
|
1194
|
+
this.updateEmitter.destroy();
|
|
1195
|
+
}
|
|
1196
|
+
hasSubscriptions() {
|
|
1197
|
+
return this.updateEmitter.hasSubscriptions();
|
|
1198
|
+
}
|
|
1199
|
+
getHandlerCount(pk) {
|
|
1200
|
+
return this.updateEmitter.getHandlerCount(pk);
|
|
1201
|
+
}
|
|
1202
|
+
getMetrics() {
|
|
1203
|
+
return this.updateEmitter.getMetrics();
|
|
1204
|
+
}
|
|
1205
|
+
subscribeOnAnyUpdate(handler) {
|
|
1206
|
+
this.anyUpdateHandlers.add(handler);
|
|
1207
|
+
return () => {
|
|
1208
|
+
this.anyUpdateHandlers.delete(handler);
|
|
1209
|
+
};
|
|
1210
|
+
}
|
|
1211
|
+
upsertOneByPk(pk, entity) {
|
|
1212
|
+
this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1213
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1214
|
+
this.updateEmitter.markUpdatedKey(pk);
|
|
1215
|
+
this.trackAnyUpdatePk(pk);
|
|
1216
|
+
}
|
|
1217
|
+
upsertOne(entity) {
|
|
1218
|
+
const pk = this.upsertOneWithoutNotifications(entity);
|
|
1219
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1220
|
+
this.updateEmitter.markUpdatedKey(pk);
|
|
1221
|
+
this.trackAnyUpdatePk(pk);
|
|
1222
|
+
}
|
|
1223
|
+
upsertMany(entities) {
|
|
1224
|
+
const pks = entities.map(
|
|
1225
|
+
(entity) => this.upsertOneWithoutNotifications(entity)
|
|
1186
1226
|
);
|
|
1187
|
-
this.
|
|
1188
|
-
|
|
1189
|
-
|
|
1190
|
-
|
|
1227
|
+
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
1228
|
+
this.updateEmitter.markUpdatedKeys(pks);
|
|
1229
|
+
this.trackAnyUpdatePks(pks);
|
|
1230
|
+
}
|
|
1231
|
+
removeOne(entity) {
|
|
1232
|
+
const pk = this.selectPk(entity);
|
|
1233
|
+
this.store.removeOneByPk(pk);
|
|
1234
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1235
|
+
this.updateEmitter.markUpdatedKey(pk);
|
|
1236
|
+
this.trackAnyUpdatePk(pk);
|
|
1237
|
+
}
|
|
1238
|
+
removeMany(entities) {
|
|
1239
|
+
const pks = entities.map(this.selectPk);
|
|
1240
|
+
this.store.removeManyByPks(pks);
|
|
1241
|
+
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
1242
|
+
this.updateEmitter.markUpdatedKeys(pks);
|
|
1243
|
+
this.trackAnyUpdatePks(pks);
|
|
1244
|
+
}
|
|
1245
|
+
removeOneByPk(pk) {
|
|
1246
|
+
this.store.removeOneByPk(pk);
|
|
1247
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1248
|
+
this.updateEmitter.markUpdatedKey(pk);
|
|
1249
|
+
this.trackAnyUpdatePk(pk);
|
|
1250
|
+
}
|
|
1251
|
+
removeManyByPks(pks) {
|
|
1252
|
+
this.store.removeManyByPks(pks);
|
|
1253
|
+
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
1254
|
+
this.updateEmitter.markUpdatedKeys(pks);
|
|
1255
|
+
this.trackAnyUpdatePks(pks);
|
|
1256
|
+
}
|
|
1257
|
+
clear() {
|
|
1258
|
+
this.store.clear();
|
|
1259
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [] });
|
|
1260
|
+
this.updateEmitter.markAllUpdated();
|
|
1261
|
+
this.trackAnyUpdateClear();
|
|
1262
|
+
}
|
|
1263
|
+
trackAnyUpdatePk(pk) {
|
|
1264
|
+
if (this.anyUpdateHandlers.size === 0) return;
|
|
1265
|
+
this.pendingAnyUpdatePks.add(pk);
|
|
1266
|
+
this.ensureAnyUpdateEnqueued();
|
|
1267
|
+
}
|
|
1268
|
+
trackAnyUpdatePks(pks) {
|
|
1269
|
+
if (this.anyUpdateHandlers.size === 0) return;
|
|
1270
|
+
for (let i = 0; i < pks.length; i++)
|
|
1271
|
+
this.pendingAnyUpdatePks.add(pks[i]);
|
|
1272
|
+
this.ensureAnyUpdateEnqueued();
|
|
1273
|
+
}
|
|
1274
|
+
trackAnyUpdateClear() {
|
|
1275
|
+
if (this.anyUpdateHandlers.size === 0) return;
|
|
1276
|
+
this.isAnyUpdateClearPending = true;
|
|
1277
|
+
this.pendingAnyUpdatePks.clear();
|
|
1278
|
+
this.ensureAnyUpdateEnqueued();
|
|
1279
|
+
}
|
|
1280
|
+
ensureAnyUpdateEnqueued() {
|
|
1281
|
+
if (this.isAnyUpdateScheduled) return;
|
|
1282
|
+
this.isAnyUpdateScheduled = true;
|
|
1283
|
+
this.dequeueAnyUpdate = this.queue.enqueue(this.runAnyUpdate);
|
|
1191
1284
|
}
|
|
1192
1285
|
destroy() {
|
|
1193
|
-
this.
|
|
1194
|
-
this.
|
|
1286
|
+
this.updateEmitter.destroy();
|
|
1287
|
+
if (this.dequeueAnyUpdate) {
|
|
1288
|
+
this.dequeueAnyUpdate();
|
|
1289
|
+
this.dequeueAnyUpdate = void 0;
|
|
1290
|
+
}
|
|
1291
|
+
this.anyUpdateHandlers.clear();
|
|
1292
|
+
this.pendingAnyUpdatePks.clear();
|
|
1195
1293
|
super.destroy();
|
|
1196
1294
|
}
|
|
1197
1295
|
};
|
|
@@ -1291,54 +1389,158 @@ var OIMObject = class {
|
|
|
1291
1389
|
}
|
|
1292
1390
|
};
|
|
1293
1391
|
|
|
1294
|
-
// src/core/OIMUpdateEventCoalescerObject.ts
|
|
1295
|
-
var OIMUpdateEventCoalescerObject = class extends OIMUpdateEventCoalescer {
|
|
1296
|
-
constructor(objectEmitter) {
|
|
1297
|
-
super();
|
|
1298
|
-
this.objectEmitter = objectEmitter;
|
|
1299
|
-
/**
|
|
1300
|
-
* When the object is updated, we keep track of the updated keys.
|
|
1301
|
-
*/
|
|
1302
|
-
this.handleUpdate = (payload) => {
|
|
1303
|
-
this.addUpdatedKeys(payload.keys);
|
|
1304
|
-
};
|
|
1305
|
-
this.objectEmitter.on(0 /* UPDATE */, this.handleUpdate);
|
|
1306
|
-
}
|
|
1307
|
-
destroy() {
|
|
1308
|
-
this.objectEmitter.off(0 /* UPDATE */, this.handleUpdate);
|
|
1309
|
-
this.emitter.offAll();
|
|
1310
|
-
this.clearUpdatedKeys();
|
|
1311
|
-
}
|
|
1312
|
-
};
|
|
1313
|
-
|
|
1314
1392
|
// src/core/OIMReactiveObject.ts
|
|
1315
1393
|
var OIMReactiveObject = class extends OIMObject {
|
|
1316
1394
|
constructor(queue, opts) {
|
|
1317
1395
|
super(opts);
|
|
1318
|
-
this.
|
|
1319
|
-
this.
|
|
1320
|
-
|
|
1321
|
-
queue
|
|
1396
|
+
this.updateEmitter = new OIMUpdateEventEmitter(queue, "queue");
|
|
1397
|
+
this.emitter.on(0 /* UPDATE */, (payload) => {
|
|
1398
|
+
this.updateEmitter.markUpdatedKeys(payload.keys);
|
|
1322
1399
|
});
|
|
1323
1400
|
}
|
|
1401
|
+
subscribeOnKey(key, handler) {
|
|
1402
|
+
return this.updateEmitter.subscribeOnKey(key, handler);
|
|
1403
|
+
}
|
|
1404
|
+
subscribeOnKeys(keys, handler) {
|
|
1405
|
+
return this.updateEmitter.subscribeOnKeys(keys, handler);
|
|
1406
|
+
}
|
|
1407
|
+
unsubscribeFromKey(key, handler) {
|
|
1408
|
+
this.updateEmitter.unsubscribeFromKey(key, handler);
|
|
1409
|
+
}
|
|
1410
|
+
unsubscribeFromKeys(keys, handler) {
|
|
1411
|
+
this.updateEmitter.unsubscribeFromKeys(keys, handler);
|
|
1412
|
+
}
|
|
1413
|
+
hasSubscriptions() {
|
|
1414
|
+
return this.updateEmitter.hasSubscriptions();
|
|
1415
|
+
}
|
|
1416
|
+
getHandlerCount(key) {
|
|
1417
|
+
return this.updateEmitter.getHandlerCount(key);
|
|
1418
|
+
}
|
|
1419
|
+
getMetrics() {
|
|
1420
|
+
return this.updateEmitter.getMetrics();
|
|
1421
|
+
}
|
|
1324
1422
|
destroy() {
|
|
1325
|
-
this.
|
|
1326
|
-
this.coalescer.destroy();
|
|
1423
|
+
this.updateEmitter.destroy();
|
|
1327
1424
|
super.destroy();
|
|
1328
1425
|
}
|
|
1329
1426
|
};
|
|
1330
1427
|
|
|
1428
|
+
// src/core/OIMIndexManualSetBased.ts
|
|
1429
|
+
var OIMIndexManualSetBased = class extends OIMIndexSetBased {
|
|
1430
|
+
constructor(options = {}) {
|
|
1431
|
+
super(options);
|
|
1432
|
+
}
|
|
1433
|
+
/**
|
|
1434
|
+
* Set primary keys for a specific index key, replacing any existing values.
|
|
1435
|
+
* Uses optional comparator to skip updates if PKs haven't actually changed.
|
|
1436
|
+
*/
|
|
1437
|
+
setPks(key, pks) {
|
|
1438
|
+
const hasChanges = this.setPksWithComparison(key, new Set(pks));
|
|
1439
|
+
if (hasChanges) {
|
|
1440
|
+
this.emitUpdateOne(key);
|
|
1441
|
+
}
|
|
1442
|
+
}
|
|
1443
|
+
setSlots(key, slots) {
|
|
1444
|
+
const hasChanges = this.setSlotsWithComparison(key, new Set(slots));
|
|
1445
|
+
if (hasChanges) {
|
|
1446
|
+
this.emitUpdateOne(key);
|
|
1447
|
+
}
|
|
1448
|
+
}
|
|
1449
|
+
/**
|
|
1450
|
+
* Add primary keys to a specific index key
|
|
1451
|
+
*/
|
|
1452
|
+
addPks(key, pks) {
|
|
1453
|
+
if (pks.length === 0) return;
|
|
1454
|
+
let slotsSet = this.store.getOneByKey(key);
|
|
1455
|
+
if (!slotsSet) {
|
|
1456
|
+
slotsSet = /* @__PURE__ */ new Set();
|
|
1457
|
+
this.store.setOneByKey(key, slotsSet);
|
|
1458
|
+
}
|
|
1459
|
+
const pksSet = this.slotsToPks(slotsSet);
|
|
1460
|
+
let hasChanges = false;
|
|
1461
|
+
for (const pk of pks) {
|
|
1462
|
+
if (!pksSet.has(pk)) {
|
|
1463
|
+
pksSet.add(pk);
|
|
1464
|
+
slotsSet.add(this.getOrCreateSlot(pk));
|
|
1465
|
+
hasChanges = true;
|
|
1466
|
+
}
|
|
1467
|
+
}
|
|
1468
|
+
if (hasChanges) {
|
|
1469
|
+
this.store.setOneByKey(key, slotsSet);
|
|
1470
|
+
this.emitUpdateOne(key);
|
|
1471
|
+
}
|
|
1472
|
+
}
|
|
1473
|
+
/**
|
|
1474
|
+
* Remove primary keys from a specific index key
|
|
1475
|
+
*/
|
|
1476
|
+
removePks(key, pks) {
|
|
1477
|
+
if (pks.length === 0) return;
|
|
1478
|
+
const slotsSet = this.store.getOneByKey(key);
|
|
1479
|
+
if (!slotsSet) return;
|
|
1480
|
+
let hasChanges = false;
|
|
1481
|
+
const pksToRemove = new Set(pks);
|
|
1482
|
+
for (const slot of Array.from(slotsSet)) {
|
|
1483
|
+
if (pksToRemove.has(slot.pk) && slotsSet.delete(slot)) {
|
|
1484
|
+
hasChanges = true;
|
|
1485
|
+
}
|
|
1486
|
+
}
|
|
1487
|
+
if (slotsSet.size === 0) {
|
|
1488
|
+
this.store.removeOneByKey(key);
|
|
1489
|
+
hasChanges = true;
|
|
1490
|
+
} else if (hasChanges) {
|
|
1491
|
+
this.store.setOneByKey(key, slotsSet);
|
|
1492
|
+
}
|
|
1493
|
+
if (hasChanges) {
|
|
1494
|
+
this.emitUpdateOne(key);
|
|
1495
|
+
}
|
|
1496
|
+
}
|
|
1497
|
+
/**
|
|
1498
|
+
* Clear all primary keys for a specific index key, or all keys if no key specified
|
|
1499
|
+
*/
|
|
1500
|
+
clear(key) {
|
|
1501
|
+
if (key === void 0) {
|
|
1502
|
+
const allKeys = this.store.getAllKeys();
|
|
1503
|
+
if (allKeys.length > 0) {
|
|
1504
|
+
this.store.clear();
|
|
1505
|
+
this.emitUpdate(allKeys);
|
|
1506
|
+
}
|
|
1507
|
+
} else {
|
|
1508
|
+
if (this.store.getOneByKey(key) !== void 0) {
|
|
1509
|
+
this.store.removeOneByKey(key);
|
|
1510
|
+
this.emitUpdateOne(key);
|
|
1511
|
+
}
|
|
1512
|
+
}
|
|
1513
|
+
}
|
|
1514
|
+
};
|
|
1515
|
+
|
|
1331
1516
|
// src/core/OIMReactiveIndexManualSetBased.ts
|
|
1517
|
+
var OIMIndexManualSetBasedReactive = class extends OIMIndexManualSetBased {
|
|
1518
|
+
constructor(updateEmitter, opts) {
|
|
1519
|
+
super(opts);
|
|
1520
|
+
this.updateEmitter = updateEmitter;
|
|
1521
|
+
}
|
|
1522
|
+
emitUpdate(keys) {
|
|
1523
|
+
this.updateEmitter.markUpdatedKeys(keys);
|
|
1524
|
+
}
|
|
1525
|
+
emitUpdateOne(key) {
|
|
1526
|
+
this.updateEmitter.markUpdatedKey(key);
|
|
1527
|
+
}
|
|
1528
|
+
};
|
|
1332
1529
|
var OIMReactiveIndexManualSetBased = class extends OIMReactiveIndexSetBased {
|
|
1333
1530
|
constructor(queue, opts) {
|
|
1334
|
-
super(queue,
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1531
|
+
super(queue, (updateEmitter) => {
|
|
1532
|
+
return new OIMIndexManualSetBasedReactive(
|
|
1533
|
+
updateEmitter,
|
|
1534
|
+
opts?.indexOptions
|
|
1535
|
+
);
|
|
1536
|
+
});
|
|
1338
1537
|
}
|
|
1339
1538
|
setPks(key, pks) {
|
|
1340
1539
|
this.index.setPks(key, pks);
|
|
1341
1540
|
}
|
|
1541
|
+
setSlots(key, slots) {
|
|
1542
|
+
this.index.setSlots(key, slots);
|
|
1543
|
+
}
|
|
1342
1544
|
addPks(key, pks) {
|
|
1343
1545
|
this.index.addPks(key, pks);
|
|
1344
1546
|
}
|
|
@@ -1362,7 +1564,13 @@ var OIMIndexManualArrayBased = class extends OIMIndexArrayBased {
|
|
|
1362
1564
|
setPks(key, pks) {
|
|
1363
1565
|
const hasChanges = this.setPksWithComparison(key, pks);
|
|
1364
1566
|
if (hasChanges) {
|
|
1365
|
-
this.
|
|
1567
|
+
this.emitUpdateOne(key);
|
|
1568
|
+
}
|
|
1569
|
+
}
|
|
1570
|
+
setSlots(key, slots) {
|
|
1571
|
+
const hasChanges = this.setSlotsWithComparison(key, slots);
|
|
1572
|
+
if (hasChanges) {
|
|
1573
|
+
this.emitUpdateOne(key);
|
|
1366
1574
|
}
|
|
1367
1575
|
}
|
|
1368
1576
|
/**
|
|
@@ -1370,22 +1578,24 @@ var OIMIndexManualArrayBased = class extends OIMIndexArrayBased {
|
|
|
1370
1578
|
*/
|
|
1371
1579
|
addPks(key, pks) {
|
|
1372
1580
|
if (pks.length === 0) return;
|
|
1373
|
-
let
|
|
1374
|
-
if (!
|
|
1375
|
-
|
|
1376
|
-
this.store.setOneByKey(key,
|
|
1581
|
+
let slotsArray = this.store.getOneByKey(key);
|
|
1582
|
+
if (!slotsArray) {
|
|
1583
|
+
slotsArray = [];
|
|
1584
|
+
this.store.setOneByKey(key, slotsArray);
|
|
1377
1585
|
}
|
|
1378
|
-
const pksSet = new Set(
|
|
1586
|
+
const pksSet = new Set(slotsArray.map((slot) => slot.pk));
|
|
1379
1587
|
let hasChanges = false;
|
|
1588
|
+
const nextSlots = slotsArray.slice();
|
|
1380
1589
|
for (const pk of pks) {
|
|
1381
1590
|
if (!pksSet.has(pk)) {
|
|
1382
1591
|
pksSet.add(pk);
|
|
1592
|
+
nextSlots.push(this.getOrCreateSlot(pk));
|
|
1383
1593
|
hasChanges = true;
|
|
1384
1594
|
}
|
|
1385
1595
|
}
|
|
1386
1596
|
if (hasChanges) {
|
|
1387
|
-
this.store.setOneByKey(key,
|
|
1388
|
-
this.
|
|
1597
|
+
this.store.setOneByKey(key, nextSlots);
|
|
1598
|
+
this.emitUpdateOne(key);
|
|
1389
1599
|
}
|
|
1390
1600
|
}
|
|
1391
1601
|
/**
|
|
@@ -1393,18 +1603,18 @@ var OIMIndexManualArrayBased = class extends OIMIndexArrayBased {
|
|
|
1393
1603
|
*/
|
|
1394
1604
|
removePks(key, pks) {
|
|
1395
1605
|
if (pks.length === 0) return;
|
|
1396
|
-
const
|
|
1397
|
-
if (!
|
|
1606
|
+
const slotsArray = this.store.getOneByKey(key);
|
|
1607
|
+
if (!slotsArray) return;
|
|
1398
1608
|
const pksSet = new Set(pks);
|
|
1399
|
-
const filtered =
|
|
1400
|
-
const hasChanges = filtered.length !==
|
|
1609
|
+
const filtered = slotsArray.filter((slot) => !pksSet.has(slot.pk));
|
|
1610
|
+
const hasChanges = filtered.length !== slotsArray.length;
|
|
1401
1611
|
if (hasChanges) {
|
|
1402
1612
|
if (filtered.length === 0) {
|
|
1403
1613
|
this.store.removeOneByKey(key);
|
|
1404
1614
|
} else {
|
|
1405
1615
|
this.store.setOneByKey(key, filtered);
|
|
1406
1616
|
}
|
|
1407
|
-
this.
|
|
1617
|
+
this.emitUpdateOne(key);
|
|
1408
1618
|
}
|
|
1409
1619
|
}
|
|
1410
1620
|
/**
|
|
@@ -1420,23 +1630,40 @@ var OIMIndexManualArrayBased = class extends OIMIndexArrayBased {
|
|
|
1420
1630
|
} else {
|
|
1421
1631
|
if (this.store.getOneByKey(key) !== void 0) {
|
|
1422
1632
|
this.store.removeOneByKey(key);
|
|
1423
|
-
this.
|
|
1633
|
+
this.emitUpdateOne(key);
|
|
1424
1634
|
}
|
|
1425
1635
|
}
|
|
1426
1636
|
}
|
|
1427
1637
|
};
|
|
1428
1638
|
|
|
1429
1639
|
// src/core/OIMReactiveIndexManualArrayBased.ts
|
|
1640
|
+
var OIMIndexManualArrayBasedReactive = class extends OIMIndexManualArrayBased {
|
|
1641
|
+
constructor(updateEmitter, opts) {
|
|
1642
|
+
super(opts);
|
|
1643
|
+
this.updateEmitter = updateEmitter;
|
|
1644
|
+
}
|
|
1645
|
+
emitUpdate(keys) {
|
|
1646
|
+
this.updateEmitter.markUpdatedKeys(keys);
|
|
1647
|
+
}
|
|
1648
|
+
emitUpdateOne(key) {
|
|
1649
|
+
this.updateEmitter.markUpdatedKey(key);
|
|
1650
|
+
}
|
|
1651
|
+
};
|
|
1430
1652
|
var OIMReactiveIndexManualArrayBased = class extends OIMReactiveIndexArrayBased {
|
|
1431
1653
|
constructor(queue, opts) {
|
|
1432
|
-
super(queue,
|
|
1433
|
-
|
|
1434
|
-
|
|
1435
|
-
|
|
1654
|
+
super(queue, (updateEmitter) => {
|
|
1655
|
+
return new OIMIndexManualArrayBasedReactive(
|
|
1656
|
+
updateEmitter,
|
|
1657
|
+
opts?.indexOptions
|
|
1658
|
+
);
|
|
1659
|
+
});
|
|
1436
1660
|
}
|
|
1437
1661
|
setPks(key, pks) {
|
|
1438
1662
|
this.index.setPks(key, pks);
|
|
1439
1663
|
}
|
|
1664
|
+
setSlots(key, slots) {
|
|
1665
|
+
this.index.setSlots(key, slots);
|
|
1666
|
+
}
|
|
1440
1667
|
addPks(key, pks) {
|
|
1441
1668
|
this.index.addPks(key, pks);
|
|
1442
1669
|
}
|
|
@@ -1453,6 +1680,10 @@ var OIMRICollection = class extends OIMReactiveCollection {
|
|
|
1453
1680
|
constructor(queue, opts) {
|
|
1454
1681
|
super(queue, opts.collectionOpts);
|
|
1455
1682
|
this.indexes = opts.indexes || {};
|
|
1683
|
+
const indexes = Object.values(this.indexes);
|
|
1684
|
+
for (const index of indexes) {
|
|
1685
|
+
index.index.setSlotResolver((pk) => this.getSlotByPk(pk));
|
|
1686
|
+
}
|
|
1456
1687
|
}
|
|
1457
1688
|
};
|
|
1458
1689
|
|
|
@@ -1521,20 +1752,12 @@ var OIMComparatorFactory = class {
|
|
|
1521
1752
|
}
|
|
1522
1753
|
};
|
|
1523
1754
|
|
|
1524
|
-
// src/enum/EOIMEventQueueEventType.ts
|
|
1525
|
-
var EOIMEventQueueEventType = /* @__PURE__ */ ((EOIMEventQueueEventType2) => {
|
|
1526
|
-
EOIMEventQueueEventType2[EOIMEventQueueEventType2["AFTER_FLUSH"] = 0] = "AFTER_FLUSH";
|
|
1527
|
-
EOIMEventQueueEventType2[EOIMEventQueueEventType2["BEFORE_FLUSH"] = 1] = "BEFORE_FLUSH";
|
|
1528
|
-
return EOIMEventQueueEventType2;
|
|
1529
|
-
})(EOIMEventQueueEventType || {});
|
|
1530
|
-
|
|
1531
1755
|
// src/core/OIMEventQueue.ts
|
|
1532
1756
|
var OIMEventQueue = class {
|
|
1533
1757
|
constructor(options = {}) {
|
|
1534
1758
|
this.emitter = new OIMEventEmitter();
|
|
1535
|
-
this.
|
|
1759
|
+
this.tasks = /* @__PURE__ */ new Set();
|
|
1536
1760
|
this.isFlushing = false;
|
|
1537
|
-
this.pendingSchedule = false;
|
|
1538
1761
|
this.scheduler = options.scheduler;
|
|
1539
1762
|
if (this.scheduler) {
|
|
1540
1763
|
this.flushBound = () => this.flush();
|
|
@@ -1545,62 +1768,76 @@ var OIMEventQueue = class {
|
|
|
1545
1768
|
}
|
|
1546
1769
|
}
|
|
1547
1770
|
/**
|
|
1548
|
-
*
|
|
1549
|
-
*
|
|
1771
|
+
* Enqueue a one-shot task to be executed on the next flush.
|
|
1772
|
+
* Returns a dequeue function that can be called to cancel the task before it runs.
|
|
1550
1773
|
*/
|
|
1551
1774
|
enqueue(fn) {
|
|
1552
|
-
|
|
1553
|
-
|
|
1554
|
-
|
|
1555
|
-
|
|
1556
|
-
|
|
1557
|
-
|
|
1558
|
-
|
|
1559
|
-
|
|
1560
|
-
|
|
1775
|
+
let isActive = true;
|
|
1776
|
+
const task = () => {
|
|
1777
|
+
if (!isActive) return;
|
|
1778
|
+
fn();
|
|
1779
|
+
};
|
|
1780
|
+
this.tasks.add(task);
|
|
1781
|
+
this.ensureScheduled();
|
|
1782
|
+
return () => {
|
|
1783
|
+
if (!isActive) return;
|
|
1784
|
+
isActive = false;
|
|
1785
|
+
this.tasks.delete(task);
|
|
1786
|
+
};
|
|
1787
|
+
}
|
|
1788
|
+
get isInFlush() {
|
|
1789
|
+
return this.isFlushing;
|
|
1561
1790
|
}
|
|
1562
1791
|
/**
|
|
1563
|
-
*
|
|
1564
|
-
* This method is safe to call multiple times and handles reentrancy.
|
|
1792
|
+
* Dequeue (cancel) a previously enqueued task by its dequeue function.
|
|
1565
1793
|
*/
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
|
|
1794
|
+
dequeue(dequeueFn) {
|
|
1795
|
+
dequeueFn();
|
|
1796
|
+
}
|
|
1797
|
+
/**
|
|
1798
|
+
* Execute all pending tasks.
|
|
1799
|
+
*
|
|
1800
|
+
* This flush drains until the queue is empty. If tasks enqueue more tasks, they will be
|
|
1801
|
+
* executed within the same flush.
|
|
1802
|
+
*/
|
|
1803
|
+
flush() {
|
|
1804
|
+
this.scheduler?.cancel();
|
|
1569
1805
|
this.isFlushing = true;
|
|
1570
1806
|
this.emitter.emit(1 /* BEFORE_FLUSH */, void 0);
|
|
1571
|
-
const
|
|
1572
|
-
this.
|
|
1573
|
-
for (let i = 0; i <
|
|
1574
|
-
|
|
1807
|
+
const snapshot = Array.from(this.tasks);
|
|
1808
|
+
this.tasks.clear();
|
|
1809
|
+
for (let i = 0; i < snapshot.length; i++) {
|
|
1810
|
+
snapshot[i]();
|
|
1575
1811
|
}
|
|
1576
|
-
this.emitter.emit(0 /* AFTER_FLUSH */, void 0);
|
|
1577
1812
|
this.isFlushing = false;
|
|
1578
|
-
|
|
1579
|
-
this.pendingSchedule = false;
|
|
1580
|
-
this.scheduler.schedule();
|
|
1581
|
-
} else {
|
|
1582
|
-
this.pendingSchedule = false;
|
|
1583
|
-
}
|
|
1813
|
+
this.emitter.emit(0 /* AFTER_FLUSH */, void 0);
|
|
1584
1814
|
}
|
|
1585
1815
|
/**
|
|
1586
1816
|
* Get the current number of queued functions.
|
|
1587
1817
|
*/
|
|
1588
1818
|
get length() {
|
|
1589
|
-
return this.
|
|
1819
|
+
return this.tasks.size;
|
|
1590
1820
|
}
|
|
1591
1821
|
/**
|
|
1592
1822
|
* Check if the queue is empty.
|
|
1593
1823
|
*/
|
|
1594
1824
|
get isEmpty() {
|
|
1595
|
-
return this.
|
|
1825
|
+
return this.tasks.size === 0;
|
|
1596
1826
|
}
|
|
1597
1827
|
/**
|
|
1598
1828
|
* Clear the queue without executing functions and cancel any scheduled flush.
|
|
1599
1829
|
*/
|
|
1600
1830
|
clear() {
|
|
1601
|
-
this.
|
|
1831
|
+
this.tasks.clear();
|
|
1602
1832
|
this.scheduler?.cancel();
|
|
1603
1833
|
}
|
|
1834
|
+
ensureScheduled() {
|
|
1835
|
+
if (!this.scheduler) return;
|
|
1836
|
+
if (this.isFlushing) return;
|
|
1837
|
+
if (this.tasks.size === 1) {
|
|
1838
|
+
this.scheduler.schedule();
|
|
1839
|
+
}
|
|
1840
|
+
}
|
|
1604
1841
|
/**
|
|
1605
1842
|
* Clean up scheduler subscription when queue is no longer needed.
|
|
1606
1843
|
*/
|
|
@@ -1714,56 +1951,75 @@ var OIMMap2Keys = class {
|
|
|
1714
1951
|
}
|
|
1715
1952
|
};
|
|
1716
1953
|
|
|
1717
|
-
// src/modules/wrapper/OIMUpdateEventCoalescerManual.ts
|
|
1718
|
-
var OIMUpdateEventCoalescerManual = class extends OIMUpdateEventCoalescer {
|
|
1719
|
-
markUpdatedKeys(keys) {
|
|
1720
|
-
if (keys.length === 0) return;
|
|
1721
|
-
this.addUpdatedKeys(keys);
|
|
1722
|
-
}
|
|
1723
|
-
destroy() {
|
|
1724
|
-
this.emitter.offAll();
|
|
1725
|
-
this.updatedKeysIndex.destroy();
|
|
1726
|
-
this.flushingUpdatedKeysIndex.destroy();
|
|
1727
|
-
}
|
|
1728
|
-
};
|
|
1729
|
-
|
|
1730
1954
|
// src/modules/wrapper/collection/OIMCollectionChangedFieldsWrapper.ts
|
|
1731
1955
|
var OIMCollectionChangedFieldsWrapper = class {
|
|
1732
1956
|
constructor(queue, collection, opts) {
|
|
1957
|
+
this.isInWrite = false;
|
|
1958
|
+
this.lastEntitySnapshotByPk = /* @__PURE__ */ new Map();
|
|
1733
1959
|
this.changedFieldsByPk = /* @__PURE__ */ new Map();
|
|
1734
1960
|
this.changedPksByField = /* @__PURE__ */ new Map();
|
|
1961
|
+
this.onAfterFlush = () => {
|
|
1962
|
+
this.clear();
|
|
1963
|
+
};
|
|
1964
|
+
this.onCollectionUpdate = (payload) => {
|
|
1965
|
+
if (this.isInWrite) return;
|
|
1966
|
+
if (payload.pks.length === 0) return;
|
|
1967
|
+
for (let i = 0; i < payload.pks.length; i++) {
|
|
1968
|
+
const pk = payload.pks[i];
|
|
1969
|
+
this.trackExternalMutationByPk(pk);
|
|
1970
|
+
}
|
|
1971
|
+
};
|
|
1735
1972
|
this.collection = collection;
|
|
1736
1973
|
this.selectPk = opts?.selectPk ?? (() => {
|
|
1737
1974
|
throw new Error(
|
|
1738
1975
|
`[OIMCollectionChangedFieldsWrapper]: selectPk was not provided. Use upsertOneByPk(...) or pass opts.selectPk.`
|
|
1739
1976
|
);
|
|
1740
1977
|
});
|
|
1741
|
-
this.
|
|
1742
|
-
|
|
1743
|
-
|
|
1744
|
-
|
|
1745
|
-
|
|
1746
|
-
this.
|
|
1747
|
-
|
|
1748
|
-
|
|
1749
|
-
|
|
1750
|
-
|
|
1978
|
+
this.changedPksEventEmitter = new OIMUpdateEventEmitter(
|
|
1979
|
+
queue,
|
|
1980
|
+
"after_flush"
|
|
1981
|
+
);
|
|
1982
|
+
this.changedFieldsEventEmitter = new OIMUpdateEventEmitter(queue, "after_flush");
|
|
1983
|
+
this.unsubscribeAfterFlush = queue.emitter.on(
|
|
1984
|
+
0 /* AFTER_FLUSH */,
|
|
1985
|
+
this.onAfterFlush
|
|
1986
|
+
);
|
|
1987
|
+
const maybeReactive = collection;
|
|
1988
|
+
this.unsubscribeFromCollectionEmitter = maybeReactive.subscribeOnAnyUpdate ? maybeReactive.subscribeOnAnyUpdate((pks) => {
|
|
1989
|
+
this.onCollectionUpdate({
|
|
1990
|
+
pks
|
|
1991
|
+
});
|
|
1992
|
+
}) : collection.emitter.on(
|
|
1993
|
+
0 /* UPDATE */,
|
|
1994
|
+
this.onCollectionUpdate
|
|
1995
|
+
);
|
|
1751
1996
|
}
|
|
1752
1997
|
upsertOneByPk(pk, patch) {
|
|
1753
|
-
this.
|
|
1754
|
-
|
|
1998
|
+
this.withWrite(() => {
|
|
1999
|
+
this.trackPatch(pk, patch);
|
|
2000
|
+
this.collection.upsertOneByPk(pk, patch);
|
|
2001
|
+
});
|
|
2002
|
+
this.updateEntitySnapshot(pk);
|
|
1755
2003
|
}
|
|
1756
2004
|
upsertOne(entity) {
|
|
1757
|
-
|
|
1758
|
-
this.trackPatch(pk, entity);
|
|
1759
|
-
this.collection.upsertOne(entity);
|
|
1760
|
-
}
|
|
1761
|
-
upsertMany(entities) {
|
|
1762
|
-
for (const entity of entities) {
|
|
2005
|
+
this.withWrite(() => {
|
|
1763
2006
|
const pk = this.selectPk(entity);
|
|
1764
2007
|
this.trackPatch(pk, entity);
|
|
1765
|
-
|
|
1766
|
-
|
|
2008
|
+
this.collection.upsertOne(entity);
|
|
2009
|
+
});
|
|
2010
|
+
this.updateEntitySnapshot(this.selectPk(entity));
|
|
2011
|
+
}
|
|
2012
|
+
upsertMany(entities) {
|
|
2013
|
+
const pks = [];
|
|
2014
|
+
this.withWrite(() => {
|
|
2015
|
+
for (const entity of entities) {
|
|
2016
|
+
const pk = this.selectPk(entity);
|
|
2017
|
+
pks.push(pk);
|
|
2018
|
+
this.trackPatch(pk, entity);
|
|
2019
|
+
}
|
|
2020
|
+
this.collection.upsertMany(entities);
|
|
2021
|
+
});
|
|
2022
|
+
for (let i = 0; i < pks.length; i++) this.updateEntitySnapshot(pks[i]);
|
|
1767
2023
|
}
|
|
1768
2024
|
getChangedFieldsByPk(pk) {
|
|
1769
2025
|
return this.changedFieldsByPk.get(pk) ?? /* @__PURE__ */ new Set();
|
|
@@ -1771,8 +2027,7 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
1771
2027
|
consumeChangedFieldsByPk(pk) {
|
|
1772
2028
|
const existing = this.changedFieldsByPk.get(pk);
|
|
1773
2029
|
if (!existing) return /* @__PURE__ */ new Set();
|
|
1774
|
-
|
|
1775
|
-
return existing;
|
|
2030
|
+
return new Set(existing);
|
|
1776
2031
|
}
|
|
1777
2032
|
getChangedPksByField(field) {
|
|
1778
2033
|
return this.changedPksByField.get(field) ?? /* @__PURE__ */ new Set();
|
|
@@ -1780,8 +2035,7 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
1780
2035
|
consumeChangedPksByField(field) {
|
|
1781
2036
|
const existing = this.changedPksByField.get(field);
|
|
1782
2037
|
if (!existing) return /* @__PURE__ */ new Set();
|
|
1783
|
-
|
|
1784
|
-
return existing;
|
|
2038
|
+
return new Set(existing);
|
|
1785
2039
|
}
|
|
1786
2040
|
clear() {
|
|
1787
2041
|
this.changedFieldsByPk.clear();
|
|
@@ -1790,18 +2044,60 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
1790
2044
|
destroy() {
|
|
1791
2045
|
this.changedPksEventEmitter.destroy();
|
|
1792
2046
|
this.changedFieldsEventEmitter.destroy();
|
|
1793
|
-
this.
|
|
1794
|
-
this.
|
|
2047
|
+
this.unsubscribeAfterFlush();
|
|
2048
|
+
this.unsubscribeFromCollectionEmitter();
|
|
1795
2049
|
this.clear();
|
|
1796
2050
|
}
|
|
1797
|
-
|
|
1798
|
-
if (
|
|
1799
|
-
|
|
1800
|
-
|
|
1801
|
-
);
|
|
2051
|
+
withWrite(fn) {
|
|
2052
|
+
if (this.isInWrite) {
|
|
2053
|
+
fn();
|
|
2054
|
+
return;
|
|
1802
2055
|
}
|
|
1803
|
-
|
|
1804
|
-
|
|
2056
|
+
this.isInWrite = true;
|
|
2057
|
+
try {
|
|
2058
|
+
fn();
|
|
2059
|
+
} finally {
|
|
2060
|
+
this.isInWrite = false;
|
|
2061
|
+
}
|
|
2062
|
+
}
|
|
2063
|
+
trackExternalMutationByPk(pk) {
|
|
2064
|
+
const prev = this.lastEntitySnapshotByPk.get(pk);
|
|
2065
|
+
const next = this.collection.getOneByPk(pk);
|
|
2066
|
+
const changedKeys = this.diffChangedKeys(prev, next);
|
|
2067
|
+
this.updateEntitySnapshot(pk);
|
|
2068
|
+
if (changedKeys.length > 0) {
|
|
2069
|
+
this.trackChangedKeys(pk, changedKeys);
|
|
2070
|
+
} else {
|
|
2071
|
+
this.changedPksEventEmitter.markUpdatedKeys([pk]);
|
|
2072
|
+
}
|
|
2073
|
+
}
|
|
2074
|
+
diffChangedKeys(prev, next) {
|
|
2075
|
+
if (!prev && !next) return [];
|
|
2076
|
+
if (!prev && next) return Object.keys(next);
|
|
2077
|
+
if (prev && !next) return Object.keys(prev);
|
|
2078
|
+
const prevObj = prev;
|
|
2079
|
+
const nextObj = next;
|
|
2080
|
+
const keys = /* @__PURE__ */ new Set();
|
|
2081
|
+
Object.keys(prevObj).forEach((k) => keys.add(k));
|
|
2082
|
+
Object.keys(nextObj).forEach((k) => keys.add(k));
|
|
2083
|
+
const changed = [];
|
|
2084
|
+
keys.forEach((k) => {
|
|
2085
|
+
if (prevObj[k] !== nextObj[k])
|
|
2086
|
+
changed.push(k);
|
|
2087
|
+
});
|
|
2088
|
+
return changed;
|
|
2089
|
+
}
|
|
2090
|
+
updateEntitySnapshot(pk) {
|
|
2091
|
+
const entity = this.collection.getOneByPk(pk);
|
|
2092
|
+
if (!entity) {
|
|
2093
|
+
this.lastEntitySnapshotByPk.delete(pk);
|
|
2094
|
+
return;
|
|
2095
|
+
}
|
|
2096
|
+
this.lastEntitySnapshotByPk.set(pk, {
|
|
2097
|
+
...entity
|
|
2098
|
+
});
|
|
2099
|
+
}
|
|
2100
|
+
trackChangedKeys(pk, keys) {
|
|
1805
2101
|
let pkFields = this.changedFieldsByPk.get(pk);
|
|
1806
2102
|
if (!pkFields) {
|
|
1807
2103
|
pkFields = /* @__PURE__ */ new Set();
|
|
@@ -1816,8 +2112,18 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
1816
2112
|
}
|
|
1817
2113
|
fieldPks.add(pk);
|
|
1818
2114
|
}
|
|
1819
|
-
this.
|
|
1820
|
-
this.
|
|
2115
|
+
this.changedPksEventEmitter.markUpdatedKeys([pk]);
|
|
2116
|
+
this.changedFieldsEventEmitter.markUpdatedKeys(keys);
|
|
2117
|
+
}
|
|
2118
|
+
trackPatch(pk, patch) {
|
|
2119
|
+
if (pk === void 0 || pk === null || pk === "") {
|
|
2120
|
+
throw new Error(
|
|
2121
|
+
`[OIMCollectionChangedFieldsWrapper]: PK is required to track changes.`
|
|
2122
|
+
);
|
|
2123
|
+
}
|
|
2124
|
+
const keys = Object.keys(patch);
|
|
2125
|
+
if (keys.length === 0) return;
|
|
2126
|
+
this.trackChangedKeys(pk, keys);
|
|
1821
2127
|
}
|
|
1822
2128
|
};
|
|
1823
2129
|
|
|
@@ -1840,14 +2146,14 @@ var OIMIndexManualOrderedArrayBased = class extends OIMIndexArrayBased {
|
|
|
1840
2146
|
push(key, itemKey) {
|
|
1841
2147
|
const list = this.getOrCreateList(key);
|
|
1842
2148
|
const index = list.length;
|
|
1843
|
-
list.push(itemKey);
|
|
2149
|
+
list.push(this.getOrCreateSlot(itemKey));
|
|
1844
2150
|
this.emitUpdate([key]);
|
|
1845
2151
|
return index;
|
|
1846
2152
|
}
|
|
1847
2153
|
insertAt(key, index, itemKey) {
|
|
1848
2154
|
const list = this.getOrCreateList(key);
|
|
1849
2155
|
const safeIndex = Math.max(0, Math.min(index, list.length));
|
|
1850
|
-
list.splice(safeIndex, 0, itemKey);
|
|
2156
|
+
list.splice(safeIndex, 0, this.getOrCreateSlot(itemKey));
|
|
1851
2157
|
this.emitUpdate([key]);
|
|
1852
2158
|
}
|
|
1853
2159
|
removeAt(key, index) {
|
|
@@ -1859,19 +2165,19 @@ var OIMIndexManualOrderedArrayBased = class extends OIMIndexArrayBased {
|
|
|
1859
2165
|
this.store.removeOneByKey(key);
|
|
1860
2166
|
}
|
|
1861
2167
|
this.emitUpdate([key]);
|
|
1862
|
-
return removed;
|
|
2168
|
+
return removed?.pk;
|
|
1863
2169
|
}
|
|
1864
2170
|
move(key, fromIndex, toIndex) {
|
|
1865
2171
|
const list = this.store.getOneByKey(key);
|
|
1866
2172
|
if (!list) return void 0;
|
|
1867
2173
|
if (fromIndex < 0 || fromIndex >= list.length) return void 0;
|
|
1868
2174
|
if (toIndex < 0 || toIndex >= list.length) return void 0;
|
|
1869
|
-
if (fromIndex === toIndex) return list[fromIndex];
|
|
2175
|
+
if (fromIndex === toIndex) return list[fromIndex]?.pk;
|
|
1870
2176
|
const [itemKey] = list.splice(fromIndex, 1);
|
|
1871
2177
|
if (itemKey === void 0) return void 0;
|
|
1872
2178
|
list.splice(toIndex, 0, itemKey);
|
|
1873
2179
|
this.emitUpdate([key]);
|
|
1874
|
-
return itemKey;
|
|
2180
|
+
return itemKey.pk;
|
|
1875
2181
|
}
|
|
1876
2182
|
reset(key, itemKeys) {
|
|
1877
2183
|
if (itemKeys.length === 0) {
|
|
@@ -1881,7 +2187,7 @@ var OIMIndexManualOrderedArrayBased = class extends OIMIndexArrayBased {
|
|
|
1881
2187
|
}
|
|
1882
2188
|
return;
|
|
1883
2189
|
}
|
|
1884
|
-
this.store.setOneByKey(key,
|
|
2190
|
+
this.store.setOneByKey(key, this.resolveSlots(itemKeys));
|
|
1885
2191
|
this.emitUpdate([key]);
|
|
1886
2192
|
}
|
|
1887
2193
|
getOrCreateList(key) {
|
|
@@ -1897,13 +2203,33 @@ var OIMIndexManualOrderedArrayBased = class extends OIMIndexArrayBased {
|
|
|
1897
2203
|
// src/modules/wrapper/index/OIMOrderedListIndexCommandStreamWrapper.ts
|
|
1898
2204
|
var OIMOrderedListIndexCommandStreamWrapper = class {
|
|
1899
2205
|
constructor(queue, index) {
|
|
2206
|
+
this.isInWrite = false;
|
|
1900
2207
|
this.commandsByKey = /* @__PURE__ */ new Map();
|
|
1901
|
-
this.
|
|
1902
|
-
|
|
1903
|
-
|
|
1904
|
-
|
|
1905
|
-
|
|
2208
|
+
this.onAfterFlush = () => {
|
|
2209
|
+
this.commandsByKey.clear();
|
|
2210
|
+
};
|
|
2211
|
+
this.onIndexUpdate = (payload) => {
|
|
2212
|
+
if (this.isInWrite) return;
|
|
2213
|
+
if (payload.keys.length === 0) return;
|
|
2214
|
+
for (let i = 0; i < payload.keys.length; i++) {
|
|
2215
|
+
const key = payload.keys[i];
|
|
2216
|
+
const list = this.index.getPksByKey(key);
|
|
2217
|
+
this.appendCommand(key, { type: "set", keys: Array.from(list) });
|
|
2218
|
+
}
|
|
2219
|
+
};
|
|
2220
|
+
this.commandsEventEmitter = new OIMUpdateEventEmitter(
|
|
2221
|
+
queue,
|
|
2222
|
+
"after_flush"
|
|
2223
|
+
);
|
|
1906
2224
|
this.index = index ?? new OIMIndexManualOrderedArrayBased();
|
|
2225
|
+
this.unsubscribeAfterFlush = queue.emitter.on(
|
|
2226
|
+
0 /* AFTER_FLUSH */,
|
|
2227
|
+
this.onAfterFlush
|
|
2228
|
+
);
|
|
2229
|
+
this.unsubscribeFromIndexEmitter = this.index.emitter.on(
|
|
2230
|
+
0 /* UPDATE */,
|
|
2231
|
+
this.onIndexUpdate
|
|
2232
|
+
);
|
|
1907
2233
|
}
|
|
1908
2234
|
getPksByKey(key) {
|
|
1909
2235
|
return this.index.getPksByKey(key);
|
|
@@ -1915,27 +2241,35 @@ var OIMOrderedListIndexCommandStreamWrapper = class {
|
|
|
1915
2241
|
return this.index.getKeys();
|
|
1916
2242
|
}
|
|
1917
2243
|
push(key, itemKey) {
|
|
1918
|
-
|
|
1919
|
-
|
|
2244
|
+
this.withWrite(() => {
|
|
2245
|
+
const index = this.index.push(key, itemKey);
|
|
2246
|
+
this.appendCommand(key, { type: "add", key: itemKey, index });
|
|
2247
|
+
});
|
|
1920
2248
|
}
|
|
1921
2249
|
removeAt(key, index) {
|
|
1922
|
-
|
|
1923
|
-
|
|
1924
|
-
|
|
2250
|
+
this.withWrite(() => {
|
|
2251
|
+
const itemKey = this.index.removeAt(key, index);
|
|
2252
|
+
if (itemKey === void 0) return;
|
|
2253
|
+
this.appendCommand(key, { type: "remove", key: itemKey, index });
|
|
2254
|
+
});
|
|
1925
2255
|
}
|
|
1926
2256
|
move(key, fromIndex, toIndex) {
|
|
1927
|
-
|
|
1928
|
-
|
|
1929
|
-
|
|
1930
|
-
|
|
1931
|
-
|
|
1932
|
-
|
|
1933
|
-
|
|
2257
|
+
this.withWrite(() => {
|
|
2258
|
+
const itemKey = this.index.move(key, fromIndex, toIndex);
|
|
2259
|
+
if (itemKey === void 0) return;
|
|
2260
|
+
this.appendCommand(key, {
|
|
2261
|
+
type: "move",
|
|
2262
|
+
key: itemKey,
|
|
2263
|
+
fromIndex,
|
|
2264
|
+
toIndex
|
|
2265
|
+
});
|
|
1934
2266
|
});
|
|
1935
2267
|
}
|
|
1936
|
-
|
|
1937
|
-
this.
|
|
1938
|
-
|
|
2268
|
+
set(key, keys) {
|
|
2269
|
+
this.withWrite(() => {
|
|
2270
|
+
this.index.reset(key, keys);
|
|
2271
|
+
this.appendCommand(key, { type: "set", keys });
|
|
2272
|
+
});
|
|
1939
2273
|
}
|
|
1940
2274
|
/**
|
|
1941
2275
|
* Read-only peek at buffered commands without clearing them.
|
|
@@ -1950,8 +2284,7 @@ var OIMOrderedListIndexCommandStreamWrapper = class {
|
|
|
1950
2284
|
consumeCommands(key) {
|
|
1951
2285
|
const cmds = this.commandsByKey.get(key);
|
|
1952
2286
|
if (!cmds || cmds.length === 0) return [];
|
|
1953
|
-
|
|
1954
|
-
return cmds;
|
|
2287
|
+
return cmds.slice();
|
|
1955
2288
|
}
|
|
1956
2289
|
clear(key) {
|
|
1957
2290
|
if (key === void 0) {
|
|
@@ -1964,17 +2297,38 @@ var OIMOrderedListIndexCommandStreamWrapper = class {
|
|
|
1964
2297
|
}
|
|
1965
2298
|
destroy() {
|
|
1966
2299
|
this.commandsEventEmitter.destroy();
|
|
1967
|
-
this.
|
|
2300
|
+
this.unsubscribeAfterFlush();
|
|
2301
|
+
this.unsubscribeFromIndexEmitter();
|
|
1968
2302
|
this.clear();
|
|
1969
2303
|
}
|
|
2304
|
+
withWrite(fn) {
|
|
2305
|
+
if (this.isInWrite) {
|
|
2306
|
+
fn();
|
|
2307
|
+
return;
|
|
2308
|
+
}
|
|
2309
|
+
this.isInWrite = true;
|
|
2310
|
+
try {
|
|
2311
|
+
fn();
|
|
2312
|
+
} finally {
|
|
2313
|
+
this.isInWrite = false;
|
|
2314
|
+
}
|
|
2315
|
+
}
|
|
1970
2316
|
appendCommand(key, cmd) {
|
|
1971
2317
|
let cmds = this.commandsByKey.get(key);
|
|
1972
2318
|
if (!cmds) {
|
|
1973
2319
|
cmds = [];
|
|
1974
2320
|
this.commandsByKey.set(key, cmds);
|
|
1975
2321
|
}
|
|
1976
|
-
|
|
1977
|
-
|
|
2322
|
+
if (cmd.type === "set") {
|
|
2323
|
+
cmds.length = 0;
|
|
2324
|
+
cmds.push(cmd);
|
|
2325
|
+
} else if (cmds.length > 0 && cmds[0].type === "set") {
|
|
2326
|
+
const setCmd = cmds[0];
|
|
2327
|
+
setCmd.keys = Array.from(this.index.getPksByKey(key));
|
|
2328
|
+
} else {
|
|
2329
|
+
cmds.push(cmd);
|
|
2330
|
+
}
|
|
2331
|
+
this.commandsEventEmitter.markUpdatedKeys([key]);
|
|
1978
2332
|
}
|
|
1979
2333
|
};
|
|
1980
2334
|
|
|
@@ -2147,159 +2501,160 @@ var OIMEventQueueSchedulerFactory = class {
|
|
|
2147
2501
|
}
|
|
2148
2502
|
};
|
|
2149
2503
|
|
|
2504
|
+
// src/const/OIMDBSettings.ts
|
|
2505
|
+
var OIMDBSettings = class {
|
|
2506
|
+
};
|
|
2507
|
+
/**
|
|
2508
|
+
* Fixed key used in the manual index to store updated keys set in coalescers.
|
|
2509
|
+
* This constant is exported so users can create their own indexes and pass them to coalescers.
|
|
2510
|
+
*/
|
|
2511
|
+
OIMDBSettings.UPDATED_KEYS_INDEX_KEY = "__updatedKeys__";
|
|
2512
|
+
OIMDBSettings.FLUSHING_KEYS_INDEX_KEY = "__flushingKeys__";
|
|
2513
|
+
|
|
2514
|
+
// src/modules/effect/core/OIMEffectDependencyComputed.ts
|
|
2515
|
+
var OIMEffectDependencyComputed = class {
|
|
2516
|
+
constructor(computed) {
|
|
2517
|
+
this.computed = computed;
|
|
2518
|
+
}
|
|
2519
|
+
subscribe(onUpdate) {
|
|
2520
|
+
return this.computed.emitter.on("update", onUpdate);
|
|
2521
|
+
}
|
|
2522
|
+
};
|
|
2523
|
+
|
|
2150
2524
|
// src/modules/effect/core/OIMEffect.ts
|
|
2151
2525
|
var OIMEffect = class {
|
|
2152
|
-
constructor(
|
|
2153
|
-
this.
|
|
2154
|
-
this.
|
|
2155
|
-
this.
|
|
2156
|
-
this.
|
|
2526
|
+
constructor(runtime, opts) {
|
|
2527
|
+
this.sourceDeps = [];
|
|
2528
|
+
this.computedDeps = [];
|
|
2529
|
+
this.sourceUnsubscribers = [];
|
|
2530
|
+
this.computedUnsubscribers = [];
|
|
2531
|
+
this.isResubscribeEnqueued = false;
|
|
2532
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2157
2533
|
this.isScheduled = false;
|
|
2158
|
-
this.handleQueueBeforeFlush = () => {
|
|
2159
|
-
this.isInFlush = true;
|
|
2160
|
-
this.hasRunInThisFlush = false;
|
|
2161
|
-
};
|
|
2162
|
-
this.handleQueueAfterFlush = () => {
|
|
2163
|
-
this.isInFlush = false;
|
|
2164
|
-
this.hasRunInThisFlush = false;
|
|
2165
|
-
};
|
|
2166
2534
|
this.runTask = () => {
|
|
2167
2535
|
this.isScheduled = false;
|
|
2168
|
-
|
|
2536
|
+
this.dequeueScheduled = void 0;
|
|
2169
2537
|
this.runOnce();
|
|
2170
2538
|
};
|
|
2171
|
-
this.
|
|
2172
|
-
|
|
2173
|
-
this.
|
|
2174
|
-
|
|
2175
|
-
|
|
2176
|
-
this.
|
|
2177
|
-
this.runOnce();
|
|
2178
|
-
return;
|
|
2539
|
+
this.onSourceInvalidate = () => {
|
|
2540
|
+
this.onUpdate?.();
|
|
2541
|
+
if (!this.isTemporarilyUnsubscribedForFlush) {
|
|
2542
|
+
this.isTemporarilyUnsubscribedForFlush = true;
|
|
2543
|
+
this.unsubscribeFromSourceDeps();
|
|
2544
|
+
this.ensureResubscribeAfterFlush();
|
|
2179
2545
|
}
|
|
2180
2546
|
if (this.isScheduled) return;
|
|
2181
2547
|
this.isScheduled = true;
|
|
2182
|
-
this.
|
|
2548
|
+
this.dequeueScheduled = this.runtime.schedule(this.runTask);
|
|
2183
2549
|
};
|
|
2184
|
-
this.
|
|
2185
|
-
|
|
2186
|
-
|
|
2550
|
+
this.onComputedInvalidate = () => {
|
|
2551
|
+
this.onUpdate?.();
|
|
2552
|
+
if (this.isScheduled) return;
|
|
2553
|
+
this.isScheduled = true;
|
|
2554
|
+
this.dequeueScheduled = this.runtime.schedule(this.runTask);
|
|
2555
|
+
};
|
|
2556
|
+
this.onAfterFlush = () => {
|
|
2557
|
+
if (!this.isResubscribeEnqueued) return;
|
|
2558
|
+
this.isResubscribeEnqueued = false;
|
|
2559
|
+
this.dequeueResubscribe = void 0;
|
|
2560
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2561
|
+
if (this.sourceUnsubscribers.length === 0) {
|
|
2562
|
+
for (const dep of this.sourceDeps) {
|
|
2563
|
+
this.sourceUnsubscribers.push(
|
|
2564
|
+
dep.subscribe(this.onSourceInvalidate)
|
|
2565
|
+
);
|
|
2566
|
+
}
|
|
2567
|
+
}
|
|
2568
|
+
};
|
|
2569
|
+
this.runtime = runtime;
|
|
2570
|
+
this.onUpdate = opts.onUpdate;
|
|
2187
2571
|
this.run = opts.run;
|
|
2188
2572
|
this.deps = opts.deps ?? [];
|
|
2189
|
-
this.queue.emitter.on(
|
|
2190
|
-
1 /* BEFORE_FLUSH */,
|
|
2191
|
-
this.handleQueueBeforeFlush
|
|
2192
|
-
);
|
|
2193
|
-
this.queue.emitter.on(
|
|
2194
|
-
0 /* AFTER_FLUSH */,
|
|
2195
|
-
this.handleQueueAfterFlush
|
|
2196
|
-
);
|
|
2197
2573
|
for (const dep of this.deps) {
|
|
2198
|
-
|
|
2574
|
+
if (dep instanceof OIMEffectDependencyComputed) {
|
|
2575
|
+
this.computedDeps.push(dep);
|
|
2576
|
+
} else {
|
|
2577
|
+
this.sourceDeps.push(dep);
|
|
2578
|
+
}
|
|
2199
2579
|
}
|
|
2580
|
+
this.subscribeToDeps();
|
|
2200
2581
|
}
|
|
2201
2582
|
destroy() {
|
|
2202
|
-
if (this.
|
|
2203
|
-
|
|
2204
|
-
|
|
2205
|
-
|
|
2206
|
-
this.
|
|
2207
|
-
|
|
2208
|
-
this.
|
|
2209
|
-
|
|
2210
|
-
|
|
2211
|
-
|
|
2212
|
-
|
|
2213
|
-
);
|
|
2583
|
+
if (this.dequeueScheduled) {
|
|
2584
|
+
this.dequeueScheduled();
|
|
2585
|
+
this.dequeueScheduled = void 0;
|
|
2586
|
+
}
|
|
2587
|
+
this.unsubscribeFromAllDeps();
|
|
2588
|
+
if (this.dequeueResubscribe) {
|
|
2589
|
+
this.dequeueResubscribe();
|
|
2590
|
+
this.dequeueResubscribe = void 0;
|
|
2591
|
+
}
|
|
2592
|
+
this.isResubscribeEnqueued = false;
|
|
2593
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2214
2594
|
}
|
|
2215
2595
|
runOnce() {
|
|
2216
|
-
if (this.isDestroyed) return;
|
|
2217
2596
|
this.run();
|
|
2218
2597
|
}
|
|
2598
|
+
subscribeToDeps() {
|
|
2599
|
+
if (this.sourceUnsubscribers.length > 0 || this.computedUnsubscribers.length > 0)
|
|
2600
|
+
return;
|
|
2601
|
+
for (const dep of this.sourceDeps) {
|
|
2602
|
+
this.sourceUnsubscribers.push(
|
|
2603
|
+
dep.subscribe(this.onSourceInvalidate)
|
|
2604
|
+
);
|
|
2605
|
+
}
|
|
2606
|
+
for (const dep of this.computedDeps) {
|
|
2607
|
+
this.computedUnsubscribers.push(
|
|
2608
|
+
dep.subscribe(this.onComputedInvalidate)
|
|
2609
|
+
);
|
|
2610
|
+
}
|
|
2611
|
+
}
|
|
2612
|
+
unsubscribeFromSourceDeps() {
|
|
2613
|
+
if (this.sourceUnsubscribers.length === 0) return;
|
|
2614
|
+
for (const unsubscribe of this.sourceUnsubscribers) unsubscribe();
|
|
2615
|
+
this.sourceUnsubscribers = [];
|
|
2616
|
+
}
|
|
2617
|
+
unsubscribeFromAllDeps() {
|
|
2618
|
+
this.unsubscribeFromSourceDeps();
|
|
2619
|
+
if (this.computedUnsubscribers.length === 0) return;
|
|
2620
|
+
for (const unsubscribe of this.computedUnsubscribers) unsubscribe();
|
|
2621
|
+
this.computedUnsubscribers = [];
|
|
2622
|
+
}
|
|
2623
|
+
ensureResubscribeAfterFlush() {
|
|
2624
|
+
if (this.isResubscribeEnqueued) return;
|
|
2625
|
+
this.isResubscribeEnqueued = true;
|
|
2626
|
+
this.dequeueResubscribe = this.runtime.scheduleAfterFlush(
|
|
2627
|
+
this.onAfterFlush
|
|
2628
|
+
);
|
|
2629
|
+
}
|
|
2219
2630
|
};
|
|
2220
2631
|
|
|
2221
|
-
// src/modules/effect/enum/EOIMEffectPhase.ts
|
|
2222
|
-
var EOIMEffectPhase = /* @__PURE__ */ ((EOIMEffectPhase2) => {
|
|
2223
|
-
EOIMEffectPhase2["PRE"] = "pre";
|
|
2224
|
-
EOIMEffectPhase2["HANDLERS"] = "handlers";
|
|
2225
|
-
return EOIMEffectPhase2;
|
|
2226
|
-
})(EOIMEffectPhase || {});
|
|
2227
|
-
|
|
2228
2632
|
// src/modules/computed/enum/EOIMComputedEventType.ts
|
|
2229
2633
|
var EOIMComputedEventType = /* @__PURE__ */ ((EOIMComputedEventType2) => {
|
|
2230
2634
|
EOIMComputedEventType2["UPDATE"] = "update";
|
|
2231
2635
|
return EOIMComputedEventType2;
|
|
2232
2636
|
})(EOIMComputedEventType || {});
|
|
2233
2637
|
|
|
2234
|
-
// src/modules/computed/core/OIMUpdateEventCoalescerComputed.ts
|
|
2235
|
-
var OIMUpdateEventCoalescerComputed = class extends OIMUpdateEventCoalescer {
|
|
2236
|
-
constructor(computedEmitter) {
|
|
2237
|
-
super();
|
|
2238
|
-
this.computedEmitter = computedEmitter;
|
|
2239
|
-
this.handleUpdate = (payload) => {
|
|
2240
|
-
this.addUpdatedKeys(payload.keys);
|
|
2241
|
-
};
|
|
2242
|
-
this.computedEmitter.on(
|
|
2243
|
-
"update" /* UPDATE */,
|
|
2244
|
-
this.handleUpdate
|
|
2245
|
-
);
|
|
2246
|
-
}
|
|
2247
|
-
destroy() {
|
|
2248
|
-
this.computedEmitter.off(
|
|
2249
|
-
"update" /* UPDATE */,
|
|
2250
|
-
this.handleUpdate
|
|
2251
|
-
);
|
|
2252
|
-
this.emitter.offAll();
|
|
2253
|
-
this.clearUpdatedKeys();
|
|
2254
|
-
}
|
|
2255
|
-
};
|
|
2256
|
-
|
|
2257
2638
|
// src/modules/computed/core/OIMComputed.ts
|
|
2258
2639
|
var OIMComputed = class {
|
|
2259
|
-
constructor(
|
|
2640
|
+
constructor(runtime, opts) {
|
|
2260
2641
|
this.emitter = new OIMEventEmitter();
|
|
2261
2642
|
this.hasValue = false;
|
|
2262
2643
|
this.isDirty = true;
|
|
2263
|
-
this.
|
|
2264
|
-
this.hasRecomputedInThisFlush = false;
|
|
2265
|
-
this.handleQueueBeforeFlush = () => {
|
|
2266
|
-
this.isInFlush = true;
|
|
2267
|
-
this.hasRecomputedInThisFlush = false;
|
|
2268
|
-
};
|
|
2269
|
-
this.handleQueueAfterFlush = () => {
|
|
2270
|
-
this.isInFlush = false;
|
|
2271
|
-
this.hasRecomputedInThisFlush = false;
|
|
2272
|
-
};
|
|
2273
|
-
this.queue = queue;
|
|
2644
|
+
this.runtime = runtime;
|
|
2274
2645
|
this.compute = opts.compute;
|
|
2275
2646
|
this.compare = opts.compare ?? Object.is;
|
|
2276
2647
|
this.deps = opts.deps ?? [];
|
|
2277
|
-
this.
|
|
2278
|
-
this.
|
|
2279
|
-
|
|
2280
|
-
this.updateEventEmitter = new OIMUpdateEventEmitter({
|
|
2281
|
-
coalescer: this.coalescer,
|
|
2282
|
-
queue: this.queue
|
|
2283
|
-
});
|
|
2284
|
-
this.queue.emitter.on(
|
|
2285
|
-
1 /* BEFORE_FLUSH */,
|
|
2286
|
-
this.handleQueueBeforeFlush
|
|
2648
|
+
this.updateEventEmitter = new OIMUpdateEventEmitter(
|
|
2649
|
+
this.runtime.queue,
|
|
2650
|
+
"immediate"
|
|
2287
2651
|
);
|
|
2288
|
-
this.
|
|
2289
|
-
0 /* AFTER_FLUSH */,
|
|
2290
|
-
this.handleQueueAfterFlush
|
|
2291
|
-
);
|
|
2292
|
-
this.effect = new OIMEffect(this.queue, {
|
|
2652
|
+
this.effect = new OIMEffect(this.runtime, {
|
|
2293
2653
|
deps: this.deps,
|
|
2294
|
-
|
|
2295
|
-
onInvalidate: () => {
|
|
2654
|
+
onUpdate: () => {
|
|
2296
2655
|
this.isDirty = true;
|
|
2297
2656
|
},
|
|
2298
2657
|
run: () => {
|
|
2299
|
-
if (this.isInFlush) {
|
|
2300
|
-
if (this.hasRecomputedInThisFlush) return;
|
|
2301
|
-
this.hasRecomputedInThisFlush = true;
|
|
2302
|
-
}
|
|
2303
2658
|
this.recomputeAndEmitIfChanged();
|
|
2304
2659
|
}
|
|
2305
2660
|
});
|
|
@@ -2313,16 +2668,7 @@ var OIMComputed = class {
|
|
|
2313
2668
|
}
|
|
2314
2669
|
destroy() {
|
|
2315
2670
|
this.effect.destroy();
|
|
2316
|
-
this.queue.emitter.off(
|
|
2317
|
-
1 /* BEFORE_FLUSH */,
|
|
2318
|
-
this.handleQueueBeforeFlush
|
|
2319
|
-
);
|
|
2320
|
-
this.queue.emitter.off(
|
|
2321
|
-
0 /* AFTER_FLUSH */,
|
|
2322
|
-
this.handleQueueAfterFlush
|
|
2323
|
-
);
|
|
2324
2671
|
this.updateEventEmitter.destroy();
|
|
2325
|
-
this.coalescer.destroy();
|
|
2326
2672
|
this.emitter.offAll();
|
|
2327
2673
|
}
|
|
2328
2674
|
recomputeAndEmitIfChanged() {
|
|
@@ -2338,6 +2684,7 @@ var OIMComputed = class {
|
|
|
2338
2684
|
this.emitter.emit("update" /* UPDATE */, {
|
|
2339
2685
|
keys: ["value"]
|
|
2340
2686
|
});
|
|
2687
|
+
this.updateEventEmitter.markUpdatedKey("value");
|
|
2341
2688
|
}
|
|
2342
2689
|
};
|
|
2343
2690
|
|
|
@@ -2346,31 +2693,21 @@ function isReadonlyArray(value) {
|
|
|
2346
2693
|
return Array.isArray(value);
|
|
2347
2694
|
}
|
|
2348
2695
|
var OIMEffectDependencyKeyed = class {
|
|
2349
|
-
constructor(
|
|
2350
|
-
this.
|
|
2696
|
+
constructor(subscription, keyOrKeys) {
|
|
2697
|
+
this.subscription = subscription;
|
|
2351
2698
|
if (isReadonlyArray(keyOrKeys)) {
|
|
2352
2699
|
this.keys = keyOrKeys;
|
|
2353
2700
|
} else {
|
|
2354
2701
|
this.key = keyOrKeys;
|
|
2355
2702
|
}
|
|
2356
2703
|
}
|
|
2357
|
-
subscribe(
|
|
2358
|
-
const isPre = phase === "pre" /* PRE */;
|
|
2704
|
+
subscribe(onUpdate) {
|
|
2359
2705
|
if (this.keys !== void 0) {
|
|
2360
|
-
return
|
|
2361
|
-
this.keys,
|
|
2362
|
-
onInvalidate
|
|
2363
|
-
) : this.updateEventEmitter.subscribeOnKeys(
|
|
2364
|
-
this.keys,
|
|
2365
|
-
onInvalidate
|
|
2366
|
-
);
|
|
2706
|
+
return this.subscription.subscribeOnKeys(this.keys, onUpdate);
|
|
2367
2707
|
}
|
|
2368
2708
|
if (this.key === void 0) return () => {
|
|
2369
2709
|
};
|
|
2370
|
-
return
|
|
2371
|
-
this.key,
|
|
2372
|
-
onInvalidate
|
|
2373
|
-
) : this.updateEventEmitter.subscribeOnKey(this.key, onInvalidate);
|
|
2710
|
+
return this.subscription.subscribeOnKey(this.key, onUpdate);
|
|
2374
2711
|
}
|
|
2375
2712
|
};
|
|
2376
2713
|
|
|
@@ -2378,12 +2715,12 @@ var OIMEffectDependencyKeyed = class {
|
|
|
2378
2715
|
var OIMEffectDependencyKeyedObject = class {
|
|
2379
2716
|
constructor(object, keyOrKeys) {
|
|
2380
2717
|
this.dep = new OIMEffectDependencyKeyed(
|
|
2381
|
-
object
|
|
2718
|
+
object,
|
|
2382
2719
|
keyOrKeys
|
|
2383
2720
|
);
|
|
2384
2721
|
}
|
|
2385
|
-
subscribe(
|
|
2386
|
-
return this.dep.subscribe(
|
|
2722
|
+
subscribe(onUpdate) {
|
|
2723
|
+
return this.dep.subscribe(onUpdate);
|
|
2387
2724
|
}
|
|
2388
2725
|
};
|
|
2389
2726
|
|
|
@@ -2391,12 +2728,12 @@ var OIMEffectDependencyKeyedObject = class {
|
|
|
2391
2728
|
var OIMEffectDependencyKeyedCollection = class {
|
|
2392
2729
|
constructor(collection, pkOrPks) {
|
|
2393
2730
|
this.dep = new OIMEffectDependencyKeyed(
|
|
2394
|
-
collection
|
|
2731
|
+
collection,
|
|
2395
2732
|
pkOrPks
|
|
2396
2733
|
);
|
|
2397
2734
|
}
|
|
2398
|
-
subscribe(
|
|
2399
|
-
return this.dep.subscribe(
|
|
2735
|
+
subscribe(onUpdate) {
|
|
2736
|
+
return this.dep.subscribe(onUpdate);
|
|
2400
2737
|
}
|
|
2401
2738
|
};
|
|
2402
2739
|
|
|
@@ -2404,44 +2741,609 @@ var OIMEffectDependencyKeyedCollection = class {
|
|
|
2404
2741
|
var OIMEffectDependencyKeyedIndex = class {
|
|
2405
2742
|
constructor(index, keyOrKeys) {
|
|
2406
2743
|
this.dep = new OIMEffectDependencyKeyed(
|
|
2407
|
-
index
|
|
2744
|
+
index,
|
|
2408
2745
|
keyOrKeys
|
|
2409
2746
|
);
|
|
2410
2747
|
}
|
|
2411
|
-
subscribe(
|
|
2412
|
-
return this.dep.subscribe(
|
|
2748
|
+
subscribe(onUpdate) {
|
|
2749
|
+
return this.dep.subscribe(onUpdate);
|
|
2413
2750
|
}
|
|
2414
2751
|
};
|
|
2415
2752
|
|
|
2416
|
-
// src/modules/
|
|
2417
|
-
var
|
|
2418
|
-
constructor(
|
|
2419
|
-
this.
|
|
2753
|
+
// src/modules/selector/core/OIMSelector.ts
|
|
2754
|
+
var OIMSelector = class {
|
|
2755
|
+
constructor(runtime, sourceDeps, computedDeps = []) {
|
|
2756
|
+
this.runtime = runtime;
|
|
2757
|
+
this.sourceDeps = sourceDeps;
|
|
2758
|
+
this.computedDeps = computedDeps;
|
|
2759
|
+
this.listeners = /* @__PURE__ */ new Set();
|
|
2760
|
+
this.sourceUnsubscribers = [];
|
|
2761
|
+
this.computedUnsubscribers = [];
|
|
2762
|
+
this.isResubscribeEnqueued = false;
|
|
2763
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2764
|
+
this.isDeliveryEnqueued = false;
|
|
2765
|
+
this.hasLastValue = false;
|
|
2766
|
+
this.onSourceInvalidate = () => {
|
|
2767
|
+
if (this.listeners.size === 0) return;
|
|
2768
|
+
if (!this.isTemporarilyUnsubscribedForFlush) {
|
|
2769
|
+
this.isTemporarilyUnsubscribedForFlush = true;
|
|
2770
|
+
this.unsubscribeFromSourceDeps();
|
|
2771
|
+
this.ensureResubscribeAfterFlush();
|
|
2772
|
+
}
|
|
2773
|
+
if (this.isDeliveryEnqueued) return;
|
|
2774
|
+
this.isDeliveryEnqueued = true;
|
|
2775
|
+
this.dequeueDelivery = this.runtime.schedule(this.deliver);
|
|
2776
|
+
};
|
|
2777
|
+
this.onComputedInvalidate = () => {
|
|
2778
|
+
if (this.listeners.size === 0) return;
|
|
2779
|
+
if (this.isDeliveryEnqueued) return;
|
|
2780
|
+
this.isDeliveryEnqueued = true;
|
|
2781
|
+
this.dequeueDelivery = this.runtime.schedule(this.deliver);
|
|
2782
|
+
};
|
|
2783
|
+
this.deliver = () => {
|
|
2784
|
+
this.isDeliveryEnqueued = false;
|
|
2785
|
+
this.dequeueDelivery = void 0;
|
|
2786
|
+
if (this.listeners.size === 0) return;
|
|
2787
|
+
const next = this.getValue();
|
|
2788
|
+
if (this.hasLastValue && this.areEqual(this.lastValue, next)) return;
|
|
2789
|
+
this.setLastValue(next);
|
|
2790
|
+
const snapshot = Array.from(this.listeners);
|
|
2791
|
+
for (let i = 0; i < snapshot.length; i++) {
|
|
2792
|
+
const listener = snapshot[i];
|
|
2793
|
+
if (this.listeners.has(listener)) listener(next);
|
|
2794
|
+
}
|
|
2795
|
+
};
|
|
2796
|
+
this.onAfterFlush = () => {
|
|
2797
|
+
if (!this.isResubscribeEnqueued) return;
|
|
2798
|
+
this.isResubscribeEnqueued = false;
|
|
2799
|
+
this.dequeueResubscribe = void 0;
|
|
2800
|
+
if (this.listeners.size === 0) return;
|
|
2801
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2802
|
+
if (this.sourceUnsubscribers.length === 0) {
|
|
2803
|
+
for (const dep of this.sourceDeps) {
|
|
2804
|
+
this.sourceUnsubscribers.push(
|
|
2805
|
+
dep.subscribe(this.onSourceInvalidate)
|
|
2806
|
+
);
|
|
2807
|
+
}
|
|
2808
|
+
}
|
|
2809
|
+
};
|
|
2810
|
+
}
|
|
2811
|
+
get queue() {
|
|
2812
|
+
return this.runtime.queue;
|
|
2813
|
+
}
|
|
2814
|
+
/**
|
|
2815
|
+
* Start watching this selector. The callback is called immediately with the current value,
|
|
2816
|
+
* then coalesced and delivered on `queue.flush()` when the selector invalidates.
|
|
2817
|
+
*/
|
|
2818
|
+
watch(onValue) {
|
|
2819
|
+
this.listeners.add(onValue);
|
|
2820
|
+
if (this.listeners.size === 1) {
|
|
2821
|
+
this.subscribeToDeps();
|
|
2822
|
+
}
|
|
2823
|
+
const current = this.getValue();
|
|
2824
|
+
this.setLastValue(current);
|
|
2825
|
+
onValue(current);
|
|
2826
|
+
return () => {
|
|
2827
|
+
this.listeners.delete(onValue);
|
|
2828
|
+
if (this.listeners.size > 0) return;
|
|
2829
|
+
this.unsubscribeFromAllDeps();
|
|
2830
|
+
if (this.dequeueResubscribe) {
|
|
2831
|
+
this.dequeueResubscribe();
|
|
2832
|
+
this.dequeueResubscribe = void 0;
|
|
2833
|
+
}
|
|
2834
|
+
this.isResubscribeEnqueued = false;
|
|
2835
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2836
|
+
if (this.dequeueDelivery) {
|
|
2837
|
+
this.dequeueDelivery();
|
|
2838
|
+
this.dequeueDelivery = void 0;
|
|
2839
|
+
}
|
|
2840
|
+
this.isDeliveryEnqueued = false;
|
|
2841
|
+
this.hasLastValue = false;
|
|
2842
|
+
};
|
|
2843
|
+
}
|
|
2844
|
+
areEqual(prev, next) {
|
|
2845
|
+
return Object.is(prev, next);
|
|
2846
|
+
}
|
|
2847
|
+
setLastValue(value) {
|
|
2848
|
+
this.lastValue = value;
|
|
2849
|
+
this.hasLastValue = true;
|
|
2850
|
+
}
|
|
2851
|
+
subscribeToDeps() {
|
|
2852
|
+
if (this.sourceUnsubscribers.length > 0 || this.computedUnsubscribers.length > 0)
|
|
2853
|
+
return;
|
|
2854
|
+
for (const dep of this.sourceDeps) {
|
|
2855
|
+
this.sourceUnsubscribers.push(
|
|
2856
|
+
dep.subscribe(this.onSourceInvalidate)
|
|
2857
|
+
);
|
|
2858
|
+
}
|
|
2859
|
+
for (const dep of this.computedDeps) {
|
|
2860
|
+
this.computedUnsubscribers.push(
|
|
2861
|
+
dep.subscribe(this.onComputedInvalidate)
|
|
2862
|
+
);
|
|
2863
|
+
}
|
|
2864
|
+
}
|
|
2865
|
+
unsubscribeFromSourceDeps() {
|
|
2866
|
+
if (this.sourceUnsubscribers.length === 0) return;
|
|
2867
|
+
for (const unsub of this.sourceUnsubscribers) unsub();
|
|
2868
|
+
this.sourceUnsubscribers = [];
|
|
2869
|
+
}
|
|
2870
|
+
unsubscribeFromAllDeps() {
|
|
2871
|
+
this.unsubscribeFromSourceDeps();
|
|
2872
|
+
if (this.computedUnsubscribers.length === 0) return;
|
|
2873
|
+
for (const unsub of this.computedUnsubscribers) unsub();
|
|
2874
|
+
this.computedUnsubscribers = [];
|
|
2875
|
+
}
|
|
2876
|
+
ensureResubscribeAfterFlush() {
|
|
2877
|
+
if (this.isResubscribeEnqueued) return;
|
|
2878
|
+
this.isResubscribeEnqueued = true;
|
|
2879
|
+
this.dequeueResubscribe = this.runtime.scheduleAfterFlush(
|
|
2880
|
+
this.onAfterFlush
|
|
2881
|
+
);
|
|
2882
|
+
}
|
|
2883
|
+
};
|
|
2884
|
+
|
|
2885
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyUpdateEventEmitterKey.ts
|
|
2886
|
+
var OIMSelectorSourceDependencyUpdateEventEmitterKey = class {
|
|
2887
|
+
constructor(subscription, key) {
|
|
2888
|
+
this.subscription = subscription;
|
|
2889
|
+
this.key = key;
|
|
2890
|
+
}
|
|
2891
|
+
subscribe(onUpdate) {
|
|
2892
|
+
return this.subscription.subscribeOnKey(this.key, onUpdate);
|
|
2893
|
+
}
|
|
2894
|
+
};
|
|
2895
|
+
|
|
2896
|
+
// src/modules/selector/core/OIMCollectionByPkSelector.ts
|
|
2897
|
+
var OIMCollectionByPkSelector = class extends OIMSelector {
|
|
2898
|
+
constructor(runtime, collection, pk) {
|
|
2899
|
+
super(runtime, [
|
|
2900
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKey(
|
|
2901
|
+
collection,
|
|
2902
|
+
pk
|
|
2903
|
+
)
|
|
2904
|
+
]);
|
|
2905
|
+
this.collection = collection;
|
|
2906
|
+
this.pk = pk;
|
|
2907
|
+
}
|
|
2908
|
+
getValue() {
|
|
2909
|
+
return this.collection.getOneByPk(this.pk);
|
|
2910
|
+
}
|
|
2911
|
+
};
|
|
2912
|
+
|
|
2913
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyUpdateEventEmitterKeys.ts
|
|
2914
|
+
var OIMSelectorSourceDependencyUpdateEventEmitterKeys = class {
|
|
2915
|
+
constructor(subscription, keys) {
|
|
2916
|
+
this.subscription = subscription;
|
|
2917
|
+
this.keys = keys;
|
|
2918
|
+
}
|
|
2919
|
+
subscribe(onUpdate) {
|
|
2920
|
+
return this.subscription.subscribeOnKeys(this.keys, onUpdate);
|
|
2921
|
+
}
|
|
2922
|
+
};
|
|
2923
|
+
|
|
2924
|
+
// src/modules/selector/core/OIMCollectionByPksSelector.ts
|
|
2925
|
+
var OIMCollectionByPksSelector = class extends OIMSelector {
|
|
2926
|
+
constructor(runtime, collection, pks) {
|
|
2927
|
+
super(runtime, [
|
|
2928
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKeys(
|
|
2929
|
+
collection,
|
|
2930
|
+
pks
|
|
2931
|
+
)
|
|
2932
|
+
]);
|
|
2933
|
+
this.collection = collection;
|
|
2934
|
+
this.pks = pks;
|
|
2935
|
+
}
|
|
2936
|
+
getValue() {
|
|
2937
|
+
return this.pks.map((pk) => this.collection.getOneByPk(pk));
|
|
2938
|
+
}
|
|
2939
|
+
areEqual(prev, next) {
|
|
2940
|
+
if (prev === next) return true;
|
|
2941
|
+
if (prev.length !== next.length) return false;
|
|
2942
|
+
for (let i = 0; i < prev.length; i++) {
|
|
2943
|
+
if (prev[i] !== next[i]) return false;
|
|
2944
|
+
}
|
|
2945
|
+
return true;
|
|
2946
|
+
}
|
|
2947
|
+
};
|
|
2948
|
+
|
|
2949
|
+
// src/modules/selector/core/OIMObjectValueByKeySelector.ts
|
|
2950
|
+
var OIMObjectValueByKeySelector = class extends OIMSelector {
|
|
2951
|
+
constructor(runtime, obj, key) {
|
|
2952
|
+
super(runtime, [
|
|
2953
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKey(
|
|
2954
|
+
obj,
|
|
2955
|
+
key
|
|
2956
|
+
)
|
|
2957
|
+
]);
|
|
2958
|
+
this.obj = obj;
|
|
2959
|
+
this.key = key;
|
|
2960
|
+
}
|
|
2961
|
+
getValue() {
|
|
2962
|
+
return this.obj.get(this.key);
|
|
2963
|
+
}
|
|
2964
|
+
};
|
|
2965
|
+
|
|
2966
|
+
// src/modules/selector/core/OIMObjectValuesByKeysSelector.ts
|
|
2967
|
+
var OIMObjectValuesByKeysSelector = class extends OIMSelector {
|
|
2968
|
+
constructor(runtime, obj, keys) {
|
|
2969
|
+
super(runtime, [
|
|
2970
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKeys(
|
|
2971
|
+
obj,
|
|
2972
|
+
keys
|
|
2973
|
+
)
|
|
2974
|
+
]);
|
|
2975
|
+
this.obj = obj;
|
|
2976
|
+
this.keys = keys;
|
|
2977
|
+
}
|
|
2978
|
+
getValue() {
|
|
2979
|
+
return this.keys.map((k) => this.obj.get(k));
|
|
2980
|
+
}
|
|
2981
|
+
areEqual(prev, next) {
|
|
2982
|
+
if (prev === next) return true;
|
|
2983
|
+
if (prev.length !== next.length) return false;
|
|
2984
|
+
for (let i = 0; i < prev.length; i++) {
|
|
2985
|
+
if (prev[i] !== next[i]) return false;
|
|
2986
|
+
}
|
|
2987
|
+
return true;
|
|
2988
|
+
}
|
|
2989
|
+
};
|
|
2990
|
+
|
|
2991
|
+
// src/modules/selector/core/OIMIndexPksByKeySetBasedSelector.ts
|
|
2992
|
+
var OIMIndexPksByKeySetBasedSelector = class extends OIMSelector {
|
|
2993
|
+
constructor(runtime, reactiveIndex, key) {
|
|
2994
|
+
super(runtime, [
|
|
2995
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKey(
|
|
2996
|
+
reactiveIndex,
|
|
2997
|
+
key
|
|
2998
|
+
)
|
|
2999
|
+
]);
|
|
3000
|
+
this.reactiveIndex = reactiveIndex;
|
|
3001
|
+
this.key = key;
|
|
3002
|
+
}
|
|
3003
|
+
getValue() {
|
|
3004
|
+
return this.reactiveIndex.getPksByKey(this.key);
|
|
3005
|
+
}
|
|
3006
|
+
};
|
|
3007
|
+
|
|
3008
|
+
// src/modules/selector/core/OIMIndexPksByKeyArrayBasedSelector.ts
|
|
3009
|
+
var OIMIndexPksByKeyArrayBasedSelector = class extends OIMSelector {
|
|
3010
|
+
constructor(runtime, reactiveIndex, key) {
|
|
3011
|
+
super(runtime, [
|
|
3012
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKey(
|
|
3013
|
+
reactiveIndex,
|
|
3014
|
+
key
|
|
3015
|
+
)
|
|
3016
|
+
]);
|
|
3017
|
+
this.reactiveIndex = reactiveIndex;
|
|
3018
|
+
this.key = key;
|
|
3019
|
+
}
|
|
3020
|
+
getValue() {
|
|
3021
|
+
return this.reactiveIndex.getPksByKey(this.key);
|
|
3022
|
+
}
|
|
3023
|
+
areEqual(prev, next) {
|
|
3024
|
+
if (prev === next) return true;
|
|
3025
|
+
if (prev.length !== next.length) return false;
|
|
3026
|
+
for (let i = 0; i < prev.length; i++)
|
|
3027
|
+
if (prev[i] !== next[i]) return false;
|
|
3028
|
+
return true;
|
|
3029
|
+
}
|
|
3030
|
+
};
|
|
3031
|
+
|
|
3032
|
+
// src/modules/selector/core/OIMIndexPksByKeysSetBasedSelector.ts
|
|
3033
|
+
var OIMIndexPksByKeysSetBasedSelector = class extends OIMSelector {
|
|
3034
|
+
constructor(runtime, reactiveIndex, keys) {
|
|
3035
|
+
super(runtime, [
|
|
3036
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKeys(
|
|
3037
|
+
reactiveIndex,
|
|
3038
|
+
keys
|
|
3039
|
+
)
|
|
3040
|
+
]);
|
|
3041
|
+
this.reactiveIndex = reactiveIndex;
|
|
3042
|
+
this.keys = keys;
|
|
3043
|
+
}
|
|
3044
|
+
getValue() {
|
|
3045
|
+
return this.keys.map((key) => Array.from(this.reactiveIndex.getPksByKey(key))).flat();
|
|
3046
|
+
}
|
|
3047
|
+
areEqual(prev, next) {
|
|
3048
|
+
if (prev === next) return true;
|
|
3049
|
+
if (prev.length !== next.length) return false;
|
|
3050
|
+
for (let i = 0; i < prev.length; i++)
|
|
3051
|
+
if (prev[i] !== next[i]) return false;
|
|
3052
|
+
return true;
|
|
3053
|
+
}
|
|
3054
|
+
};
|
|
3055
|
+
|
|
3056
|
+
// src/modules/selector/core/OIMIndexPksByKeysArrayBasedSelector.ts
|
|
3057
|
+
var OIMIndexPksByKeysArrayBasedSelector = class extends OIMSelector {
|
|
3058
|
+
constructor(runtime, reactiveIndex, keys) {
|
|
3059
|
+
super(runtime, [
|
|
3060
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKeys(
|
|
3061
|
+
reactiveIndex,
|
|
3062
|
+
keys
|
|
3063
|
+
)
|
|
3064
|
+
]);
|
|
3065
|
+
this.reactiveIndex = reactiveIndex;
|
|
3066
|
+
this.keys = keys;
|
|
3067
|
+
}
|
|
3068
|
+
getValue() {
|
|
3069
|
+
return this.keys.map((key) => this.reactiveIndex.getPksByKey(key)).flat();
|
|
3070
|
+
}
|
|
3071
|
+
areEqual(prev, next) {
|
|
3072
|
+
if (prev === next) return true;
|
|
3073
|
+
if (prev.length !== next.length) return false;
|
|
3074
|
+
for (let i = 0; i < prev.length; i++)
|
|
3075
|
+
if (prev[i] !== next[i]) return false;
|
|
3076
|
+
return true;
|
|
3077
|
+
}
|
|
3078
|
+
};
|
|
3079
|
+
|
|
3080
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyEntitiesByIndexKeySetBased.ts
|
|
3081
|
+
var OIMSelectorSourceDependencyEntitiesByIndexKeySetBased = class {
|
|
3082
|
+
constructor(collection, reactiveIndex, key) {
|
|
3083
|
+
this.collection = collection;
|
|
3084
|
+
this.reactiveIndex = reactiveIndex;
|
|
3085
|
+
this.key = key;
|
|
3086
|
+
this.currentPks = [];
|
|
3087
|
+
}
|
|
3088
|
+
subscribe(onUpdate) {
|
|
3089
|
+
const resubscribeCollection = () => {
|
|
3090
|
+
const nextPks = Array.from(
|
|
3091
|
+
this.reactiveIndex.getSlotsByKey(this.key),
|
|
3092
|
+
(slot) => slot.pk
|
|
3093
|
+
);
|
|
3094
|
+
if (this.sameArray(this.currentPks, nextPks)) return;
|
|
3095
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
3096
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
3097
|
+
this.currentPks = nextPks;
|
|
3098
|
+
if (this.currentPks.length === 0) return;
|
|
3099
|
+
this.unsubscribeFromCollectionKeys = this.collection.subscribeOnKeys(this.currentPks, onUpdate);
|
|
3100
|
+
};
|
|
3101
|
+
const onIndexUpdate = () => {
|
|
3102
|
+
resubscribeCollection();
|
|
3103
|
+
onUpdate();
|
|
3104
|
+
};
|
|
3105
|
+
resubscribeCollection();
|
|
3106
|
+
const unsubscribeFromIndex = this.reactiveIndex.subscribeOnKey(
|
|
3107
|
+
this.key,
|
|
3108
|
+
onIndexUpdate
|
|
3109
|
+
);
|
|
3110
|
+
return () => {
|
|
3111
|
+
unsubscribeFromIndex();
|
|
3112
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
3113
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
3114
|
+
this.currentPks = [];
|
|
3115
|
+
};
|
|
2420
3116
|
}
|
|
2421
|
-
|
|
2422
|
-
if (
|
|
2423
|
-
|
|
3117
|
+
sameArray(a, b) {
|
|
3118
|
+
if (a === b) return true;
|
|
3119
|
+
if (a.length !== b.length) return false;
|
|
3120
|
+
for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return false;
|
|
3121
|
+
return true;
|
|
3122
|
+
}
|
|
3123
|
+
};
|
|
3124
|
+
|
|
3125
|
+
// src/modules/selector/core/OIMEntitiesByIndexKeySetBasedSelector.ts
|
|
3126
|
+
var OIMEntitiesByIndexKeySetBasedSelector = class extends OIMSelector {
|
|
3127
|
+
constructor(runtime, collection, reactiveIndex, key) {
|
|
3128
|
+
super(runtime, [
|
|
3129
|
+
new OIMSelectorSourceDependencyEntitiesByIndexKeySetBased(collection, reactiveIndex, key)
|
|
3130
|
+
]);
|
|
3131
|
+
this.collection = collection;
|
|
3132
|
+
this.reactiveIndex = reactiveIndex;
|
|
3133
|
+
this.key = key;
|
|
3134
|
+
this.reactiveIndex.index.setSlotResolver(
|
|
3135
|
+
(pk) => this.collection.getSlotByPk(pk)
|
|
3136
|
+
);
|
|
3137
|
+
}
|
|
3138
|
+
getValue() {
|
|
3139
|
+
const slots = this.reactiveIndex.getSlotsByKey(this.key);
|
|
3140
|
+
const entities = [];
|
|
3141
|
+
entities.length = slots.size;
|
|
3142
|
+
let writeIndex = 0;
|
|
3143
|
+
for (const slot of slots) {
|
|
3144
|
+
entities[writeIndex++] = slot.item;
|
|
2424
3145
|
}
|
|
2425
|
-
return
|
|
2426
|
-
|
|
2427
|
-
|
|
3146
|
+
return entities;
|
|
3147
|
+
}
|
|
3148
|
+
areEqual(prev, next) {
|
|
3149
|
+
if (prev === next) return true;
|
|
3150
|
+
if (prev.length !== next.length) return false;
|
|
3151
|
+
for (let i = 0; i < prev.length; i++)
|
|
3152
|
+
if (prev[i] !== next[i]) return false;
|
|
3153
|
+
return true;
|
|
3154
|
+
}
|
|
3155
|
+
};
|
|
3156
|
+
|
|
3157
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyEntitiesByIndexKeyArrayBased.ts
|
|
3158
|
+
var OIMSelectorSourceDependencyEntitiesByIndexKeyArrayBased = class {
|
|
3159
|
+
constructor(collection, reactiveIndex, key) {
|
|
3160
|
+
this.collection = collection;
|
|
3161
|
+
this.reactiveIndex = reactiveIndex;
|
|
3162
|
+
this.key = key;
|
|
3163
|
+
this.currentPks = [];
|
|
3164
|
+
}
|
|
3165
|
+
subscribe(onUpdate) {
|
|
3166
|
+
const resubscribeCollection = () => {
|
|
3167
|
+
const nextPks = this.reactiveIndex.getSlotsByKey(this.key).map((slot) => slot.pk);
|
|
3168
|
+
if (this.sameArray(this.currentPks, nextPks)) return;
|
|
3169
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
3170
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
3171
|
+
this.currentPks = nextPks;
|
|
3172
|
+
if (this.currentPks.length === 0) return;
|
|
3173
|
+
this.unsubscribeFromCollectionKeys = this.collection.subscribeOnKeys(this.currentPks, onUpdate);
|
|
3174
|
+
};
|
|
3175
|
+
const onIndexUpdate = () => {
|
|
3176
|
+
resubscribeCollection();
|
|
3177
|
+
onUpdate();
|
|
3178
|
+
};
|
|
3179
|
+
resubscribeCollection();
|
|
3180
|
+
const unsubscribeFromIndex = this.reactiveIndex.subscribeOnKey(
|
|
3181
|
+
this.key,
|
|
3182
|
+
onIndexUpdate
|
|
3183
|
+
);
|
|
3184
|
+
return () => {
|
|
3185
|
+
unsubscribeFromIndex();
|
|
3186
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
3187
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
3188
|
+
this.currentPks = [];
|
|
3189
|
+
};
|
|
3190
|
+
}
|
|
3191
|
+
sameArray(a, b) {
|
|
3192
|
+
if (a === b) return true;
|
|
3193
|
+
if (a.length !== b.length) return false;
|
|
3194
|
+
for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return false;
|
|
3195
|
+
return true;
|
|
3196
|
+
}
|
|
3197
|
+
};
|
|
3198
|
+
|
|
3199
|
+
// src/modules/selector/core/OIMEntitiesByIndexKeyArrayBasedSelector.ts
|
|
3200
|
+
var OIMEntitiesByIndexKeyArrayBasedSelector = class extends OIMSelector {
|
|
3201
|
+
constructor(runtime, collection, reactiveIndex, key) {
|
|
3202
|
+
super(runtime, [
|
|
3203
|
+
new OIMSelectorSourceDependencyEntitiesByIndexKeyArrayBased(collection, reactiveIndex, key)
|
|
3204
|
+
]);
|
|
3205
|
+
this.collection = collection;
|
|
3206
|
+
this.reactiveIndex = reactiveIndex;
|
|
3207
|
+
this.key = key;
|
|
3208
|
+
this.reactiveIndex.index.setSlotResolver(
|
|
3209
|
+
(pk) => this.collection.getSlotByPk(pk)
|
|
2428
3210
|
);
|
|
2429
3211
|
}
|
|
3212
|
+
getValue() {
|
|
3213
|
+
const slots = this.reactiveIndex.getSlotsByKey(this.key);
|
|
3214
|
+
const entities = [];
|
|
3215
|
+
entities.length = slots.length;
|
|
3216
|
+
for (let i = 0; i < slots.length; i++) {
|
|
3217
|
+
entities[i] = slots[i].item;
|
|
3218
|
+
}
|
|
3219
|
+
return entities;
|
|
3220
|
+
}
|
|
3221
|
+
areEqual(prev, next) {
|
|
3222
|
+
if (prev === next) return true;
|
|
3223
|
+
if (prev.length !== next.length) return false;
|
|
3224
|
+
for (let i = 0; i < prev.length; i++)
|
|
3225
|
+
if (prev[i] !== next[i]) return false;
|
|
3226
|
+
return true;
|
|
3227
|
+
}
|
|
3228
|
+
};
|
|
3229
|
+
|
|
3230
|
+
// src/modules/computative/core/OIMComputativeRuntime.ts
|
|
3231
|
+
var OIMComputativeRuntime = class {
|
|
3232
|
+
constructor(queue) {
|
|
3233
|
+
this.queue = queue;
|
|
3234
|
+
this.isFlushScheduled = false;
|
|
3235
|
+
this.isFlushing = false;
|
|
3236
|
+
this.minLevel = Infinity;
|
|
3237
|
+
this.maxLevel = -Infinity;
|
|
3238
|
+
this.dirtyByLevel = /* @__PURE__ */ new Map();
|
|
3239
|
+
this.afterFlushTasks = /* @__PURE__ */ new Set();
|
|
3240
|
+
this.queue.emitter.on(0 /* AFTER_FLUSH */, () => {
|
|
3241
|
+
if (!this.isFlushScheduled) return;
|
|
3242
|
+
this.flush();
|
|
3243
|
+
});
|
|
3244
|
+
}
|
|
3245
|
+
/**
|
|
3246
|
+
* Schedule a one-shot task to run on the next `queue.flush()` (AFTER_FLUSH),
|
|
3247
|
+
* ordered by `level` ascending.
|
|
3248
|
+
*/
|
|
3249
|
+
schedule(task, level = 0) {
|
|
3250
|
+
let isActive = true;
|
|
3251
|
+
const wrapped = () => {
|
|
3252
|
+
if (!isActive) return;
|
|
3253
|
+
task();
|
|
3254
|
+
};
|
|
3255
|
+
let bucket = this.dirtyByLevel.get(level);
|
|
3256
|
+
if (!bucket) {
|
|
3257
|
+
bucket = /* @__PURE__ */ new Set();
|
|
3258
|
+
this.dirtyByLevel.set(level, bucket);
|
|
3259
|
+
}
|
|
3260
|
+
bucket.add(wrapped);
|
|
3261
|
+
if (level < this.minLevel) this.minLevel = level;
|
|
3262
|
+
if (level > this.maxLevel) this.maxLevel = level;
|
|
3263
|
+
if (!this.isFlushing) this.isFlushScheduled = true;
|
|
3264
|
+
return () => {
|
|
3265
|
+
if (!isActive) return;
|
|
3266
|
+
isActive = false;
|
|
3267
|
+
bucket.delete(wrapped);
|
|
3268
|
+
};
|
|
3269
|
+
}
|
|
3270
|
+
/**
|
|
3271
|
+
* Run once at the start of the next runtime flush (i.e. after queue.flush()).
|
|
3272
|
+
* Useful for resubscribing dependencies exactly once per source flush.
|
|
3273
|
+
*/
|
|
3274
|
+
scheduleAfterFlush(task) {
|
|
3275
|
+
let isActive = true;
|
|
3276
|
+
const wrapped = () => {
|
|
3277
|
+
if (!isActive) return;
|
|
3278
|
+
task();
|
|
3279
|
+
};
|
|
3280
|
+
this.afterFlushTasks.add(wrapped);
|
|
3281
|
+
if (!this.isFlushing) this.isFlushScheduled = true;
|
|
3282
|
+
return () => {
|
|
3283
|
+
if (!isActive) return;
|
|
3284
|
+
isActive = false;
|
|
3285
|
+
this.afterFlushTasks.delete(wrapped);
|
|
3286
|
+
};
|
|
3287
|
+
}
|
|
3288
|
+
flush() {
|
|
3289
|
+
this.isFlushScheduled = false;
|
|
3290
|
+
if (this.dirtyByLevel.size === 0 && this.afterFlushTasks.size === 0)
|
|
3291
|
+
return;
|
|
3292
|
+
this.isFlushing = true;
|
|
3293
|
+
try {
|
|
3294
|
+
if (this.afterFlushTasks.size > 0) {
|
|
3295
|
+
const snapshot = Array.from(this.afterFlushTasks);
|
|
3296
|
+
this.afterFlushTasks.clear();
|
|
3297
|
+
for (let i = 0; i < snapshot.length; i++) snapshot[i]();
|
|
3298
|
+
}
|
|
3299
|
+
if (this.dirtyByLevel.size === 0) return;
|
|
3300
|
+
let level = this.minLevel;
|
|
3301
|
+
let max = this.maxLevel;
|
|
3302
|
+
while (level <= max) {
|
|
3303
|
+
for (; ; ) {
|
|
3304
|
+
const bucket = this.dirtyByLevel.get(level);
|
|
3305
|
+
if (!bucket || bucket.size === 0) break;
|
|
3306
|
+
this.dirtyByLevel.delete(level);
|
|
3307
|
+
const snapshot = Array.from(bucket);
|
|
3308
|
+
for (let i = 0; i < snapshot.length; i++) snapshot[i]();
|
|
3309
|
+
}
|
|
3310
|
+
if (this.maxLevel > max) max = this.maxLevel;
|
|
3311
|
+
level++;
|
|
3312
|
+
}
|
|
3313
|
+
} finally {
|
|
3314
|
+
this.isFlushing = false;
|
|
3315
|
+
if (this.dirtyByLevel.size === 0) {
|
|
3316
|
+
this.minLevel = Infinity;
|
|
3317
|
+
this.maxLevel = -Infinity;
|
|
3318
|
+
} else {
|
|
3319
|
+
let nextMin = Infinity;
|
|
3320
|
+
let nextMax = -Infinity;
|
|
3321
|
+
this.dirtyByLevel.forEach((_bucket, lvl) => {
|
|
3322
|
+
if (lvl < nextMin) nextMin = lvl;
|
|
3323
|
+
if (lvl > nextMax) nextMax = lvl;
|
|
3324
|
+
});
|
|
3325
|
+
this.minLevel = nextMin;
|
|
3326
|
+
this.maxLevel = nextMax;
|
|
3327
|
+
this.isFlushScheduled = true;
|
|
3328
|
+
}
|
|
3329
|
+
}
|
|
3330
|
+
}
|
|
2430
3331
|
};
|
|
2431
3332
|
export {
|
|
2432
3333
|
EOIMCollectionEventType,
|
|
2433
3334
|
EOIMComputedEventType,
|
|
2434
|
-
EOIMEffectPhase,
|
|
2435
3335
|
EOIMEventQueueEventType,
|
|
2436
3336
|
EOIMEventQueueSchedulerEventType,
|
|
2437
3337
|
EOIMIndexEventType,
|
|
2438
3338
|
EOIMObjectEventType,
|
|
2439
|
-
EOIMUpdateEventCoalescerEventType,
|
|
2440
3339
|
OIMCollection,
|
|
3340
|
+
OIMCollectionByPkSelector,
|
|
3341
|
+
OIMCollectionByPksSelector,
|
|
2441
3342
|
OIMCollectionChangedFieldsWrapper,
|
|
2442
3343
|
OIMCollectionStore,
|
|
2443
3344
|
OIMCollectionStoreMapDriven,
|
|
2444
3345
|
OIMComparatorFactory,
|
|
3346
|
+
OIMComputativeRuntime,
|
|
2445
3347
|
OIMComputed,
|
|
2446
3348
|
OIMDBSettings,
|
|
2447
3349
|
OIMEffect,
|
|
@@ -2450,6 +3352,8 @@ export {
|
|
|
2450
3352
|
OIMEffectDependencyKeyedCollection,
|
|
2451
3353
|
OIMEffectDependencyKeyedIndex,
|
|
2452
3354
|
OIMEffectDependencyKeyedObject,
|
|
3355
|
+
OIMEntitiesByIndexKeyArrayBasedSelector,
|
|
3356
|
+
OIMEntitiesByIndexKeySetBasedSelector,
|
|
2453
3357
|
OIMEntityUpdaterFactory,
|
|
2454
3358
|
OIMEventEmitter,
|
|
2455
3359
|
OIMEventQueue,
|
|
@@ -2464,6 +3368,10 @@ export {
|
|
|
2464
3368
|
OIMIndexManualArrayBased,
|
|
2465
3369
|
OIMIndexManualOrderedArrayBased,
|
|
2466
3370
|
OIMIndexManualSetBased,
|
|
3371
|
+
OIMIndexPksByKeyArrayBasedSelector,
|
|
3372
|
+
OIMIndexPksByKeySetBasedSelector,
|
|
3373
|
+
OIMIndexPksByKeysArrayBasedSelector,
|
|
3374
|
+
OIMIndexPksByKeysSetBasedSelector,
|
|
2467
3375
|
OIMIndexSetBased,
|
|
2468
3376
|
OIMIndexStoreArrayBased,
|
|
2469
3377
|
OIMIndexStoreMapDrivenArrayBased,
|
|
@@ -2474,6 +3382,8 @@ export {
|
|
|
2474
3382
|
OIMObjectStore,
|
|
2475
3383
|
OIMObjectStoreMapDriven,
|
|
2476
3384
|
OIMObjectStoreRecordDriven,
|
|
3385
|
+
OIMObjectValueByKeySelector,
|
|
3386
|
+
OIMObjectValuesByKeysSelector,
|
|
2477
3387
|
OIMOrderedListIndexCommandStreamWrapper,
|
|
2478
3388
|
OIMPkSelectorFactory,
|
|
2479
3389
|
OIMRICollection,
|
|
@@ -2483,11 +3393,5 @@ export {
|
|
|
2483
3393
|
OIMReactiveIndexManualSetBased,
|
|
2484
3394
|
OIMReactiveIndexSetBased,
|
|
2485
3395
|
OIMReactiveObject,
|
|
2486
|
-
|
|
2487
|
-
OIMUpdateEventCoalescerCollection,
|
|
2488
|
-
OIMUpdateEventCoalescerComputed,
|
|
2489
|
-
OIMUpdateEventCoalescerIndex,
|
|
2490
|
-
OIMUpdateEventCoalescerManual,
|
|
2491
|
-
OIMUpdateEventCoalescerObject,
|
|
2492
|
-
OIMUpdateEventEmitter
|
|
3396
|
+
OIMSelector
|
|
2493
3397
|
};
|