@oimdb/core 1.5.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +572 -68
- package/dist/index.cjs +1849 -1535
- package/dist/index.d.cts +587 -507
- package/dist/index.d.ts +587 -507
- package/dist/index.js +1833 -1530
- package/llms.txt +429 -0
- package/package.json +4 -2
package/dist/index.js
CHANGED
|
@@ -2,14 +2,6 @@
|
|
|
2
2
|
var OIMCollectionStore = class {
|
|
3
3
|
};
|
|
4
4
|
|
|
5
|
-
// src/abstract/OIMIndexStoreSetBased.ts
|
|
6
|
-
var OIMIndexStoreSetBased = class {
|
|
7
|
-
};
|
|
8
|
-
|
|
9
|
-
// src/abstract/OIMIndexStoreArrayBased.ts
|
|
10
|
-
var OIMIndexStoreArrayBased = class {
|
|
11
|
-
};
|
|
12
|
-
|
|
13
5
|
// src/core/OIMEventEmitter.ts
|
|
14
6
|
var OIMEventEmitter = class {
|
|
15
7
|
constructor() {
|
|
@@ -115,7 +107,94 @@ var OIMEventEmitter = class {
|
|
|
115
107
|
}
|
|
116
108
|
};
|
|
117
109
|
|
|
118
|
-
// src/
|
|
110
|
+
// src/enums/EOIMIndexEventType.ts
|
|
111
|
+
var EOIMIndexEventType = /* @__PURE__ */ ((EOIMIndexEventType2) => {
|
|
112
|
+
EOIMIndexEventType2[EOIMIndexEventType2["UPDATE"] = 0] = "UPDATE";
|
|
113
|
+
return EOIMIndexEventType2;
|
|
114
|
+
})(EOIMIndexEventType || {});
|
|
115
|
+
|
|
116
|
+
// src/abstract/OIMIndex.ts
|
|
117
|
+
var OIMIndex = class {
|
|
118
|
+
constructor(store, comparePks) {
|
|
119
|
+
this.emitter = new OIMEventEmitter();
|
|
120
|
+
this.store = store;
|
|
121
|
+
this.comparePks = comparePks;
|
|
122
|
+
}
|
|
123
|
+
hasKey(key) {
|
|
124
|
+
return this.store.getOneByKey(key) !== void 0;
|
|
125
|
+
}
|
|
126
|
+
getKeys() {
|
|
127
|
+
return this.store.getAllKeys();
|
|
128
|
+
}
|
|
129
|
+
getKeySize(key) {
|
|
130
|
+
const bucket = this.store.getOneByKey(key);
|
|
131
|
+
return bucket ? this.getBucketSize(bucket) : 0;
|
|
132
|
+
}
|
|
133
|
+
get size() {
|
|
134
|
+
return this.store.countAll();
|
|
135
|
+
}
|
|
136
|
+
get isEmpty() {
|
|
137
|
+
return this.store.countAll() === 0;
|
|
138
|
+
}
|
|
139
|
+
getEntitiesByKey(key) {
|
|
140
|
+
const bucket = this.store.getOneByKey(key);
|
|
141
|
+
return bucket ? this.slotsToEntities(bucket) : [];
|
|
142
|
+
}
|
|
143
|
+
getEntitiesByKeys(keys) {
|
|
144
|
+
const result = /* @__PURE__ */ new Map();
|
|
145
|
+
const bucketsByKey = this.store.getManyByKeys(keys);
|
|
146
|
+
for (const [key, bucket] of bucketsByKey) {
|
|
147
|
+
result.set(key, this.slotsToEntities(bucket));
|
|
148
|
+
}
|
|
149
|
+
return result;
|
|
150
|
+
}
|
|
151
|
+
getMetrics() {
|
|
152
|
+
let totalPks = 0;
|
|
153
|
+
let maxBucketSize = 0;
|
|
154
|
+
let minBucketSize = Infinity;
|
|
155
|
+
const all = this.store.getAll();
|
|
156
|
+
for (const bucket of all.values()) {
|
|
157
|
+
const size = this.getBucketSize(bucket);
|
|
158
|
+
totalPks += size;
|
|
159
|
+
maxBucketSize = Math.max(maxBucketSize, size);
|
|
160
|
+
minBucketSize = Math.min(minBucketSize, size);
|
|
161
|
+
}
|
|
162
|
+
return {
|
|
163
|
+
totalKeys: all.size,
|
|
164
|
+
totalPks,
|
|
165
|
+
averagePksPerKey: all.size > 0 ? totalPks / all.size : 0,
|
|
166
|
+
maxBucketSize: maxBucketSize === -Infinity ? 0 : maxBucketSize,
|
|
167
|
+
minBucketSize: minBucketSize === Infinity ? 0 : minBucketSize
|
|
168
|
+
};
|
|
169
|
+
}
|
|
170
|
+
destroy() {
|
|
171
|
+
this.emitter.offAll();
|
|
172
|
+
this.store.clear();
|
|
173
|
+
}
|
|
174
|
+
emitUpdate(keys) {
|
|
175
|
+
this.emitter.emit(0 /* UPDATE */, { keys });
|
|
176
|
+
}
|
|
177
|
+
emitUpdateOne(key) {
|
|
178
|
+
this.emitUpdate([key]);
|
|
179
|
+
}
|
|
180
|
+
slotsToEntities(slots) {
|
|
181
|
+
const entities = [];
|
|
182
|
+
for (const slot of slots) {
|
|
183
|
+
if (slot.item !== void 0) entities.push(slot.item);
|
|
184
|
+
}
|
|
185
|
+
return entities;
|
|
186
|
+
}
|
|
187
|
+
};
|
|
188
|
+
|
|
189
|
+
// src/abstract/OIMIndexStoreSetBased.ts
|
|
190
|
+
var OIMIndexStoreSetBased = class {
|
|
191
|
+
};
|
|
192
|
+
|
|
193
|
+
// src/abstract/OIMIndexStoreArrayBased.ts
|
|
194
|
+
var OIMIndexStoreArrayBased = class {
|
|
195
|
+
};
|
|
196
|
+
|
|
197
|
+
// src/enums/EOIMEventQueueSchedulerEventType.ts
|
|
119
198
|
var EOIMEventQueueSchedulerEventType = /* @__PURE__ */ ((EOIMEventQueueSchedulerEventType2) => {
|
|
120
199
|
EOIMEventQueueSchedulerEventType2[EOIMEventQueueSchedulerEventType2["FLUSH"] = 0] = "FLUSH";
|
|
121
200
|
return EOIMEventQueueSchedulerEventType2;
|
|
@@ -140,12 +219,6 @@ var OIMEventQueueScheduler = class {
|
|
|
140
219
|
}
|
|
141
220
|
};
|
|
142
221
|
|
|
143
|
-
// src/enum/EOIMIndexEventType.ts
|
|
144
|
-
var EOIMIndexEventType = /* @__PURE__ */ ((EOIMIndexEventType2) => {
|
|
145
|
-
EOIMIndexEventType2[EOIMIndexEventType2["UPDATE"] = 0] = "UPDATE";
|
|
146
|
-
return EOIMIndexEventType2;
|
|
147
|
-
})(EOIMIndexEventType || {});
|
|
148
|
-
|
|
149
222
|
// src/core/OIMIndexStoreMapDrivenSetBased.ts
|
|
150
223
|
var OIMIndexStoreMapDrivenSetBased = class extends OIMIndexStoreSetBased {
|
|
151
224
|
constructor() {
|
|
@@ -191,17 +264,20 @@ var OIMIndexStoreMapDrivenSetBased = class extends OIMIndexStoreSetBased {
|
|
|
191
264
|
};
|
|
192
265
|
|
|
193
266
|
// src/abstract/OIMIndexSetBased.ts
|
|
194
|
-
var OIMIndexSetBased = class {
|
|
267
|
+
var OIMIndexSetBased = class extends OIMIndex {
|
|
195
268
|
constructor(options = {}) {
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
269
|
+
super(
|
|
270
|
+
options.store ?? new OIMIndexStoreMapDrivenSetBased(),
|
|
271
|
+
options.comparePks
|
|
272
|
+
);
|
|
273
|
+
}
|
|
274
|
+
getBucketSize(bucket) {
|
|
275
|
+
return bucket.size;
|
|
276
|
+
}
|
|
277
|
+
getPksByKey(key) {
|
|
278
|
+
const slotsSet = this.store.getOneByKey(key);
|
|
279
|
+
return slotsSet ? this.slotsToPks(slotsSet) : /* @__PURE__ */ new Set();
|
|
201
280
|
}
|
|
202
|
-
/**
|
|
203
|
-
* Get primary keys for multiple index keys
|
|
204
|
-
*/
|
|
205
281
|
getPksByKeys(keys) {
|
|
206
282
|
const result = /* @__PURE__ */ new Map();
|
|
207
283
|
const slotsByKey = this.store.getManyByKeys(keys);
|
|
@@ -210,112 +286,25 @@ var OIMIndexSetBased = class {
|
|
|
210
286
|
}
|
|
211
287
|
return result;
|
|
212
288
|
}
|
|
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
|
-
}
|
|
222
|
-
}
|
|
223
|
-
/**
|
|
224
|
-
* @deprecated Use getPksByKey instead
|
|
225
|
-
* Get primary keys for a specific index key
|
|
226
|
-
*/
|
|
227
|
-
getPks(key) {
|
|
228
|
-
return this.getPksByKey(key);
|
|
229
|
-
}
|
|
230
|
-
/**
|
|
231
|
-
* Get primary keys for a specific index key
|
|
232
|
-
*/
|
|
233
|
-
getPksByKey(key) {
|
|
234
|
-
const slotsSet = this.store.getOneByKey(key);
|
|
235
|
-
return slotsSet ? this.slotsToPks(slotsSet) : /* @__PURE__ */ new Set();
|
|
236
|
-
}
|
|
237
289
|
getSlotsByKey(key) {
|
|
238
|
-
|
|
239
|
-
return slotsSet ? slotsSet : /* @__PURE__ */ new Set();
|
|
290
|
+
return this.store.getOneByKey(key) ?? /* @__PURE__ */ new Set();
|
|
240
291
|
}
|
|
241
292
|
getSlotsByKeys(keys) {
|
|
242
293
|
return this.store.getManyByKeys(keys);
|
|
243
294
|
}
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
return this.store.getOneByKey(key) !== void 0;
|
|
249
|
-
}
|
|
250
|
-
/**
|
|
251
|
-
* Get all index keys
|
|
252
|
-
*/
|
|
253
|
-
getKeys() {
|
|
254
|
-
return this.store.getAllKeys();
|
|
255
|
-
}
|
|
256
|
-
/**
|
|
257
|
-
* Get the number of primary keys for a specific index key
|
|
258
|
-
*/
|
|
259
|
-
getKeySize(key) {
|
|
260
|
-
const slotsSet = this.store.getOneByKey(key);
|
|
261
|
-
return slotsSet ? slotsSet.size : 0;
|
|
262
|
-
}
|
|
263
|
-
/**
|
|
264
|
-
* Get total number of index keys
|
|
265
|
-
*/
|
|
266
|
-
get size() {
|
|
267
|
-
return this.store.countAll();
|
|
268
|
-
}
|
|
269
|
-
/**
|
|
270
|
-
* Check if the index is empty
|
|
271
|
-
*/
|
|
272
|
-
get isEmpty() {
|
|
273
|
-
return this.store.countAll() === 0;
|
|
274
|
-
}
|
|
275
|
-
/**
|
|
276
|
-
* Get performance metrics for monitoring and debugging
|
|
277
|
-
*/
|
|
278
|
-
getMetrics() {
|
|
279
|
-
let totalPks = 0;
|
|
280
|
-
let maxBucketSize = 0;
|
|
281
|
-
let minBucketSize = Infinity;
|
|
282
|
-
const allPks = this.store.getAll();
|
|
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);
|
|
287
|
-
}
|
|
288
|
-
return {
|
|
289
|
-
totalKeys: allPks.size,
|
|
290
|
-
totalPks,
|
|
291
|
-
averagePksPerKey: allPks.size > 0 ? totalPks / allPks.size : 0,
|
|
292
|
-
maxBucketSize: maxBucketSize === -Infinity ? 0 : maxBucketSize,
|
|
293
|
-
minBucketSize: minBucketSize === Infinity ? 0 : minBucketSize
|
|
294
|
-
};
|
|
295
|
-
}
|
|
296
|
-
/**
|
|
297
|
-
* Clean up event listeners when index is no longer needed
|
|
298
|
-
*/
|
|
299
|
-
destroy() {
|
|
300
|
-
this.emitter.offAll();
|
|
301
|
-
this.store.clear();
|
|
302
|
-
}
|
|
303
|
-
/**
|
|
304
|
-
* Set primary keys for a specific index key with optional comparison.
|
|
305
|
-
* If comparator is provided and returns true (no changes), skip the update.
|
|
306
|
-
*/
|
|
307
|
-
setPksWithComparison(key, newPks) {
|
|
308
|
-
return this.setSlotsWithComparison(key, this.resolveSlots(newPks));
|
|
295
|
+
slotsToPks(slots) {
|
|
296
|
+
const pks = /* @__PURE__ */ new Set();
|
|
297
|
+
for (const slot of slots) pks.add(slot.pk);
|
|
298
|
+
return pks;
|
|
309
299
|
}
|
|
310
300
|
setSlotsWithComparison(key, newSlots) {
|
|
311
301
|
if (this.comparePks) {
|
|
312
302
|
const existingSlotsSet = this.store.getOneByKey(key);
|
|
313
303
|
if (existingSlotsSet && existingSlotsSet.size === newSlots.size) {
|
|
314
|
-
|
|
315
|
-
this.slotsToPks(existingSlotsSet)
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
if (this.comparePks(existingPksArray, newPksArray)) {
|
|
304
|
+
if (this.comparePks(
|
|
305
|
+
Array.from(this.slotsToPks(existingSlotsSet)),
|
|
306
|
+
Array.from(this.slotsToPks(newSlots))
|
|
307
|
+
)) {
|
|
319
308
|
return false;
|
|
320
309
|
}
|
|
321
310
|
} else if (!existingSlotsSet && newSlots.size === 0) {
|
|
@@ -325,38 +314,6 @@ var OIMIndexSetBased = class {
|
|
|
325
314
|
this.store.setOneByKey(key, newSlots);
|
|
326
315
|
return true;
|
|
327
316
|
}
|
|
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
|
-
}
|
|
348
|
-
/**
|
|
349
|
-
* Emit update event with changed keys
|
|
350
|
-
*/
|
|
351
|
-
emitUpdate(keys) {
|
|
352
|
-
this.emitter.emit(0 /* UPDATE */, { keys });
|
|
353
|
-
}
|
|
354
|
-
/**
|
|
355
|
-
* Emit update event for a single key (fast-path override point).
|
|
356
|
-
*/
|
|
357
|
-
emitUpdateOne(key) {
|
|
358
|
-
this.emitUpdate([key]);
|
|
359
|
-
}
|
|
360
317
|
};
|
|
361
318
|
|
|
362
319
|
// src/core/OIMIndexStoreMapDrivenArrayBased.ts
|
|
@@ -404,17 +361,20 @@ var OIMIndexStoreMapDrivenArrayBased = class extends OIMIndexStoreArrayBased {
|
|
|
404
361
|
};
|
|
405
362
|
|
|
406
363
|
// src/abstract/OIMIndexArrayBased.ts
|
|
407
|
-
var OIMIndexArrayBased = class {
|
|
364
|
+
var OIMIndexArrayBased = class extends OIMIndex {
|
|
408
365
|
constructor(options = {}) {
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
366
|
+
super(
|
|
367
|
+
options.store ?? new OIMIndexStoreMapDrivenArrayBased(),
|
|
368
|
+
options.comparePks
|
|
369
|
+
);
|
|
370
|
+
}
|
|
371
|
+
getBucketSize(bucket) {
|
|
372
|
+
return bucket.length;
|
|
373
|
+
}
|
|
374
|
+
getPksByKey(key) {
|
|
375
|
+
const slotsArray = this.store.getOneByKey(key);
|
|
376
|
+
return slotsArray ? this.slotsToPks(slotsArray) : [];
|
|
414
377
|
}
|
|
415
|
-
/**
|
|
416
|
-
* Get primary keys for multiple index keys
|
|
417
|
-
*/
|
|
418
378
|
getPksByKeys(keys) {
|
|
419
379
|
const result = /* @__PURE__ */ new Map();
|
|
420
380
|
const slotsByKey = this.store.getManyByKeys(keys);
|
|
@@ -423,95 +383,17 @@ var OIMIndexArrayBased = class {
|
|
|
423
383
|
}
|
|
424
384
|
return result;
|
|
425
385
|
}
|
|
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
|
-
}
|
|
435
|
-
}
|
|
436
|
-
/**
|
|
437
|
-
* Get primary keys for a specific index key
|
|
438
|
-
*/
|
|
439
|
-
getPksByKey(key) {
|
|
440
|
-
const slotsArray = this.store.getOneByKey(key);
|
|
441
|
-
return slotsArray ? this.slotsToPks(slotsArray) : [];
|
|
442
|
-
}
|
|
443
386
|
getSlotsByKey(key) {
|
|
444
|
-
|
|
445
|
-
return slotsArray ? slotsArray : [];
|
|
387
|
+
return this.store.getOneByKey(key) ?? [];
|
|
446
388
|
}
|
|
447
389
|
getSlotsByKeys(keys) {
|
|
448
390
|
return this.store.getManyByKeys(keys);
|
|
449
391
|
}
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
return
|
|
455
|
-
}
|
|
456
|
-
/**
|
|
457
|
-
* Get all index keys
|
|
458
|
-
*/
|
|
459
|
-
getKeys() {
|
|
460
|
-
return this.store.getAllKeys();
|
|
461
|
-
}
|
|
462
|
-
/**
|
|
463
|
-
* Get the number of primary keys for a specific index key
|
|
464
|
-
*/
|
|
465
|
-
getKeySize(key) {
|
|
466
|
-
const slotsArray = this.store.getOneByKey(key);
|
|
467
|
-
return slotsArray ? slotsArray.length : 0;
|
|
468
|
-
}
|
|
469
|
-
/**
|
|
470
|
-
* Get total number of index keys
|
|
471
|
-
*/
|
|
472
|
-
get size() {
|
|
473
|
-
return this.store.countAll();
|
|
474
|
-
}
|
|
475
|
-
/**
|
|
476
|
-
* Check if the index is empty
|
|
477
|
-
*/
|
|
478
|
-
get isEmpty() {
|
|
479
|
-
return this.store.countAll() === 0;
|
|
480
|
-
}
|
|
481
|
-
/**
|
|
482
|
-
* Get performance metrics for monitoring and debugging
|
|
483
|
-
*/
|
|
484
|
-
getMetrics() {
|
|
485
|
-
let totalPks = 0;
|
|
486
|
-
let maxBucketSize = 0;
|
|
487
|
-
let minBucketSize = Infinity;
|
|
488
|
-
const allPks = this.store.getAll();
|
|
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);
|
|
493
|
-
}
|
|
494
|
-
return {
|
|
495
|
-
totalKeys: allPks.size,
|
|
496
|
-
totalPks,
|
|
497
|
-
averagePksPerKey: allPks.size > 0 ? totalPks / allPks.size : 0,
|
|
498
|
-
maxBucketSize: maxBucketSize === -Infinity ? 0 : maxBucketSize,
|
|
499
|
-
minBucketSize: minBucketSize === Infinity ? 0 : minBucketSize
|
|
500
|
-
};
|
|
501
|
-
}
|
|
502
|
-
/**
|
|
503
|
-
* Clean up event listeners when index is no longer needed
|
|
504
|
-
*/
|
|
505
|
-
destroy() {
|
|
506
|
-
this.emitter.offAll();
|
|
507
|
-
this.store.clear();
|
|
508
|
-
}
|
|
509
|
-
/**
|
|
510
|
-
* Set primary keys for a specific index key with optional comparison.
|
|
511
|
-
* If comparator is provided and returns true (no changes), skip the update.
|
|
512
|
-
*/
|
|
513
|
-
setPksWithComparison(key, newPks) {
|
|
514
|
-
return this.setSlotsWithComparison(key, this.resolveSlots(newPks));
|
|
392
|
+
slotsToPks(slots) {
|
|
393
|
+
const pks = [];
|
|
394
|
+
pks.length = slots.length;
|
|
395
|
+
for (let i = 0; i < slots.length; i++) pks[i] = slots[i].pk;
|
|
396
|
+
return pks;
|
|
515
397
|
}
|
|
516
398
|
setSlotsWithComparison(key, newSlots) {
|
|
517
399
|
if (this.comparePks) {
|
|
@@ -530,45 +412,9 @@ var OIMIndexArrayBased = class {
|
|
|
530
412
|
this.store.setOneByKey(key, newSlots);
|
|
531
413
|
return true;
|
|
532
414
|
}
|
|
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
|
-
}
|
|
557
|
-
/**
|
|
558
|
-
* Emit update event with changed keys
|
|
559
|
-
*/
|
|
560
|
-
emitUpdate(keys) {
|
|
561
|
-
this.emitter.emit(0 /* UPDATE */, { keys });
|
|
562
|
-
}
|
|
563
|
-
/**
|
|
564
|
-
* Emit update event for a single key (fast-path override point).
|
|
565
|
-
*/
|
|
566
|
-
emitUpdateOne(key) {
|
|
567
|
-
this.emitUpdate([key]);
|
|
568
|
-
}
|
|
569
415
|
};
|
|
570
416
|
|
|
571
|
-
// src/
|
|
417
|
+
// src/enums/EOIMEventQueueEventType.ts
|
|
572
418
|
var EOIMEventQueueEventType = /* @__PURE__ */ ((EOIMEventQueueEventType2) => {
|
|
573
419
|
EOIMEventQueueEventType2[EOIMEventQueueEventType2["AFTER_FLUSH"] = 0] = "AFTER_FLUSH";
|
|
574
420
|
EOIMEventQueueEventType2[EOIMEventQueueEventType2["BEFORE_FLUSH"] = 1] = "BEFORE_FLUSH";
|
|
@@ -822,23 +668,17 @@ var OIMUpdateEventEmitter = class {
|
|
|
822
668
|
}
|
|
823
669
|
};
|
|
824
670
|
|
|
825
|
-
// src/abstract/
|
|
826
|
-
var
|
|
671
|
+
// src/abstract/OIMReactiveIndex.ts
|
|
672
|
+
var OIMReactiveIndex = class {
|
|
827
673
|
constructor(queue, createIndex) {
|
|
828
674
|
this.updateEmitter = new OIMUpdateEventEmitter(queue);
|
|
829
675
|
this.index = createIndex(this.updateEmitter);
|
|
830
676
|
}
|
|
831
|
-
|
|
832
|
-
return this.index.
|
|
833
|
-
}
|
|
834
|
-
getPksByKeys(keys) {
|
|
835
|
-
return this.index.getPksByKeys(keys);
|
|
836
|
-
}
|
|
837
|
-
getSlotsByKey(key) {
|
|
838
|
-
return this.index.getSlotsByKey(key);
|
|
677
|
+
getEntitiesByKey(key) {
|
|
678
|
+
return this.index.getEntitiesByKey(key);
|
|
839
679
|
}
|
|
840
|
-
|
|
841
|
-
return this.index.
|
|
680
|
+
getEntitiesByKeys(keys) {
|
|
681
|
+
return this.index.getEntitiesByKeys(keys);
|
|
842
682
|
}
|
|
843
683
|
hasKey(key) {
|
|
844
684
|
return this.index.hasKey(key);
|
|
@@ -885,11 +725,10 @@ var OIMReactiveIndexSetBased = class {
|
|
|
885
725
|
}
|
|
886
726
|
};
|
|
887
727
|
|
|
888
|
-
// src/abstract/
|
|
889
|
-
var
|
|
728
|
+
// src/abstract/OIMReactiveIndexSetBased.ts
|
|
729
|
+
var OIMReactiveIndexSetBased = class extends OIMReactiveIndex {
|
|
890
730
|
constructor(queue, createIndex) {
|
|
891
|
-
|
|
892
|
-
this.index = createIndex(this.updateEmitter);
|
|
731
|
+
super(queue, createIndex);
|
|
893
732
|
}
|
|
894
733
|
getPksByKey(key) {
|
|
895
734
|
return this.index.getPksByKey(key);
|
|
@@ -903,48 +742,24 @@ var OIMReactiveIndexArrayBased = class {
|
|
|
903
742
|
getSlotsByKeys(keys) {
|
|
904
743
|
return this.index.getSlotsByKeys(keys);
|
|
905
744
|
}
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
getKeySize(key) {
|
|
913
|
-
return this.index.getKeySize(key);
|
|
914
|
-
}
|
|
915
|
-
get size() {
|
|
916
|
-
return this.index.size;
|
|
917
|
-
}
|
|
918
|
-
get isEmpty() {
|
|
919
|
-
return this.index.isEmpty;
|
|
920
|
-
}
|
|
921
|
-
getMetrics() {
|
|
922
|
-
return this.index.getMetrics();
|
|
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);
|
|
745
|
+
};
|
|
746
|
+
|
|
747
|
+
// src/abstract/OIMReactiveIndexArrayBased.ts
|
|
748
|
+
var OIMReactiveIndexArrayBased = class extends OIMReactiveIndex {
|
|
749
|
+
constructor(queue, createIndex) {
|
|
750
|
+
super(queue, createIndex);
|
|
935
751
|
}
|
|
936
|
-
|
|
937
|
-
return this.
|
|
752
|
+
getPksByKey(key) {
|
|
753
|
+
return this.index.getPksByKey(key);
|
|
938
754
|
}
|
|
939
|
-
|
|
940
|
-
return this.
|
|
755
|
+
getPksByKeys(keys) {
|
|
756
|
+
return this.index.getPksByKeys(keys);
|
|
941
757
|
}
|
|
942
|
-
|
|
943
|
-
return this.
|
|
758
|
+
getSlotsByKey(key) {
|
|
759
|
+
return this.index.getSlotsByKey(key);
|
|
944
760
|
}
|
|
945
|
-
|
|
946
|
-
this.
|
|
947
|
-
this.index.destroy();
|
|
761
|
+
getSlotsByKeys(keys) {
|
|
762
|
+
return this.index.getSlotsByKeys(keys);
|
|
948
763
|
}
|
|
949
764
|
};
|
|
950
765
|
|
|
@@ -969,14 +784,20 @@ var OIMCollectionStoreMapDriven = class extends OIMCollectionStore {
|
|
|
969
784
|
const slot = this.slots.get(pk);
|
|
970
785
|
if (slot) {
|
|
971
786
|
slot.item = entity;
|
|
787
|
+
return slot;
|
|
972
788
|
} else {
|
|
973
|
-
|
|
789
|
+
const nextSlot = { pk, item: entity };
|
|
790
|
+
this.slots.set(pk, nextSlot);
|
|
791
|
+
return nextSlot;
|
|
974
792
|
}
|
|
975
793
|
}
|
|
976
794
|
setManyByPks(pks, entities) {
|
|
795
|
+
const slots = [];
|
|
796
|
+
slots.length = pks.length;
|
|
977
797
|
for (let i = 0; i < pks.length; i++) {
|
|
978
|
-
this.setOneByPk(pks[i], entities[i]);
|
|
798
|
+
slots[i] = this.setOneByPk(pks[i], entities[i]);
|
|
979
799
|
}
|
|
800
|
+
return slots;
|
|
980
801
|
}
|
|
981
802
|
getSlotByPk(pk) {
|
|
982
803
|
return this.slots.get(pk);
|
|
@@ -1056,7 +877,7 @@ var OIMEntityUpdaterFactory = class {
|
|
|
1056
877
|
}
|
|
1057
878
|
};
|
|
1058
879
|
|
|
1059
|
-
// src/
|
|
880
|
+
// src/enums/EOIMCollectionEventType.ts
|
|
1060
881
|
var EOIMCollectionEventType = /* @__PURE__ */ ((EOIMCollectionEventType2) => {
|
|
1061
882
|
EOIMCollectionEventType2[EOIMCollectionEventType2["UPDATE"] = 0] = "UPDATE";
|
|
1062
883
|
return EOIMCollectionEventType2;
|
|
@@ -1086,18 +907,23 @@ var OIMCollection = class {
|
|
|
1086
907
|
return this.store.getAllSlots();
|
|
1087
908
|
}
|
|
1088
909
|
upsertOneByPk(pk, entity) {
|
|
1089
|
-
this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
910
|
+
const slot = this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1090
911
|
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
912
|
+
return slot;
|
|
1091
913
|
}
|
|
1092
914
|
upsertOne(entity) {
|
|
1093
|
-
const
|
|
1094
|
-
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
915
|
+
const slot = this.upsertOneWithoutNotifications(entity);
|
|
916
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [slot.pk] });
|
|
917
|
+
return slot;
|
|
1095
918
|
}
|
|
1096
919
|
upsertMany(entities) {
|
|
1097
|
-
|
|
920
|
+
if (entities.length === 0) return [];
|
|
921
|
+
const slots = entities.map(
|
|
1098
922
|
(entity) => this.upsertOneWithoutNotifications(entity)
|
|
1099
923
|
);
|
|
924
|
+
const pks = slots.map((slot) => slot.pk);
|
|
1100
925
|
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
926
|
+
return slots;
|
|
1101
927
|
}
|
|
1102
928
|
removeOne(entity) {
|
|
1103
929
|
const pk = this.selectPk(entity);
|
|
@@ -1105,6 +931,7 @@ var OIMCollection = class {
|
|
|
1105
931
|
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1106
932
|
}
|
|
1107
933
|
removeMany(entities) {
|
|
934
|
+
if (entities.length === 0) return;
|
|
1108
935
|
const pks = entities.map(this.selectPk);
|
|
1109
936
|
this.store.removeManyByPks(pks);
|
|
1110
937
|
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
@@ -1114,6 +941,7 @@ var OIMCollection = class {
|
|
|
1114
941
|
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1115
942
|
}
|
|
1116
943
|
removeManyByPks(pks) {
|
|
944
|
+
if (pks.length === 0) return;
|
|
1117
945
|
this.store.removeManyByPks(pks);
|
|
1118
946
|
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
1119
947
|
}
|
|
@@ -1132,8 +960,7 @@ var OIMCollection = class {
|
|
|
1132
960
|
}
|
|
1133
961
|
upsertOneWithoutNotifications(entity) {
|
|
1134
962
|
const pk = this.selectPk(entity);
|
|
1135
|
-
this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1136
|
-
return pk;
|
|
963
|
+
return this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1137
964
|
}
|
|
1138
965
|
upsertOneWithoutNotificationsByPk(pk, entity) {
|
|
1139
966
|
if (!pk) {
|
|
@@ -1143,12 +970,12 @@ var OIMCollection = class {
|
|
|
1143
970
|
}
|
|
1144
971
|
const existingEntity = this.store.getOneByPk(pk);
|
|
1145
972
|
if (existingEntity) {
|
|
1146
|
-
this.store.setOneByPk(
|
|
973
|
+
return this.store.setOneByPk(
|
|
1147
974
|
pk,
|
|
1148
975
|
this.updateEntity(entity, existingEntity)
|
|
1149
976
|
);
|
|
1150
977
|
} else {
|
|
1151
|
-
this.store.setOneByPk(pk, entity);
|
|
978
|
+
return this.store.setOneByPk(pk, entity);
|
|
1152
979
|
}
|
|
1153
980
|
}
|
|
1154
981
|
destroy() {
|
|
@@ -1209,24 +1036,29 @@ var OIMReactiveCollection = class extends OIMCollection {
|
|
|
1209
1036
|
};
|
|
1210
1037
|
}
|
|
1211
1038
|
upsertOneByPk(pk, entity) {
|
|
1212
|
-
this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1039
|
+
const slot = this.upsertOneWithoutNotificationsByPk(pk, entity);
|
|
1213
1040
|
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1214
1041
|
this.updateEmitter.markUpdatedKey(pk);
|
|
1215
1042
|
this.trackAnyUpdatePk(pk);
|
|
1043
|
+
return slot;
|
|
1216
1044
|
}
|
|
1217
1045
|
upsertOne(entity) {
|
|
1218
|
-
const
|
|
1219
|
-
this.emitter.emit(0 /* UPDATE */, { pks: [pk] });
|
|
1220
|
-
this.updateEmitter.markUpdatedKey(pk);
|
|
1221
|
-
this.trackAnyUpdatePk(pk);
|
|
1046
|
+
const slot = this.upsertOneWithoutNotifications(entity);
|
|
1047
|
+
this.emitter.emit(0 /* UPDATE */, { pks: [slot.pk] });
|
|
1048
|
+
this.updateEmitter.markUpdatedKey(slot.pk);
|
|
1049
|
+
this.trackAnyUpdatePk(slot.pk);
|
|
1050
|
+
return slot;
|
|
1222
1051
|
}
|
|
1223
1052
|
upsertMany(entities) {
|
|
1224
|
-
|
|
1053
|
+
if (entities.length === 0) return [];
|
|
1054
|
+
const slots = entities.map(
|
|
1225
1055
|
(entity) => this.upsertOneWithoutNotifications(entity)
|
|
1226
1056
|
);
|
|
1057
|
+
const pks = slots.map((slot) => slot.pk);
|
|
1227
1058
|
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
1228
1059
|
this.updateEmitter.markUpdatedKeys(pks);
|
|
1229
1060
|
this.trackAnyUpdatePks(pks);
|
|
1061
|
+
return slots;
|
|
1230
1062
|
}
|
|
1231
1063
|
removeOne(entity) {
|
|
1232
1064
|
const pk = this.selectPk(entity);
|
|
@@ -1236,6 +1068,7 @@ var OIMReactiveCollection = class extends OIMCollection {
|
|
|
1236
1068
|
this.trackAnyUpdatePk(pk);
|
|
1237
1069
|
}
|
|
1238
1070
|
removeMany(entities) {
|
|
1071
|
+
if (entities.length === 0) return;
|
|
1239
1072
|
const pks = entities.map(this.selectPk);
|
|
1240
1073
|
this.store.removeManyByPks(pks);
|
|
1241
1074
|
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
@@ -1249,6 +1082,7 @@ var OIMReactiveCollection = class extends OIMCollection {
|
|
|
1249
1082
|
this.trackAnyUpdatePk(pk);
|
|
1250
1083
|
}
|
|
1251
1084
|
removeManyByPks(pks) {
|
|
1085
|
+
if (pks.length === 0) return;
|
|
1252
1086
|
this.store.removeManyByPks(pks);
|
|
1253
1087
|
this.emitter.emit(0 /* UPDATE */, { pks });
|
|
1254
1088
|
this.updateEmitter.markUpdatedKeys(pks);
|
|
@@ -1294,202 +1128,347 @@ var OIMReactiveCollection = class extends OIMCollection {
|
|
|
1294
1128
|
}
|
|
1295
1129
|
};
|
|
1296
1130
|
|
|
1297
|
-
// src/
|
|
1298
|
-
var
|
|
1299
|
-
|
|
1300
|
-
|
|
1301
|
-
|
|
1302
|
-
|
|
1303
|
-
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
|
|
1308
|
-
|
|
1309
|
-
|
|
1310
|
-
|
|
1311
|
-
|
|
1312
|
-
get(key) {
|
|
1313
|
-
return this.properties[key];
|
|
1314
|
-
}
|
|
1315
|
-
getAll() {
|
|
1316
|
-
return { ...this.properties };
|
|
1131
|
+
// src/modules/wrapper/index/OIMIndexManualOrderedArrayBased.ts
|
|
1132
|
+
var OIMIndexManualOrderedArrayBased = class extends OIMIndexArrayBased {
|
|
1133
|
+
clear(key) {
|
|
1134
|
+
if (key === void 0) {
|
|
1135
|
+
const keys = this.getKeys();
|
|
1136
|
+
if (keys.length > 0) {
|
|
1137
|
+
this.store.clear();
|
|
1138
|
+
this.emitUpdate(Array.from(keys));
|
|
1139
|
+
}
|
|
1140
|
+
return;
|
|
1141
|
+
}
|
|
1142
|
+
if (this.store.getOneByKey(key) !== void 0) {
|
|
1143
|
+
this.store.removeOneByKey(key);
|
|
1144
|
+
this.emitUpdate([key]);
|
|
1145
|
+
}
|
|
1317
1146
|
}
|
|
1318
|
-
|
|
1319
|
-
|
|
1147
|
+
pushSlot(key, slot) {
|
|
1148
|
+
const list = this.getOrCreateList(key);
|
|
1149
|
+
const index = list.length;
|
|
1150
|
+
list.push(slot);
|
|
1151
|
+
this.emitUpdate([key]);
|
|
1152
|
+
return index;
|
|
1320
1153
|
}
|
|
1321
|
-
|
|
1322
|
-
|
|
1154
|
+
insertSlotAt(key, index, slot) {
|
|
1155
|
+
const list = this.getOrCreateList(key);
|
|
1156
|
+
const safeIndex = Math.max(0, Math.min(index, list.length));
|
|
1157
|
+
list.splice(safeIndex, 0, slot);
|
|
1158
|
+
this.emitUpdate([key]);
|
|
1159
|
+
return safeIndex;
|
|
1323
1160
|
}
|
|
1324
|
-
|
|
1325
|
-
|
|
1161
|
+
removeAt(key, index) {
|
|
1162
|
+
const list = this.store.getOneByKey(key);
|
|
1163
|
+
if (!list) return void 0;
|
|
1164
|
+
if (index < 0 || index >= list.length) return void 0;
|
|
1165
|
+
const [removed] = list.splice(index, 1);
|
|
1166
|
+
if (list.length === 0) {
|
|
1167
|
+
this.store.removeOneByKey(key);
|
|
1168
|
+
}
|
|
1169
|
+
this.emitUpdate([key]);
|
|
1170
|
+
return removed;
|
|
1326
1171
|
}
|
|
1327
|
-
|
|
1328
|
-
|
|
1172
|
+
move(key, fromIndex, toIndex) {
|
|
1173
|
+
const list = this.store.getOneByKey(key);
|
|
1174
|
+
if (!list) return void 0;
|
|
1175
|
+
if (fromIndex < 0 || fromIndex >= list.length) return void 0;
|
|
1176
|
+
if (toIndex < 0 || toIndex >= list.length) return void 0;
|
|
1177
|
+
if (fromIndex === toIndex) return list[fromIndex];
|
|
1178
|
+
const [slot] = list.splice(fromIndex, 1);
|
|
1179
|
+
if (slot === void 0) return void 0;
|
|
1180
|
+
list.splice(toIndex, 0, slot);
|
|
1181
|
+
this.emitUpdate([key]);
|
|
1182
|
+
return slot;
|
|
1329
1183
|
}
|
|
1330
|
-
|
|
1331
|
-
|
|
1184
|
+
resetSlots(key, slots) {
|
|
1185
|
+
if (slots.length === 0) {
|
|
1186
|
+
if (this.store.getOneByKey(key) !== void 0) {
|
|
1187
|
+
this.store.removeOneByKey(key);
|
|
1188
|
+
this.emitUpdate([key]);
|
|
1189
|
+
}
|
|
1190
|
+
return;
|
|
1191
|
+
}
|
|
1192
|
+
this.store.setOneByKey(key, slots.slice());
|
|
1193
|
+
this.emitUpdate([key]);
|
|
1332
1194
|
}
|
|
1333
|
-
|
|
1334
|
-
this.
|
|
1195
|
+
getOrCreateList(key) {
|
|
1196
|
+
let list = this.store.getOneByKey(key);
|
|
1197
|
+
if (!list) {
|
|
1198
|
+
list = [];
|
|
1199
|
+
this.store.setOneByKey(key, list);
|
|
1200
|
+
}
|
|
1201
|
+
return list;
|
|
1335
1202
|
}
|
|
1336
1203
|
};
|
|
1337
1204
|
|
|
1338
|
-
// src/
|
|
1339
|
-
var
|
|
1340
|
-
EOIMObjectEventType2[EOIMObjectEventType2["UPDATE"] = 0] = "UPDATE";
|
|
1341
|
-
return EOIMObjectEventType2;
|
|
1342
|
-
})(EOIMObjectEventType || {});
|
|
1343
|
-
|
|
1344
|
-
// src/core/OIMObject.ts
|
|
1345
|
-
var OIMObject = class {
|
|
1205
|
+
// src/modules/wrapper/index/OIMCollectionIndexManualOrderedArrayBased.ts
|
|
1206
|
+
var OIMCollectionIndexManualOrderedArrayBased = class extends OIMIndexManualOrderedArrayBased {
|
|
1346
1207
|
constructor(opts) {
|
|
1347
|
-
|
|
1348
|
-
this.
|
|
1208
|
+
super();
|
|
1209
|
+
this.resolveSlot = opts.collection !== void 0 ? (pk) => opts.collection.getSlotByPk(pk) : opts.resolveSlot;
|
|
1349
1210
|
}
|
|
1350
|
-
|
|
1351
|
-
this.
|
|
1352
|
-
this.emitter.emit(0 /* UPDATE */, { keys: [key] });
|
|
1211
|
+
push(key, pk) {
|
|
1212
|
+
return this.pushSlot(key, this.resolveRequiredSlot(pk));
|
|
1353
1213
|
}
|
|
1354
|
-
|
|
1355
|
-
this.
|
|
1356
|
-
this.emitter.emit(0 /* UPDATE */, {
|
|
1357
|
-
keys: Object.keys(draft)
|
|
1358
|
-
});
|
|
1214
|
+
insertAt(key, index, pk) {
|
|
1215
|
+
return this.insertSlotAt(key, index, this.resolveRequiredSlot(pk));
|
|
1359
1216
|
}
|
|
1360
|
-
|
|
1361
|
-
this.
|
|
1362
|
-
this.emitter.emit(0 /* UPDATE */, { keys: [key] });
|
|
1217
|
+
reset(key, pks) {
|
|
1218
|
+
this.resetSlots(key, this.resolveSlots(pks));
|
|
1363
1219
|
}
|
|
1364
|
-
|
|
1365
|
-
return
|
|
1220
|
+
getEntitiesByKey(key) {
|
|
1221
|
+
return super.getEntitiesByKey(key);
|
|
1366
1222
|
}
|
|
1367
|
-
|
|
1368
|
-
return
|
|
1223
|
+
getEntitiesByKeys(keys) {
|
|
1224
|
+
return super.getEntitiesByKeys(keys);
|
|
1369
1225
|
}
|
|
1370
|
-
|
|
1371
|
-
this.
|
|
1372
|
-
this.emitter.emit(0 /* UPDATE */, { keys: [] });
|
|
1226
|
+
resolvePk(pk) {
|
|
1227
|
+
return this.resolveRequiredSlot(pk);
|
|
1373
1228
|
}
|
|
1374
|
-
|
|
1375
|
-
|
|
1229
|
+
resolveSlots(pks) {
|
|
1230
|
+
const slots = [];
|
|
1231
|
+
slots.length = pks.length;
|
|
1232
|
+
for (let i = 0; i < pks.length; i++) {
|
|
1233
|
+
slots[i] = this.resolveRequiredSlot(pks[i]);
|
|
1234
|
+
}
|
|
1235
|
+
return slots;
|
|
1376
1236
|
}
|
|
1377
|
-
|
|
1378
|
-
|
|
1237
|
+
resolveRequiredSlot(pk) {
|
|
1238
|
+
const slot = this.resolveSlot(pk);
|
|
1239
|
+
if (!slot) {
|
|
1240
|
+
throw new Error(
|
|
1241
|
+
`[OIMCollectionIndexManualOrderedArrayBased]: Unable to resolve slot for PK "${String(pk)}".`
|
|
1242
|
+
);
|
|
1243
|
+
}
|
|
1244
|
+
return slot;
|
|
1379
1245
|
}
|
|
1380
|
-
|
|
1381
|
-
|
|
1246
|
+
};
|
|
1247
|
+
|
|
1248
|
+
// src/modules/wrapper/index/OIMOrderedListCommandStream.ts
|
|
1249
|
+
var OIMOrderedListCommandStream = class {
|
|
1250
|
+
constructor(queue, index) {
|
|
1251
|
+
this.isInWrite = false;
|
|
1252
|
+
this.commandsByKey = /* @__PURE__ */ new Map();
|
|
1253
|
+
this.onAfterFlush = () => {
|
|
1254
|
+
this.commandsByKey.clear();
|
|
1255
|
+
};
|
|
1256
|
+
this.onIndexUpdate = (payload) => {
|
|
1257
|
+
if (this.isInWrite) return;
|
|
1258
|
+
if (payload.keys.length === 0) return;
|
|
1259
|
+
for (let i = 0; i < payload.keys.length; i++) {
|
|
1260
|
+
const key = payload.keys[i];
|
|
1261
|
+
this.appendSetCommand(key, this.getSlotsByKey(key));
|
|
1262
|
+
}
|
|
1263
|
+
};
|
|
1264
|
+
this.commandsEventEmitter = new OIMUpdateEventEmitter(
|
|
1265
|
+
queue,
|
|
1266
|
+
"after_flush"
|
|
1267
|
+
);
|
|
1268
|
+
this.index = index ?? new OIMIndexManualOrderedArrayBased();
|
|
1269
|
+
this.unsubscribeAfterFlush = queue.emitter.on(
|
|
1270
|
+
0 /* AFTER_FLUSH */,
|
|
1271
|
+
this.onAfterFlush
|
|
1272
|
+
);
|
|
1273
|
+
this.unsubscribeFromIndexEmitter = this.index.emitter.on(
|
|
1274
|
+
0 /* UPDATE */,
|
|
1275
|
+
this.onIndexUpdate
|
|
1276
|
+
);
|
|
1382
1277
|
}
|
|
1383
|
-
|
|
1384
|
-
return this.
|
|
1278
|
+
getPksByKey(key) {
|
|
1279
|
+
return this.index.getPksByKey(key);
|
|
1385
1280
|
}
|
|
1386
|
-
|
|
1387
|
-
this.
|
|
1388
|
-
|
|
1281
|
+
getSlotsByKey(key) {
|
|
1282
|
+
return this.index.getSlotsByKey(
|
|
1283
|
+
key
|
|
1284
|
+
);
|
|
1389
1285
|
}
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
// src/core/OIMReactiveObject.ts
|
|
1393
|
-
var OIMReactiveObject = class extends OIMObject {
|
|
1394
|
-
constructor(queue, opts) {
|
|
1395
|
-
super(opts);
|
|
1396
|
-
this.updateEmitter = new OIMUpdateEventEmitter(queue, "queue");
|
|
1397
|
-
this.emitter.on(0 /* UPDATE */, (payload) => {
|
|
1398
|
-
this.updateEmitter.markUpdatedKeys(payload.keys);
|
|
1399
|
-
});
|
|
1286
|
+
getEntitiesByKey(key) {
|
|
1287
|
+
return this.index.getEntitiesByKey(key);
|
|
1400
1288
|
}
|
|
1401
|
-
|
|
1402
|
-
return this.
|
|
1289
|
+
hasKey(key) {
|
|
1290
|
+
return this.index.hasKey(key);
|
|
1403
1291
|
}
|
|
1404
|
-
|
|
1405
|
-
return this.
|
|
1292
|
+
getKeys() {
|
|
1293
|
+
return this.index.getKeys();
|
|
1406
1294
|
}
|
|
1407
|
-
|
|
1408
|
-
this.
|
|
1295
|
+
pushSlot(key, slot) {
|
|
1296
|
+
this.withWrite(() => {
|
|
1297
|
+
const index = this.index.pushSlot(key, slot);
|
|
1298
|
+
this.appendCommand(key, {
|
|
1299
|
+
type: "insert",
|
|
1300
|
+
pk: slot.pk,
|
|
1301
|
+
slot,
|
|
1302
|
+
index
|
|
1303
|
+
});
|
|
1304
|
+
});
|
|
1409
1305
|
}
|
|
1410
|
-
|
|
1411
|
-
this.
|
|
1306
|
+
insertSlotAt(key, index, slot) {
|
|
1307
|
+
this.withWrite(() => {
|
|
1308
|
+
const safeIndex = this.index.insertSlotAt(key, index, slot);
|
|
1309
|
+
this.appendCommand(key, {
|
|
1310
|
+
type: "insert",
|
|
1311
|
+
pk: slot.pk,
|
|
1312
|
+
slot,
|
|
1313
|
+
index: safeIndex
|
|
1314
|
+
});
|
|
1315
|
+
});
|
|
1412
1316
|
}
|
|
1413
|
-
|
|
1414
|
-
|
|
1317
|
+
removeAt(key, index) {
|
|
1318
|
+
this.withWrite(() => {
|
|
1319
|
+
const slot = this.index.removeAt(key, index);
|
|
1320
|
+
if (slot === void 0) return;
|
|
1321
|
+
this.appendCommand(key, {
|
|
1322
|
+
type: "remove",
|
|
1323
|
+
pk: slot.pk,
|
|
1324
|
+
slot,
|
|
1325
|
+
index
|
|
1326
|
+
});
|
|
1327
|
+
});
|
|
1415
1328
|
}
|
|
1416
|
-
|
|
1417
|
-
|
|
1329
|
+
move(key, fromIndex, toIndex) {
|
|
1330
|
+
this.withWrite(() => {
|
|
1331
|
+
const slot = this.index.move(key, fromIndex, toIndex);
|
|
1332
|
+
if (slot === void 0) return;
|
|
1333
|
+
this.appendCommand(key, {
|
|
1334
|
+
type: "move",
|
|
1335
|
+
pk: slot.pk,
|
|
1336
|
+
slot,
|
|
1337
|
+
fromIndex,
|
|
1338
|
+
toIndex
|
|
1339
|
+
});
|
|
1340
|
+
});
|
|
1418
1341
|
}
|
|
1419
|
-
|
|
1420
|
-
|
|
1342
|
+
setSlots(key, slots) {
|
|
1343
|
+
this.withWrite(() => {
|
|
1344
|
+
this.index.resetSlots(key, slots);
|
|
1345
|
+
this.appendSetCommand(key, slots);
|
|
1346
|
+
});
|
|
1421
1347
|
}
|
|
1422
|
-
|
|
1423
|
-
this.
|
|
1424
|
-
super.destroy();
|
|
1348
|
+
getBufferedCommands(key) {
|
|
1349
|
+
return this.commandsByKey.get(key) ?? [];
|
|
1425
1350
|
}
|
|
1426
|
-
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
constructor(options = {}) {
|
|
1431
|
-
super(options);
|
|
1351
|
+
consumeCommands(key) {
|
|
1352
|
+
const cmds = this.commandsByKey.get(key);
|
|
1353
|
+
if (!cmds || cmds.length === 0) return [];
|
|
1354
|
+
return cmds.slice();
|
|
1432
1355
|
}
|
|
1433
|
-
|
|
1434
|
-
|
|
1435
|
-
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
const hasChanges = this.setPksWithComparison(key, new Set(pks));
|
|
1439
|
-
if (hasChanges) {
|
|
1440
|
-
this.emitUpdateOne(key);
|
|
1356
|
+
clear(key) {
|
|
1357
|
+
if (key === void 0) {
|
|
1358
|
+
this.index.destroy();
|
|
1359
|
+
this.commandsByKey.clear();
|
|
1360
|
+
return;
|
|
1441
1361
|
}
|
|
1362
|
+
this.index.clear(key);
|
|
1363
|
+
this.commandsByKey.delete(key);
|
|
1442
1364
|
}
|
|
1443
|
-
|
|
1444
|
-
|
|
1445
|
-
|
|
1446
|
-
|
|
1447
|
-
|
|
1365
|
+
destroy() {
|
|
1366
|
+
this.commandsEventEmitter.destroy();
|
|
1367
|
+
this.unsubscribeAfterFlush();
|
|
1368
|
+
this.unsubscribeFromIndexEmitter();
|
|
1369
|
+
this.clear();
|
|
1448
1370
|
}
|
|
1449
|
-
|
|
1450
|
-
|
|
1451
|
-
|
|
1452
|
-
|
|
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
|
-
}
|
|
1371
|
+
withWrite(fn) {
|
|
1372
|
+
if (this.isInWrite) {
|
|
1373
|
+
fn();
|
|
1374
|
+
return;
|
|
1467
1375
|
}
|
|
1468
|
-
|
|
1469
|
-
|
|
1470
|
-
|
|
1376
|
+
this.isInWrite = true;
|
|
1377
|
+
try {
|
|
1378
|
+
fn();
|
|
1379
|
+
} finally {
|
|
1380
|
+
this.isInWrite = false;
|
|
1471
1381
|
}
|
|
1472
1382
|
}
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
|
|
1476
|
-
|
|
1477
|
-
|
|
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
|
-
}
|
|
1383
|
+
appendCommand(key, cmd) {
|
|
1384
|
+
let cmds = this.commandsByKey.get(key);
|
|
1385
|
+
if (!cmds) {
|
|
1386
|
+
cmds = [];
|
|
1387
|
+
this.commandsByKey.set(key, cmds);
|
|
1486
1388
|
}
|
|
1487
|
-
if (
|
|
1488
|
-
|
|
1489
|
-
|
|
1490
|
-
} else if (
|
|
1491
|
-
this.
|
|
1389
|
+
if (cmd.type === "set") {
|
|
1390
|
+
cmds.length = 0;
|
|
1391
|
+
cmds.push(cmd);
|
|
1392
|
+
} else if (cmds.length > 0 && cmds[0].type === "set") {
|
|
1393
|
+
const slots = this.getSlotsByKey(key);
|
|
1394
|
+
cmds[0] = this.createSetCommand(slots);
|
|
1395
|
+
} else {
|
|
1396
|
+
cmds.push(cmd);
|
|
1492
1397
|
}
|
|
1398
|
+
this.commandsEventEmitter.markUpdatedKeys([key]);
|
|
1399
|
+
}
|
|
1400
|
+
appendSetCommand(key, slots) {
|
|
1401
|
+
this.appendCommand(key, this.createSetCommand(slots));
|
|
1402
|
+
}
|
|
1403
|
+
createSetCommand(slots) {
|
|
1404
|
+
return {
|
|
1405
|
+
type: "set",
|
|
1406
|
+
pks: slots.map((slot) => slot.pk),
|
|
1407
|
+
slots
|
|
1408
|
+
};
|
|
1409
|
+
}
|
|
1410
|
+
};
|
|
1411
|
+
|
|
1412
|
+
// src/modules/wrapper/index/OIMCollectionOrderedListCommandStream.ts
|
|
1413
|
+
var OIMCollectionOrderedListCommandStream = class extends OIMOrderedListCommandStream {
|
|
1414
|
+
constructor(queue, opts) {
|
|
1415
|
+
const index = opts.index ?? new OIMCollectionIndexManualOrderedArrayBased(
|
|
1416
|
+
opts.collection !== void 0 ? { collection: opts.collection } : { resolveSlot: opts.resolveSlot }
|
|
1417
|
+
);
|
|
1418
|
+
super(queue, index);
|
|
1419
|
+
this.index = index;
|
|
1420
|
+
}
|
|
1421
|
+
push(key, pk) {
|
|
1422
|
+
this.withWrite(() => {
|
|
1423
|
+
const slot = this.resolvePk(pk);
|
|
1424
|
+
const index = this.index.pushSlot(key, slot);
|
|
1425
|
+
this.appendCommand(key, {
|
|
1426
|
+
type: "insert",
|
|
1427
|
+
pk,
|
|
1428
|
+
slot,
|
|
1429
|
+
index
|
|
1430
|
+
});
|
|
1431
|
+
});
|
|
1432
|
+
}
|
|
1433
|
+
insertAt(key, index, pk) {
|
|
1434
|
+
this.withWrite(() => {
|
|
1435
|
+
const slot = this.resolvePk(pk);
|
|
1436
|
+
const safeIndex = this.index.insertSlotAt(key, index, slot);
|
|
1437
|
+
this.appendCommand(key, {
|
|
1438
|
+
type: "insert",
|
|
1439
|
+
pk,
|
|
1440
|
+
slot,
|
|
1441
|
+
index: safeIndex
|
|
1442
|
+
});
|
|
1443
|
+
});
|
|
1444
|
+
}
|
|
1445
|
+
set(key, pks) {
|
|
1446
|
+
this.withWrite(() => {
|
|
1447
|
+
const slots = pks.map((pk) => this.resolvePk(pk));
|
|
1448
|
+
this.index.resetSlots(key, slots);
|
|
1449
|
+
this.appendSetCommand(key, slots);
|
|
1450
|
+
});
|
|
1451
|
+
}
|
|
1452
|
+
getSlotsByKey(key) {
|
|
1453
|
+
return this.index.getSlotsByKey(
|
|
1454
|
+
key
|
|
1455
|
+
);
|
|
1456
|
+
}
|
|
1457
|
+
getEntitiesByKey(key) {
|
|
1458
|
+
return this.index.getEntitiesByKey(key);
|
|
1459
|
+
}
|
|
1460
|
+
resolvePk(pk) {
|
|
1461
|
+
return this.index.resolvePk(pk);
|
|
1462
|
+
}
|
|
1463
|
+
};
|
|
1464
|
+
|
|
1465
|
+
// src/core/OIMIndexManualArrayBased.ts
|
|
1466
|
+
var OIMIndexManualArrayBased = class extends OIMIndexArrayBased {
|
|
1467
|
+
constructor(options = {}) {
|
|
1468
|
+
super(options);
|
|
1469
|
+
}
|
|
1470
|
+
setSlots(key, slots) {
|
|
1471
|
+
const hasChanges = this.setSlotsWithComparison(key, slots);
|
|
1493
1472
|
if (hasChanges) {
|
|
1494
1473
|
this.emitUpdateOne(key);
|
|
1495
1474
|
}
|
|
@@ -1513,8 +1492,8 @@ var OIMIndexManualSetBased = class extends OIMIndexSetBased {
|
|
|
1513
1492
|
}
|
|
1514
1493
|
};
|
|
1515
1494
|
|
|
1516
|
-
// src/core/
|
|
1517
|
-
var
|
|
1495
|
+
// src/core/OIMReactiveIndexManualArrayBased.ts
|
|
1496
|
+
var OIMIndexManualArrayBasedReactive = class extends OIMIndexManualArrayBased {
|
|
1518
1497
|
constructor(updateEmitter, opts) {
|
|
1519
1498
|
super(opts);
|
|
1520
1499
|
this.updateEmitter = updateEmitter;
|
|
@@ -1526,94 +1505,93 @@ var OIMIndexManualSetBasedReactive = class extends OIMIndexManualSetBased {
|
|
|
1526
1505
|
this.updateEmitter.markUpdatedKey(key);
|
|
1527
1506
|
}
|
|
1528
1507
|
};
|
|
1529
|
-
var
|
|
1508
|
+
var OIMReactiveIndexManualArrayBased = class extends OIMReactiveIndexArrayBased {
|
|
1530
1509
|
constructor(queue, opts) {
|
|
1531
1510
|
super(queue, (updateEmitter) => {
|
|
1532
|
-
return new
|
|
1511
|
+
return new OIMIndexManualArrayBasedReactive(
|
|
1533
1512
|
updateEmitter,
|
|
1534
1513
|
opts?.indexOptions
|
|
1535
1514
|
);
|
|
1536
1515
|
});
|
|
1537
1516
|
}
|
|
1538
|
-
setPks(key, pks) {
|
|
1539
|
-
this.index.setPks(key, pks);
|
|
1540
|
-
}
|
|
1541
1517
|
setSlots(key, slots) {
|
|
1542
1518
|
this.index.setSlots(key, slots);
|
|
1543
1519
|
}
|
|
1544
|
-
addPks(key, pks) {
|
|
1545
|
-
this.index.addPks(key, pks);
|
|
1546
|
-
}
|
|
1547
|
-
removePks(key, pks) {
|
|
1548
|
-
this.index.removePks(key, pks);
|
|
1549
|
-
}
|
|
1550
1520
|
clear(key) {
|
|
1551
1521
|
this.index.clear(key);
|
|
1552
1522
|
}
|
|
1553
1523
|
};
|
|
1554
1524
|
|
|
1555
|
-
// src/core/
|
|
1556
|
-
var
|
|
1557
|
-
constructor(
|
|
1558
|
-
|
|
1525
|
+
// src/core/OIMReactiveCollectionIndexManualArrayBased.ts
|
|
1526
|
+
var OIMReactiveCollectionIndexManualArrayBased = class extends OIMReactiveIndexManualArrayBased {
|
|
1527
|
+
constructor(queue, opts) {
|
|
1528
|
+
const resolveSlot = opts.collection !== void 0 ? (pk) => opts.collection.getSlotByPk(pk) : opts.resolveSlot;
|
|
1529
|
+
super(queue, {
|
|
1530
|
+
indexOptions: opts.indexOptions
|
|
1531
|
+
});
|
|
1532
|
+
this.resolveSlot = resolveSlot;
|
|
1559
1533
|
}
|
|
1560
|
-
/**
|
|
1561
|
-
* Set primary keys for a specific index key, replacing any existing values.
|
|
1562
|
-
* Uses optional comparator to skip updates if PKs haven't actually changed.
|
|
1563
|
-
*/
|
|
1564
1534
|
setPks(key, pks) {
|
|
1565
|
-
|
|
1566
|
-
if (hasChanges) {
|
|
1567
|
-
this.emitUpdateOne(key);
|
|
1568
|
-
}
|
|
1569
|
-
}
|
|
1570
|
-
setSlots(key, slots) {
|
|
1571
|
-
const hasChanges = this.setSlotsWithComparison(key, slots);
|
|
1572
|
-
if (hasChanges) {
|
|
1573
|
-
this.emitUpdateOne(key);
|
|
1574
|
-
}
|
|
1535
|
+
this.setSlots(key, this.resolveSlots(pks));
|
|
1575
1536
|
}
|
|
1576
|
-
/**
|
|
1577
|
-
* Add primary keys to a specific index key
|
|
1578
|
-
*/
|
|
1579
1537
|
addPks(key, pks) {
|
|
1580
1538
|
if (pks.length === 0) return;
|
|
1581
|
-
|
|
1582
|
-
|
|
1583
|
-
|
|
1584
|
-
this.store.setOneByKey(key, slotsArray);
|
|
1585
|
-
}
|
|
1586
|
-
const pksSet = new Set(slotsArray.map((slot) => slot.pk));
|
|
1539
|
+
const existingSlots = this.index.getSlotsByKey(key);
|
|
1540
|
+
const existingPks = new Set(existingSlots.map((slot) => slot.pk));
|
|
1541
|
+
const nextSlots = existingSlots.slice();
|
|
1587
1542
|
let hasChanges = false;
|
|
1588
|
-
const nextSlots = slotsArray.slice();
|
|
1589
1543
|
for (const pk of pks) {
|
|
1590
|
-
if (
|
|
1591
|
-
|
|
1592
|
-
|
|
1593
|
-
|
|
1594
|
-
}
|
|
1595
|
-
}
|
|
1596
|
-
if (hasChanges) {
|
|
1597
|
-
this.store.setOneByKey(key, nextSlots);
|
|
1598
|
-
this.emitUpdateOne(key);
|
|
1544
|
+
if (existingPks.has(pk)) continue;
|
|
1545
|
+
nextSlots.push(this.resolveRequiredSlot(pk));
|
|
1546
|
+
existingPks.add(pk);
|
|
1547
|
+
hasChanges = true;
|
|
1599
1548
|
}
|
|
1549
|
+
if (hasChanges) this.setSlots(key, nextSlots);
|
|
1600
1550
|
}
|
|
1601
|
-
/**
|
|
1602
|
-
* Remove primary keys from a specific index key
|
|
1603
|
-
*/
|
|
1604
1551
|
removePks(key, pks) {
|
|
1605
1552
|
if (pks.length === 0) return;
|
|
1606
|
-
const
|
|
1607
|
-
|
|
1608
|
-
const
|
|
1609
|
-
|
|
1610
|
-
|
|
1553
|
+
const pksToRemove = new Set(pks);
|
|
1554
|
+
const existingSlots = this.index.getSlotsByKey(key);
|
|
1555
|
+
const nextSlots = existingSlots.filter(
|
|
1556
|
+
(slot) => !pksToRemove.has(slot.pk)
|
|
1557
|
+
);
|
|
1558
|
+
if (nextSlots.length === existingSlots.length) return;
|
|
1559
|
+
if (nextSlots.length === 0) this.clear(key);
|
|
1560
|
+
else this.setSlots(key, nextSlots);
|
|
1561
|
+
}
|
|
1562
|
+
getEntitiesByKey(key) {
|
|
1563
|
+
return super.getEntitiesByKey(key);
|
|
1564
|
+
}
|
|
1565
|
+
getEntitiesByKeys(keys) {
|
|
1566
|
+
return super.getEntitiesByKeys(keys);
|
|
1567
|
+
}
|
|
1568
|
+
resolveSlots(pks) {
|
|
1569
|
+
const slots = [];
|
|
1570
|
+
slots.length = pks.length;
|
|
1571
|
+
for (let i = 0; i < pks.length; i++) {
|
|
1572
|
+
slots[i] = this.resolveRequiredSlot(pks[i]);
|
|
1573
|
+
}
|
|
1574
|
+
return slots;
|
|
1575
|
+
}
|
|
1576
|
+
resolveRequiredSlot(pk) {
|
|
1577
|
+
const slot = this.resolveSlot(pk);
|
|
1578
|
+
if (!slot) {
|
|
1579
|
+
throw new Error(
|
|
1580
|
+
`[OIMReactiveCollectionIndexManualArrayBased]: Unable to resolve slot for PK "${String(pk)}".`
|
|
1581
|
+
);
|
|
1582
|
+
}
|
|
1583
|
+
return slot;
|
|
1584
|
+
}
|
|
1585
|
+
};
|
|
1586
|
+
|
|
1587
|
+
// src/core/OIMIndexManualSetBased.ts
|
|
1588
|
+
var OIMIndexManualSetBased = class extends OIMIndexSetBased {
|
|
1589
|
+
constructor(options = {}) {
|
|
1590
|
+
super(options);
|
|
1591
|
+
}
|
|
1592
|
+
setSlots(key, slots) {
|
|
1593
|
+
const hasChanges = this.setSlotsWithComparison(key, new Set(slots));
|
|
1611
1594
|
if (hasChanges) {
|
|
1612
|
-
if (filtered.length === 0) {
|
|
1613
|
-
this.store.removeOneByKey(key);
|
|
1614
|
-
} else {
|
|
1615
|
-
this.store.setOneByKey(key, filtered);
|
|
1616
|
-
}
|
|
1617
1595
|
this.emitUpdateOne(key);
|
|
1618
1596
|
}
|
|
1619
1597
|
}
|
|
@@ -1636,8 +1614,8 @@ var OIMIndexManualArrayBased = class extends OIMIndexArrayBased {
|
|
|
1636
1614
|
}
|
|
1637
1615
|
};
|
|
1638
1616
|
|
|
1639
|
-
// src/core/
|
|
1640
|
-
var
|
|
1617
|
+
// src/core/OIMReactiveIndexManualSetBased.ts
|
|
1618
|
+
var OIMIndexManualSetBasedReactive = class extends OIMIndexManualSetBased {
|
|
1641
1619
|
constructor(updateEmitter, opts) {
|
|
1642
1620
|
super(opts);
|
|
1643
1621
|
this.updateEmitter = updateEmitter;
|
|
@@ -1649,310 +1627,1256 @@ var OIMIndexManualArrayBasedReactive = class extends OIMIndexManualArrayBased {
|
|
|
1649
1627
|
this.updateEmitter.markUpdatedKey(key);
|
|
1650
1628
|
}
|
|
1651
1629
|
};
|
|
1652
|
-
var
|
|
1630
|
+
var OIMReactiveIndexManualSetBased = class extends OIMReactiveIndexSetBased {
|
|
1653
1631
|
constructor(queue, opts) {
|
|
1654
1632
|
super(queue, (updateEmitter) => {
|
|
1655
|
-
return new
|
|
1633
|
+
return new OIMIndexManualSetBasedReactive(
|
|
1656
1634
|
updateEmitter,
|
|
1657
1635
|
opts?.indexOptions
|
|
1658
1636
|
);
|
|
1659
1637
|
});
|
|
1660
1638
|
}
|
|
1661
|
-
setPks(key, pks) {
|
|
1662
|
-
this.index.setPks(key, pks);
|
|
1663
|
-
}
|
|
1664
1639
|
setSlots(key, slots) {
|
|
1665
1640
|
this.index.setSlots(key, slots);
|
|
1666
1641
|
}
|
|
1667
|
-
addPks(key, pks) {
|
|
1668
|
-
this.index.addPks(key, pks);
|
|
1669
|
-
}
|
|
1670
|
-
removePks(key, pks) {
|
|
1671
|
-
this.index.removePks(key, pks);
|
|
1672
|
-
}
|
|
1673
1642
|
clear(key) {
|
|
1674
1643
|
this.index.clear(key);
|
|
1675
1644
|
}
|
|
1676
1645
|
};
|
|
1677
1646
|
|
|
1678
|
-
// src/core/
|
|
1679
|
-
var
|
|
1647
|
+
// src/core/OIMReactiveCollectionIndexManualSetBased.ts
|
|
1648
|
+
var OIMReactiveCollectionIndexManualSetBased = class extends OIMReactiveIndexManualSetBased {
|
|
1680
1649
|
constructor(queue, opts) {
|
|
1681
|
-
|
|
1682
|
-
|
|
1683
|
-
|
|
1684
|
-
|
|
1685
|
-
|
|
1686
|
-
}
|
|
1687
|
-
}
|
|
1688
|
-
};
|
|
1689
|
-
|
|
1690
|
-
// src/core/OIMObjectStoreMapDriven.ts
|
|
1691
|
-
var OIMObjectStoreMapDriven = class extends OIMObjectStore {
|
|
1692
|
-
constructor() {
|
|
1693
|
-
super(...arguments);
|
|
1694
|
-
this.properties = /* @__PURE__ */ new Map();
|
|
1650
|
+
const resolveSlot = opts.collection !== void 0 ? (pk) => opts.collection.getSlotByPk(pk) : opts.resolveSlot;
|
|
1651
|
+
super(queue, {
|
|
1652
|
+
indexOptions: opts.indexOptions
|
|
1653
|
+
});
|
|
1654
|
+
this.resolveSlot = resolveSlot;
|
|
1695
1655
|
}
|
|
1696
|
-
|
|
1697
|
-
this.
|
|
1656
|
+
setPks(key, pks) {
|
|
1657
|
+
this.setSlots(key, this.resolveSlots(pks));
|
|
1698
1658
|
}
|
|
1699
|
-
|
|
1700
|
-
|
|
1701
|
-
|
|
1702
|
-
|
|
1703
|
-
|
|
1704
|
-
|
|
1705
|
-
|
|
1659
|
+
addPks(key, pks) {
|
|
1660
|
+
if (pks.length === 0) return;
|
|
1661
|
+
const existingSlots = this.index.getSlotsByKey(key);
|
|
1662
|
+
const existingPks = this.index.getPksByKey(key);
|
|
1663
|
+
const nextSlots = new Set(existingSlots);
|
|
1664
|
+
let hasChanges = false;
|
|
1665
|
+
for (const pk of pks) {
|
|
1666
|
+
if (existingPks.has(pk)) continue;
|
|
1667
|
+
const slot = this.resolveRequiredSlot(pk);
|
|
1668
|
+
nextSlots.add(slot);
|
|
1669
|
+
existingPks.add(pk);
|
|
1670
|
+
hasChanges = true;
|
|
1706
1671
|
}
|
|
1672
|
+
if (hasChanges) this.setSlots(key, nextSlots);
|
|
1707
1673
|
}
|
|
1708
|
-
|
|
1709
|
-
|
|
1674
|
+
removePks(key, pks) {
|
|
1675
|
+
if (pks.length === 0) return;
|
|
1676
|
+
const pksToRemove = new Set(pks);
|
|
1677
|
+
const existingSlots = this.index.getSlotsByKey(key);
|
|
1678
|
+
const nextSlots = /* @__PURE__ */ new Set();
|
|
1679
|
+
let hasChanges = false;
|
|
1680
|
+
for (const slot of existingSlots) {
|
|
1681
|
+
if (pksToRemove.has(slot.pk)) {
|
|
1682
|
+
hasChanges = true;
|
|
1683
|
+
} else {
|
|
1684
|
+
nextSlots.add(slot);
|
|
1685
|
+
}
|
|
1686
|
+
}
|
|
1687
|
+
if (!hasChanges) return;
|
|
1688
|
+
if (nextSlots.size === 0) this.clear(key);
|
|
1689
|
+
else this.setSlots(key, nextSlots);
|
|
1710
1690
|
}
|
|
1711
|
-
|
|
1712
|
-
return
|
|
1691
|
+
getEntitiesByKey(key) {
|
|
1692
|
+
return super.getEntitiesByKey(key);
|
|
1713
1693
|
}
|
|
1714
|
-
|
|
1715
|
-
return
|
|
1694
|
+
getEntitiesByKeys(keys) {
|
|
1695
|
+
return super.getEntitiesByKeys(keys);
|
|
1716
1696
|
}
|
|
1717
|
-
|
|
1718
|
-
|
|
1697
|
+
resolveSlots(pks) {
|
|
1698
|
+
const slots = /* @__PURE__ */ new Set();
|
|
1699
|
+
for (const pk of pks) slots.add(this.resolveRequiredSlot(pk));
|
|
1700
|
+
return slots;
|
|
1719
1701
|
}
|
|
1720
|
-
|
|
1721
|
-
|
|
1702
|
+
resolveRequiredSlot(pk) {
|
|
1703
|
+
const slot = this.resolveSlot(pk);
|
|
1704
|
+
if (!slot) {
|
|
1705
|
+
throw new Error(
|
|
1706
|
+
`[OIMReactiveCollectionIndexManualSetBased]: Unable to resolve slot for PK "${String(pk)}".`
|
|
1707
|
+
);
|
|
1708
|
+
}
|
|
1709
|
+
return slot;
|
|
1722
1710
|
}
|
|
1723
|
-
|
|
1724
|
-
|
|
1711
|
+
};
|
|
1712
|
+
|
|
1713
|
+
// src/core/OIMDerivedCollectionIndexSetBased.ts
|
|
1714
|
+
var OIMDerivedCollectionIndexSetBased = class extends OIMReactiveCollectionIndexManualSetBased {
|
|
1715
|
+
constructor(queue, collection, opts) {
|
|
1716
|
+
super(queue, {
|
|
1717
|
+
collection,
|
|
1718
|
+
indexOptions: opts.indexOptions
|
|
1719
|
+
});
|
|
1720
|
+
this.keysByPk = /* @__PURE__ */ new Map();
|
|
1721
|
+
this.onCollectionUpdate = (pks) => {
|
|
1722
|
+
if (pks.length === 0) {
|
|
1723
|
+
this.rebuildFromCollection();
|
|
1724
|
+
return;
|
|
1725
|
+
}
|
|
1726
|
+
for (const pk of pks) {
|
|
1727
|
+
this.syncPk(pk);
|
|
1728
|
+
}
|
|
1729
|
+
};
|
|
1730
|
+
this.collection = collection;
|
|
1731
|
+
this.selectIndexKeys = opts.selectIndexKeys;
|
|
1732
|
+
this.unsubscribeFromCollection = collection.emitter.on(
|
|
1733
|
+
0 /* UPDATE */,
|
|
1734
|
+
(payload) => this.onCollectionUpdate(payload.pks)
|
|
1735
|
+
);
|
|
1736
|
+
if (opts.buildInitial !== false) {
|
|
1737
|
+
this.rebuildFromCollection();
|
|
1738
|
+
}
|
|
1725
1739
|
}
|
|
1726
|
-
|
|
1727
|
-
|
|
1740
|
+
rebuildFromCollection() {
|
|
1741
|
+
this.keysByPk.clear();
|
|
1742
|
+
super.clear();
|
|
1743
|
+
const slotsByKey = /* @__PURE__ */ new Map();
|
|
1744
|
+
const slots = this.collection.getAllSlots();
|
|
1745
|
+
for (const slot of slots) {
|
|
1746
|
+
if (slot.item === void 0) continue;
|
|
1747
|
+
const keys = this.normalizeKeys(this.selectIndexKeys(slot.item));
|
|
1748
|
+
if (keys.length === 0) continue;
|
|
1749
|
+
this.keysByPk.set(slot.pk, new Set(keys));
|
|
1750
|
+
for (const key of keys) {
|
|
1751
|
+
let slotsForKey = slotsByKey.get(key);
|
|
1752
|
+
if (!slotsForKey) {
|
|
1753
|
+
slotsForKey = /* @__PURE__ */ new Set();
|
|
1754
|
+
slotsByKey.set(key, slotsForKey);
|
|
1755
|
+
}
|
|
1756
|
+
slotsForKey.add(slot);
|
|
1757
|
+
}
|
|
1758
|
+
}
|
|
1759
|
+
for (const [key, keySlots] of slotsByKey) {
|
|
1760
|
+
this.setSlots(key, keySlots);
|
|
1761
|
+
}
|
|
1728
1762
|
}
|
|
1729
|
-
|
|
1730
|
-
|
|
1763
|
+
clear(key) {
|
|
1764
|
+
if (key === void 0) {
|
|
1765
|
+
this.keysByPk.clear();
|
|
1766
|
+
} else {
|
|
1767
|
+
for (const keys of this.keysByPk.values()) {
|
|
1768
|
+
keys.delete(key);
|
|
1769
|
+
}
|
|
1770
|
+
}
|
|
1771
|
+
super.clear(key);
|
|
1731
1772
|
}
|
|
1732
1773
|
destroy() {
|
|
1733
|
-
this.
|
|
1774
|
+
this.unsubscribeFromCollection();
|
|
1775
|
+
this.keysByPk.clear();
|
|
1776
|
+
super.destroy();
|
|
1734
1777
|
}
|
|
1735
|
-
|
|
1736
|
-
|
|
1737
|
-
|
|
1738
|
-
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
if (
|
|
1742
|
-
|
|
1743
|
-
const kb = Object.keys(b);
|
|
1744
|
-
if (ka.length !== kb.length) return true;
|
|
1745
|
-
for (let i = 0; i < ka.length; i++) {
|
|
1746
|
-
const k = ka[i];
|
|
1747
|
-
if (b[k] !== a[k])
|
|
1748
|
-
return true;
|
|
1778
|
+
syncPk(pk) {
|
|
1779
|
+
const prevKeys = this.keysByPk.get(pk) ?? /* @__PURE__ */ new Set();
|
|
1780
|
+
const slot = this.collection.getSlotByPk(pk);
|
|
1781
|
+
const entity = slot?.item;
|
|
1782
|
+
const nextKeys = entity === void 0 ? /* @__PURE__ */ new Set() : new Set(this.normalizeKeys(this.selectIndexKeys(entity)));
|
|
1783
|
+
for (const key of prevKeys) {
|
|
1784
|
+
if (!nextKeys.has(key)) {
|
|
1785
|
+
this.removePks(key, [pk]);
|
|
1749
1786
|
}
|
|
1750
|
-
|
|
1751
|
-
|
|
1787
|
+
}
|
|
1788
|
+
if (entity !== void 0) {
|
|
1789
|
+
for (const key of nextKeys) {
|
|
1790
|
+
if (!prevKeys.has(key)) {
|
|
1791
|
+
this.addPks(key, [pk]);
|
|
1792
|
+
}
|
|
1793
|
+
}
|
|
1794
|
+
}
|
|
1795
|
+
if (nextKeys.size === 0) {
|
|
1796
|
+
this.keysByPk.delete(pk);
|
|
1797
|
+
} else {
|
|
1798
|
+
this.keysByPk.set(pk, nextKeys);
|
|
1799
|
+
}
|
|
1752
1800
|
}
|
|
1753
|
-
|
|
1754
|
-
|
|
1755
|
-
|
|
1756
|
-
|
|
1757
|
-
|
|
1758
|
-
|
|
1759
|
-
|
|
1760
|
-
|
|
1761
|
-
|
|
1762
|
-
if (this.scheduler) {
|
|
1763
|
-
this.flushBound = () => this.flush();
|
|
1764
|
-
this.scheduler.on(
|
|
1765
|
-
0 /* FLUSH */,
|
|
1766
|
-
this.flushBound
|
|
1767
|
-
);
|
|
1801
|
+
normalizeKeys(keys) {
|
|
1802
|
+
if (keys === void 0 || keys === null) return [];
|
|
1803
|
+
const rawKeys = Array.isArray(keys) ? keys : [keys];
|
|
1804
|
+
const result = [];
|
|
1805
|
+
const seen = /* @__PURE__ */ new Set();
|
|
1806
|
+
for (const key of rawKeys) {
|
|
1807
|
+
if (seen.has(key)) continue;
|
|
1808
|
+
seen.add(key);
|
|
1809
|
+
result.push(key);
|
|
1768
1810
|
}
|
|
1811
|
+
return result;
|
|
1769
1812
|
}
|
|
1770
|
-
|
|
1771
|
-
|
|
1772
|
-
|
|
1773
|
-
|
|
1774
|
-
|
|
1775
|
-
|
|
1776
|
-
|
|
1777
|
-
|
|
1778
|
-
|
|
1779
|
-
|
|
1780
|
-
this.
|
|
1781
|
-
|
|
1782
|
-
|
|
1783
|
-
|
|
1784
|
-
|
|
1785
|
-
|
|
1813
|
+
};
|
|
1814
|
+
|
|
1815
|
+
// src/core/OIMDerivedCollectionIndexArrayBased.ts
|
|
1816
|
+
var OIMDerivedCollectionIndexArrayBased = class extends OIMReactiveCollectionIndexManualArrayBased {
|
|
1817
|
+
constructor(queue, collection, opts) {
|
|
1818
|
+
super(queue, {
|
|
1819
|
+
collection,
|
|
1820
|
+
indexOptions: opts.indexOptions
|
|
1821
|
+
});
|
|
1822
|
+
this.keysByPk = /* @__PURE__ */ new Map();
|
|
1823
|
+
this.onCollectionUpdate = (pks) => {
|
|
1824
|
+
if (pks.length === 0) {
|
|
1825
|
+
this.rebuildFromCollection();
|
|
1826
|
+
return;
|
|
1827
|
+
}
|
|
1828
|
+
const affectedKeys = /* @__PURE__ */ new Set();
|
|
1829
|
+
for (const pk of pks) {
|
|
1830
|
+
this.trackPkKeys(pk, affectedKeys);
|
|
1831
|
+
}
|
|
1832
|
+
for (const key of affectedKeys) {
|
|
1833
|
+
this.rebuildKey(key);
|
|
1834
|
+
}
|
|
1786
1835
|
};
|
|
1836
|
+
this.collection = collection;
|
|
1837
|
+
this.selectIndexKeys = opts.selectIndexKeys;
|
|
1838
|
+
this.compareEntities = opts.compareEntities;
|
|
1839
|
+
this.orderBy = opts.orderBy;
|
|
1840
|
+
this.unsubscribeFromCollection = collection.emitter.on(
|
|
1841
|
+
0 /* UPDATE */,
|
|
1842
|
+
(payload) => this.onCollectionUpdate(payload.pks)
|
|
1843
|
+
);
|
|
1844
|
+
if (opts.buildInitial !== false) {
|
|
1845
|
+
this.rebuildFromCollection();
|
|
1846
|
+
}
|
|
1787
1847
|
}
|
|
1788
|
-
|
|
1789
|
-
|
|
1790
|
-
|
|
1791
|
-
|
|
1792
|
-
|
|
1793
|
-
|
|
1794
|
-
|
|
1795
|
-
|
|
1796
|
-
|
|
1797
|
-
|
|
1798
|
-
|
|
1799
|
-
|
|
1800
|
-
|
|
1801
|
-
|
|
1802
|
-
|
|
1803
|
-
|
|
1804
|
-
|
|
1805
|
-
|
|
1806
|
-
|
|
1807
|
-
const
|
|
1808
|
-
|
|
1809
|
-
for (let i = 0; i < snapshot.length; i++) {
|
|
1810
|
-
snapshot[i]();
|
|
1848
|
+
rebuildFromCollection() {
|
|
1849
|
+
this.keysByPk.clear();
|
|
1850
|
+
super.clear();
|
|
1851
|
+
const slotsByKey = /* @__PURE__ */ new Map();
|
|
1852
|
+
const slots = this.collection.getAllSlots();
|
|
1853
|
+
for (const slot of slots) {
|
|
1854
|
+
if (slot.item === void 0) continue;
|
|
1855
|
+
const keys = this.normalizeKeys(this.selectIndexKeys(slot.item));
|
|
1856
|
+
if (keys.length === 0) continue;
|
|
1857
|
+
this.keysByPk.set(slot.pk, new Set(keys));
|
|
1858
|
+
for (const key of keys) {
|
|
1859
|
+
let slotsForKey = slotsByKey.get(key);
|
|
1860
|
+
if (!slotsForKey) {
|
|
1861
|
+
slotsForKey = [];
|
|
1862
|
+
slotsByKey.set(key, slotsForKey);
|
|
1863
|
+
}
|
|
1864
|
+
slotsForKey.push(slot);
|
|
1865
|
+
}
|
|
1866
|
+
}
|
|
1867
|
+
for (const [key, keySlots] of slotsByKey) {
|
|
1868
|
+
this.setSlots(key, this.sortSlots(keySlots));
|
|
1811
1869
|
}
|
|
1812
|
-
this.isFlushing = false;
|
|
1813
|
-
this.emitter.emit(0 /* AFTER_FLUSH */, void 0);
|
|
1814
1870
|
}
|
|
1815
|
-
|
|
1816
|
-
|
|
1817
|
-
|
|
1818
|
-
|
|
1819
|
-
|
|
1871
|
+
clear(key) {
|
|
1872
|
+
if (key === void 0) {
|
|
1873
|
+
this.keysByPk.clear();
|
|
1874
|
+
} else {
|
|
1875
|
+
for (const keys of this.keysByPk.values()) {
|
|
1876
|
+
keys.delete(key);
|
|
1877
|
+
}
|
|
1878
|
+
}
|
|
1879
|
+
super.clear(key);
|
|
1820
1880
|
}
|
|
1821
|
-
|
|
1822
|
-
|
|
1823
|
-
|
|
1824
|
-
|
|
1825
|
-
return this.tasks.size === 0;
|
|
1881
|
+
destroy() {
|
|
1882
|
+
this.unsubscribeFromCollection();
|
|
1883
|
+
this.keysByPk.clear();
|
|
1884
|
+
super.destroy();
|
|
1826
1885
|
}
|
|
1827
|
-
|
|
1828
|
-
|
|
1829
|
-
|
|
1830
|
-
|
|
1831
|
-
|
|
1832
|
-
this.
|
|
1886
|
+
trackPkKeys(pk, affectedKeys) {
|
|
1887
|
+
const prevKeys = this.keysByPk.get(pk) ?? /* @__PURE__ */ new Set();
|
|
1888
|
+
for (const key of prevKeys) affectedKeys.add(key);
|
|
1889
|
+
const slot = this.collection.getSlotByPk(pk);
|
|
1890
|
+
const entity = slot?.item;
|
|
1891
|
+
const nextKeys = entity === void 0 ? /* @__PURE__ */ new Set() : new Set(this.normalizeKeys(this.selectIndexKeys(entity)));
|
|
1892
|
+
for (const key of nextKeys) affectedKeys.add(key);
|
|
1893
|
+
if (nextKeys.size === 0) {
|
|
1894
|
+
this.keysByPk.delete(pk);
|
|
1895
|
+
} else {
|
|
1896
|
+
this.keysByPk.set(pk, nextKeys);
|
|
1897
|
+
}
|
|
1833
1898
|
}
|
|
1834
|
-
|
|
1835
|
-
|
|
1836
|
-
|
|
1837
|
-
|
|
1838
|
-
|
|
1899
|
+
rebuildKey(key) {
|
|
1900
|
+
const keySlots = [];
|
|
1901
|
+
const slots = this.collection.getAllSlots();
|
|
1902
|
+
for (const slot of slots) {
|
|
1903
|
+
if (slot.item === void 0) continue;
|
|
1904
|
+
const keys = this.keysByPk.get(slot.pk);
|
|
1905
|
+
if (keys?.has(key)) keySlots.push(slot);
|
|
1906
|
+
}
|
|
1907
|
+
if (keySlots.length === 0) {
|
|
1908
|
+
super.clear(key);
|
|
1909
|
+
} else {
|
|
1910
|
+
this.setSlots(key, this.sortSlots(keySlots));
|
|
1839
1911
|
}
|
|
1840
1912
|
}
|
|
1841
|
-
|
|
1842
|
-
|
|
1843
|
-
|
|
1844
|
-
|
|
1845
|
-
|
|
1846
|
-
|
|
1847
|
-
|
|
1848
|
-
this.
|
|
1849
|
-
|
|
1913
|
+
sortSlots(slots) {
|
|
1914
|
+
if (!this.compareEntities && !this.orderBy) return slots;
|
|
1915
|
+
return slots.slice().sort((a, b) => {
|
|
1916
|
+
const aItem = a.item;
|
|
1917
|
+
const bItem = b.item;
|
|
1918
|
+
if (aItem === void 0 || bItem === void 0) return 0;
|
|
1919
|
+
if (this.compareEntities) {
|
|
1920
|
+
return this.compareEntities(aItem, bItem);
|
|
1921
|
+
}
|
|
1922
|
+
const aValue = this.orderBy(aItem);
|
|
1923
|
+
const bValue = this.orderBy(bItem);
|
|
1924
|
+
if (aValue < bValue) return -1;
|
|
1925
|
+
if (aValue > bValue) return 1;
|
|
1926
|
+
return 0;
|
|
1927
|
+
});
|
|
1928
|
+
}
|
|
1929
|
+
normalizeKeys(keys) {
|
|
1930
|
+
if (keys === void 0 || keys === null) return [];
|
|
1931
|
+
const rawKeys = Array.isArray(keys) ? keys : [keys];
|
|
1932
|
+
const result = [];
|
|
1933
|
+
const seen = /* @__PURE__ */ new Set();
|
|
1934
|
+
for (const key of rawKeys) {
|
|
1935
|
+
if (seen.has(key)) continue;
|
|
1936
|
+
seen.add(key);
|
|
1937
|
+
result.push(key);
|
|
1850
1938
|
}
|
|
1851
|
-
|
|
1939
|
+
return result;
|
|
1852
1940
|
}
|
|
1853
1941
|
};
|
|
1854
1942
|
|
|
1855
|
-
// src/core/
|
|
1856
|
-
var
|
|
1857
|
-
|
|
1858
|
-
|
|
1859
|
-
|
|
1860
|
-
|
|
1861
|
-
|
|
1862
|
-
return (
|
|
1863
|
-
|
|
1864
|
-
|
|
1943
|
+
// src/core/OIMCollectionIndexFactory.ts
|
|
1944
|
+
var OIMCollectionIndexFactory = class {
|
|
1945
|
+
constructor(queue, collection) {
|
|
1946
|
+
this.queue = queue;
|
|
1947
|
+
this.collection = collection;
|
|
1948
|
+
}
|
|
1949
|
+
setBasedIndex(opts = {}) {
|
|
1950
|
+
return new OIMReactiveCollectionIndexManualSetBased(this.queue, {
|
|
1951
|
+
collection: this.collection,
|
|
1952
|
+
indexOptions: opts.indexOptions
|
|
1953
|
+
});
|
|
1954
|
+
}
|
|
1955
|
+
derivedSetIndex(selectIndexKeys, opts = {}) {
|
|
1956
|
+
return new OIMDerivedCollectionIndexSetBased(
|
|
1957
|
+
this.queue,
|
|
1958
|
+
this.collection,
|
|
1959
|
+
{
|
|
1960
|
+
selectIndexKeys,
|
|
1961
|
+
buildInitial: opts.buildInitial,
|
|
1962
|
+
indexOptions: opts.indexOptions
|
|
1865
1963
|
}
|
|
1866
|
-
|
|
1867
|
-
|
|
1868
|
-
|
|
1869
|
-
|
|
1964
|
+
);
|
|
1965
|
+
}
|
|
1966
|
+
arrayBasedIndex(opts = {}) {
|
|
1967
|
+
return new OIMReactiveCollectionIndexManualArrayBased(this.queue, {
|
|
1968
|
+
collection: this.collection,
|
|
1969
|
+
indexOptions: opts.indexOptions
|
|
1970
|
+
});
|
|
1971
|
+
}
|
|
1972
|
+
derivedArrayIndex(selectIndexKeys, opts = {}) {
|
|
1973
|
+
return new OIMDerivedCollectionIndexArrayBased(
|
|
1974
|
+
this.queue,
|
|
1975
|
+
this.collection,
|
|
1976
|
+
{
|
|
1977
|
+
selectIndexKeys,
|
|
1978
|
+
buildInitial: opts.buildInitial,
|
|
1979
|
+
compareEntities: opts.compareEntities,
|
|
1980
|
+
orderBy: opts.orderBy,
|
|
1981
|
+
indexOptions: opts.indexOptions
|
|
1870
1982
|
}
|
|
1871
|
-
|
|
1872
|
-
};
|
|
1983
|
+
);
|
|
1873
1984
|
}
|
|
1874
|
-
|
|
1875
|
-
|
|
1876
|
-
|
|
1877
|
-
|
|
1878
|
-
|
|
1879
|
-
|
|
1880
|
-
|
|
1881
|
-
|
|
1882
|
-
}
|
|
1883
|
-
|
|
1884
|
-
|
|
1885
|
-
|
|
1886
|
-
|
|
1887
|
-
|
|
1888
|
-
|
|
1889
|
-
|
|
1890
|
-
|
|
1891
|
-
|
|
1985
|
+
orderedIndex() {
|
|
1986
|
+
return new OIMCollectionIndexManualOrderedArrayBased({
|
|
1987
|
+
collection: this.collection
|
|
1988
|
+
});
|
|
1989
|
+
}
|
|
1990
|
+
orderedList(opts = {}) {
|
|
1991
|
+
return new OIMCollectionOrderedListCommandStream(
|
|
1992
|
+
this.queue,
|
|
1993
|
+
opts.index ? { collection: this.collection, index: opts.index } : { collection: this.collection }
|
|
1994
|
+
);
|
|
1995
|
+
}
|
|
1996
|
+
};
|
|
1997
|
+
function createOIMCollectionIndexFactory(queue, collection) {
|
|
1998
|
+
return new OIMCollectionIndexFactory(queue, collection);
|
|
1999
|
+
}
|
|
2000
|
+
|
|
2001
|
+
// src/core/OIMObjectStoreRecordDriven.ts
|
|
2002
|
+
var OIMObjectStoreRecordDriven = class extends OIMObjectStore {
|
|
2003
|
+
constructor(initial) {
|
|
2004
|
+
super();
|
|
2005
|
+
this.properties = Object.assign(/* @__PURE__ */ Object.create(null), initial ?? {});
|
|
2006
|
+
}
|
|
2007
|
+
setProperty(key, value) {
|
|
2008
|
+
this.properties[key] = value;
|
|
2009
|
+
}
|
|
2010
|
+
merge(draft) {
|
|
2011
|
+
Object.assign(this.properties, draft);
|
|
2012
|
+
}
|
|
2013
|
+
delete(key) {
|
|
2014
|
+
delete this.properties[key];
|
|
2015
|
+
}
|
|
2016
|
+
get(key) {
|
|
2017
|
+
return this.properties[key];
|
|
2018
|
+
}
|
|
2019
|
+
getAll() {
|
|
2020
|
+
return { ...this.properties };
|
|
2021
|
+
}
|
|
2022
|
+
clear() {
|
|
2023
|
+
this.properties = /* @__PURE__ */ Object.create(null);
|
|
2024
|
+
}
|
|
2025
|
+
count() {
|
|
2026
|
+
return Object.keys(this.properties).length;
|
|
2027
|
+
}
|
|
2028
|
+
keys() {
|
|
2029
|
+
return Object.keys(this.properties);
|
|
2030
|
+
}
|
|
2031
|
+
values() {
|
|
2032
|
+
return Object.values(this.properties);
|
|
2033
|
+
}
|
|
2034
|
+
entries() {
|
|
2035
|
+
return Object.entries(this.properties);
|
|
2036
|
+
}
|
|
2037
|
+
destroy() {
|
|
2038
|
+
this.clear();
|
|
2039
|
+
}
|
|
2040
|
+
};
|
|
2041
|
+
|
|
2042
|
+
// src/enums/EOIMObjectEventType.ts
|
|
2043
|
+
var EOIMObjectEventType = /* @__PURE__ */ ((EOIMObjectEventType2) => {
|
|
2044
|
+
EOIMObjectEventType2[EOIMObjectEventType2["UPDATE"] = 0] = "UPDATE";
|
|
2045
|
+
return EOIMObjectEventType2;
|
|
2046
|
+
})(EOIMObjectEventType || {});
|
|
2047
|
+
|
|
2048
|
+
// src/core/OIMObject.ts
|
|
2049
|
+
var OIMObject = class {
|
|
2050
|
+
constructor(opts) {
|
|
2051
|
+
this.emitter = new OIMEventEmitter();
|
|
2052
|
+
this.store = opts?.store ?? new OIMObjectStoreRecordDriven();
|
|
2053
|
+
}
|
|
2054
|
+
setProperty(key, value) {
|
|
2055
|
+
this.store.setProperty(key, value);
|
|
2056
|
+
this.emitter.emit(0 /* UPDATE */, { keys: [key] });
|
|
2057
|
+
}
|
|
2058
|
+
merge(draft) {
|
|
2059
|
+
this.store.merge(draft);
|
|
2060
|
+
this.emitter.emit(0 /* UPDATE */, {
|
|
2061
|
+
keys: Object.keys(draft)
|
|
2062
|
+
});
|
|
2063
|
+
}
|
|
2064
|
+
delete(key) {
|
|
2065
|
+
this.store.delete(key);
|
|
2066
|
+
this.emitter.emit(0 /* UPDATE */, { keys: [key] });
|
|
2067
|
+
}
|
|
2068
|
+
get(key) {
|
|
2069
|
+
return this.store.get(key);
|
|
2070
|
+
}
|
|
2071
|
+
getAll() {
|
|
2072
|
+
return this.store.getAll();
|
|
2073
|
+
}
|
|
2074
|
+
clear() {
|
|
2075
|
+
this.store.clear();
|
|
2076
|
+
this.emitter.emit(0 /* UPDATE */, { keys: [] });
|
|
2077
|
+
}
|
|
2078
|
+
count() {
|
|
2079
|
+
return this.store.count();
|
|
2080
|
+
}
|
|
2081
|
+
keys() {
|
|
2082
|
+
return this.store.keys();
|
|
2083
|
+
}
|
|
2084
|
+
values() {
|
|
2085
|
+
return this.store.values();
|
|
2086
|
+
}
|
|
2087
|
+
entries() {
|
|
2088
|
+
return this.store.entries();
|
|
2089
|
+
}
|
|
2090
|
+
destroy() {
|
|
2091
|
+
this.store.destroy();
|
|
2092
|
+
this.emitter.offAll();
|
|
2093
|
+
}
|
|
2094
|
+
};
|
|
2095
|
+
|
|
2096
|
+
// src/core/OIMReactiveObject.ts
|
|
2097
|
+
var OIMReactiveObject = class extends OIMObject {
|
|
2098
|
+
constructor(queue, opts) {
|
|
2099
|
+
super(opts);
|
|
2100
|
+
this.updateEmitter = new OIMUpdateEventEmitter(queue, "queue");
|
|
2101
|
+
this.emitter.on(0 /* UPDATE */, (payload) => {
|
|
2102
|
+
this.updateEmitter.markUpdatedKeys(payload.keys);
|
|
2103
|
+
});
|
|
2104
|
+
}
|
|
2105
|
+
subscribeOnKey(key, handler) {
|
|
2106
|
+
return this.updateEmitter.subscribeOnKey(key, handler);
|
|
2107
|
+
}
|
|
2108
|
+
subscribeOnKeys(keys, handler) {
|
|
2109
|
+
return this.updateEmitter.subscribeOnKeys(keys, handler);
|
|
2110
|
+
}
|
|
2111
|
+
unsubscribeFromKey(key, handler) {
|
|
2112
|
+
this.updateEmitter.unsubscribeFromKey(key, handler);
|
|
2113
|
+
}
|
|
2114
|
+
unsubscribeFromKeys(keys, handler) {
|
|
2115
|
+
this.updateEmitter.unsubscribeFromKeys(keys, handler);
|
|
2116
|
+
}
|
|
2117
|
+
hasSubscriptions() {
|
|
2118
|
+
return this.updateEmitter.hasSubscriptions();
|
|
2119
|
+
}
|
|
2120
|
+
getHandlerCount(key) {
|
|
2121
|
+
return this.updateEmitter.getHandlerCount(key);
|
|
2122
|
+
}
|
|
2123
|
+
getMetrics() {
|
|
2124
|
+
return this.updateEmitter.getMetrics();
|
|
2125
|
+
}
|
|
2126
|
+
destroy() {
|
|
2127
|
+
this.updateEmitter.destroy();
|
|
2128
|
+
super.destroy();
|
|
2129
|
+
}
|
|
2130
|
+
};
|
|
2131
|
+
|
|
2132
|
+
// src/core/OIMObjectStoreMapDriven.ts
|
|
2133
|
+
var OIMObjectStoreMapDriven = class extends OIMObjectStore {
|
|
2134
|
+
constructor() {
|
|
2135
|
+
super(...arguments);
|
|
2136
|
+
this.properties = /* @__PURE__ */ new Map();
|
|
2137
|
+
}
|
|
2138
|
+
setProperty(key, value) {
|
|
2139
|
+
this.properties.set(key, value);
|
|
2140
|
+
}
|
|
2141
|
+
merge(draft) {
|
|
2142
|
+
for (const key in draft) {
|
|
2143
|
+
if (!Object.prototype.hasOwnProperty.call(draft, key)) continue;
|
|
2144
|
+
this.properties.set(
|
|
2145
|
+
key,
|
|
2146
|
+
draft[key]
|
|
2147
|
+
);
|
|
2148
|
+
}
|
|
2149
|
+
}
|
|
2150
|
+
delete(key) {
|
|
2151
|
+
this.properties.delete(key);
|
|
2152
|
+
}
|
|
2153
|
+
get(key) {
|
|
2154
|
+
return this.properties.get(key);
|
|
2155
|
+
}
|
|
2156
|
+
getAll() {
|
|
2157
|
+
return Object.fromEntries(this.properties.entries());
|
|
2158
|
+
}
|
|
2159
|
+
clear() {
|
|
2160
|
+
this.properties.clear();
|
|
2161
|
+
}
|
|
2162
|
+
count() {
|
|
2163
|
+
return this.properties.size;
|
|
2164
|
+
}
|
|
2165
|
+
keys() {
|
|
2166
|
+
return Array.from(this.properties.keys());
|
|
2167
|
+
}
|
|
2168
|
+
values() {
|
|
2169
|
+
return Array.from(this.properties.values());
|
|
2170
|
+
}
|
|
2171
|
+
entries() {
|
|
2172
|
+
return Array.from(this.properties.entries());
|
|
2173
|
+
}
|
|
2174
|
+
destroy() {
|
|
2175
|
+
this.properties.clear();
|
|
2176
|
+
}
|
|
2177
|
+
};
|
|
2178
|
+
|
|
2179
|
+
// src/core/OIMComparatorFactory.ts
|
|
2180
|
+
var OIMComparatorFactory = class {
|
|
2181
|
+
createShallowComparator() {
|
|
2182
|
+
return (a, b) => {
|
|
2183
|
+
if (a === b) return false;
|
|
2184
|
+
const ka = Object.keys(a);
|
|
2185
|
+
const kb = Object.keys(b);
|
|
2186
|
+
if (ka.length !== kb.length) return true;
|
|
2187
|
+
for (let i = 0; i < ka.length; i++) {
|
|
2188
|
+
const k = ka[i];
|
|
2189
|
+
if (b[k] !== a[k])
|
|
2190
|
+
return true;
|
|
1892
2191
|
}
|
|
1893
|
-
return
|
|
2192
|
+
return false;
|
|
1894
2193
|
};
|
|
1895
2194
|
}
|
|
2195
|
+
};
|
|
2196
|
+
|
|
2197
|
+
// src/core/OIMEventQueue.ts
|
|
2198
|
+
var OIMEventQueue = class {
|
|
2199
|
+
constructor(options = {}) {
|
|
2200
|
+
this.emitter = new OIMEventEmitter();
|
|
2201
|
+
this.tasks = /* @__PURE__ */ new Set();
|
|
2202
|
+
this.isFlushing = false;
|
|
2203
|
+
this.scheduler = options.scheduler;
|
|
2204
|
+
if (this.scheduler) {
|
|
2205
|
+
this.flushBound = () => this.flush();
|
|
2206
|
+
this.scheduler.on(
|
|
2207
|
+
0 /* FLUSH */,
|
|
2208
|
+
this.flushBound
|
|
2209
|
+
);
|
|
2210
|
+
}
|
|
2211
|
+
}
|
|
1896
2212
|
/**
|
|
1897
|
-
*
|
|
1898
|
-
*
|
|
2213
|
+
* Enqueue a one-shot task to be executed on the next flush.
|
|
2214
|
+
* Returns a dequeue function that can be called to cancel the task before it runs.
|
|
1899
2215
|
*/
|
|
1900
|
-
|
|
1901
|
-
|
|
1902
|
-
|
|
2216
|
+
enqueue(fn) {
|
|
2217
|
+
let isActive = true;
|
|
2218
|
+
const task = () => {
|
|
2219
|
+
if (!isActive) return;
|
|
2220
|
+
fn();
|
|
1903
2221
|
};
|
|
2222
|
+
this.tasks.add(task);
|
|
2223
|
+
this.ensureScheduled();
|
|
2224
|
+
return () => {
|
|
2225
|
+
if (!isActive) return;
|
|
2226
|
+
isActive = false;
|
|
2227
|
+
this.tasks.delete(task);
|
|
2228
|
+
};
|
|
2229
|
+
}
|
|
2230
|
+
get isInFlush() {
|
|
2231
|
+
return this.isFlushing;
|
|
1904
2232
|
}
|
|
1905
2233
|
/**
|
|
1906
|
-
*
|
|
1907
|
-
* Useful for disabling comparison while keeping the same interface.
|
|
2234
|
+
* Dequeue (cancel) a previously enqueued task by its dequeue function.
|
|
1908
2235
|
*/
|
|
1909
|
-
|
|
1910
|
-
|
|
2236
|
+
dequeue(dequeueFn) {
|
|
2237
|
+
dequeueFn();
|
|
2238
|
+
}
|
|
2239
|
+
/**
|
|
2240
|
+
* Execute all pending tasks.
|
|
2241
|
+
*
|
|
2242
|
+
* This flush drains until the queue is empty. If tasks enqueue more tasks, they will be
|
|
2243
|
+
* executed within the same flush.
|
|
2244
|
+
*/
|
|
2245
|
+
flush() {
|
|
2246
|
+
this.scheduler?.cancel();
|
|
2247
|
+
this.isFlushing = true;
|
|
2248
|
+
this.emitter.emit(1 /* BEFORE_FLUSH */, void 0);
|
|
2249
|
+
const snapshot = Array.from(this.tasks);
|
|
2250
|
+
this.tasks.clear();
|
|
2251
|
+
for (let i = 0; i < snapshot.length; i++) {
|
|
2252
|
+
snapshot[i]();
|
|
2253
|
+
}
|
|
2254
|
+
this.isFlushing = false;
|
|
2255
|
+
this.emitter.emit(0 /* AFTER_FLUSH */, void 0);
|
|
2256
|
+
}
|
|
2257
|
+
/**
|
|
2258
|
+
* Get the current number of queued functions.
|
|
2259
|
+
*/
|
|
2260
|
+
get length() {
|
|
2261
|
+
return this.tasks.size;
|
|
2262
|
+
}
|
|
2263
|
+
/**
|
|
2264
|
+
* Check if the queue is empty.
|
|
2265
|
+
*/
|
|
2266
|
+
get isEmpty() {
|
|
2267
|
+
return this.tasks.size === 0;
|
|
2268
|
+
}
|
|
2269
|
+
/**
|
|
2270
|
+
* Clear the queue without executing functions and cancel any scheduled flush.
|
|
2271
|
+
*/
|
|
2272
|
+
clear() {
|
|
2273
|
+
this.tasks.clear();
|
|
2274
|
+
this.scheduler?.cancel();
|
|
2275
|
+
}
|
|
2276
|
+
ensureScheduled() {
|
|
2277
|
+
if (!this.scheduler) return;
|
|
2278
|
+
if (this.isFlushing) return;
|
|
2279
|
+
if (this.tasks.size === 1) {
|
|
2280
|
+
this.scheduler.schedule();
|
|
2281
|
+
}
|
|
2282
|
+
}
|
|
2283
|
+
/**
|
|
2284
|
+
* Clean up scheduler subscription when queue is no longer needed.
|
|
2285
|
+
*/
|
|
2286
|
+
destroy() {
|
|
2287
|
+
if (this.scheduler && this.flushBound) {
|
|
2288
|
+
this.scheduler.off(
|
|
2289
|
+
0 /* FLUSH */,
|
|
2290
|
+
this.flushBound
|
|
2291
|
+
);
|
|
2292
|
+
}
|
|
2293
|
+
this.clear();
|
|
2294
|
+
}
|
|
2295
|
+
};
|
|
2296
|
+
|
|
2297
|
+
// src/core/OIMIndexComparatorFactory.ts
|
|
2298
|
+
var OIMIndexComparatorFactory = class {
|
|
2299
|
+
/**
|
|
2300
|
+
* Create an element-wise comparator that checks arrays for strict equality.
|
|
2301
|
+
* Compares array lengths and each element using strict equality (===).
|
|
2302
|
+
*/
|
|
2303
|
+
static createElementWiseComparator() {
|
|
2304
|
+
return (existingPks, newPks) => {
|
|
2305
|
+
if (existingPks.length !== newPks.length) {
|
|
2306
|
+
return false;
|
|
2307
|
+
}
|
|
2308
|
+
for (let i = 0; i < existingPks.length; i++) {
|
|
2309
|
+
if (existingPks[i] !== newPks[i]) {
|
|
2310
|
+
return false;
|
|
2311
|
+
}
|
|
2312
|
+
}
|
|
2313
|
+
return true;
|
|
2314
|
+
};
|
|
2315
|
+
}
|
|
2316
|
+
/**
|
|
2317
|
+
* Create a set-based comparator that checks if arrays contain the same elements.
|
|
2318
|
+
* Order doesn't matter, only the presence of elements.
|
|
2319
|
+
*/
|
|
2320
|
+
static createSetBasedComparator() {
|
|
2321
|
+
return (existingPks, newPks) => {
|
|
2322
|
+
if (existingPks.length !== newPks.length) {
|
|
2323
|
+
return false;
|
|
2324
|
+
}
|
|
2325
|
+
const existingSet = new Set(existingPks);
|
|
2326
|
+
const newSet = new Set(newPks);
|
|
2327
|
+
if (existingSet.size !== newSet.size || existingSet.size !== existingPks.length) {
|
|
2328
|
+
return false;
|
|
2329
|
+
}
|
|
2330
|
+
for (const pk of Array.from(existingSet)) {
|
|
2331
|
+
if (!newSet.has(pk)) {
|
|
2332
|
+
return false;
|
|
2333
|
+
}
|
|
2334
|
+
}
|
|
2335
|
+
return true;
|
|
2336
|
+
};
|
|
2337
|
+
}
|
|
2338
|
+
/**
|
|
2339
|
+
* Create a shallow comparator that only checks array references.
|
|
2340
|
+
* Fastest but only works if you're reusing the same array instances.
|
|
2341
|
+
*/
|
|
2342
|
+
static createShallowComparator() {
|
|
2343
|
+
return (existingPks, newPks) => {
|
|
2344
|
+
return existingPks === newPks;
|
|
2345
|
+
};
|
|
2346
|
+
}
|
|
2347
|
+
/**
|
|
2348
|
+
* Create a no-comparison comparator that always returns false (always updates).
|
|
2349
|
+
* Useful for disabling comparison while keeping the same interface.
|
|
2350
|
+
*/
|
|
2351
|
+
static createAlwaysUpdateComparator() {
|
|
2352
|
+
return () => false;
|
|
2353
|
+
}
|
|
2354
|
+
};
|
|
2355
|
+
|
|
2356
|
+
// src/core/OIMMap2Keys.ts
|
|
2357
|
+
var OIMMap2Keys = class {
|
|
2358
|
+
constructor() {
|
|
2359
|
+
this.map = /* @__PURE__ */ new Map();
|
|
2360
|
+
this._size = 0;
|
|
2361
|
+
}
|
|
2362
|
+
get size() {
|
|
2363
|
+
return this._size;
|
|
2364
|
+
}
|
|
2365
|
+
set(k1, k2, v) {
|
|
2366
|
+
let m = this.map.get(k1);
|
|
2367
|
+
if (!m) {
|
|
2368
|
+
m = /* @__PURE__ */ new Map();
|
|
2369
|
+
this.map.set(k1, m);
|
|
2370
|
+
}
|
|
2371
|
+
if (!m.has(k2)) this._size++;
|
|
2372
|
+
m.set(k2, v);
|
|
2373
|
+
}
|
|
2374
|
+
get(k1, k2) {
|
|
2375
|
+
return this.map.get(k1)?.get(k2);
|
|
2376
|
+
}
|
|
2377
|
+
has(k1, k2) {
|
|
2378
|
+
return this.map.get(k1)?.has(k2);
|
|
2379
|
+
}
|
|
2380
|
+
delete(k1, k2) {
|
|
2381
|
+
const m = this.map.get(k1);
|
|
2382
|
+
if (!m) return false;
|
|
2383
|
+
const had = m.delete(k2);
|
|
2384
|
+
if (had) {
|
|
2385
|
+
this._size--;
|
|
2386
|
+
if (m.size === 0) this.map.delete(k1);
|
|
2387
|
+
}
|
|
2388
|
+
return had;
|
|
2389
|
+
}
|
|
2390
|
+
clear() {
|
|
2391
|
+
this.map.clear();
|
|
2392
|
+
this._size = 0;
|
|
2393
|
+
}
|
|
2394
|
+
};
|
|
2395
|
+
|
|
2396
|
+
// src/modules/compute/core/OIMComputeRuntime.ts
|
|
2397
|
+
var OIMComputeRuntime = class {
|
|
2398
|
+
constructor(queue) {
|
|
2399
|
+
this.queue = queue;
|
|
2400
|
+
this.isFlushScheduled = false;
|
|
2401
|
+
this.isFlushing = false;
|
|
2402
|
+
this.minLevel = Infinity;
|
|
2403
|
+
this.maxLevel = -Infinity;
|
|
2404
|
+
this.dirtyByLevel = /* @__PURE__ */ new Map();
|
|
2405
|
+
this.afterFlushTasks = /* @__PURE__ */ new Set();
|
|
2406
|
+
this.queue.emitter.on(0 /* AFTER_FLUSH */, () => {
|
|
2407
|
+
if (!this.isFlushScheduled) return;
|
|
2408
|
+
this.flush();
|
|
2409
|
+
});
|
|
2410
|
+
}
|
|
2411
|
+
/**
|
|
2412
|
+
* Schedule a one-shot task to run on the next `queue.flush()` (AFTER_FLUSH),
|
|
2413
|
+
* ordered by `level` ascending.
|
|
2414
|
+
*/
|
|
2415
|
+
schedule(task, level = 0) {
|
|
2416
|
+
let isActive = true;
|
|
2417
|
+
const wrapped = () => {
|
|
2418
|
+
if (!isActive) return;
|
|
2419
|
+
task();
|
|
2420
|
+
};
|
|
2421
|
+
let bucket = this.dirtyByLevel.get(level);
|
|
2422
|
+
if (!bucket) {
|
|
2423
|
+
bucket = /* @__PURE__ */ new Set();
|
|
2424
|
+
this.dirtyByLevel.set(level, bucket);
|
|
2425
|
+
}
|
|
2426
|
+
bucket.add(wrapped);
|
|
2427
|
+
if (level < this.minLevel) this.minLevel = level;
|
|
2428
|
+
if (level > this.maxLevel) this.maxLevel = level;
|
|
2429
|
+
if (!this.isFlushing) this.isFlushScheduled = true;
|
|
2430
|
+
return () => {
|
|
2431
|
+
if (!isActive) return;
|
|
2432
|
+
isActive = false;
|
|
2433
|
+
bucket.delete(wrapped);
|
|
2434
|
+
};
|
|
2435
|
+
}
|
|
2436
|
+
/**
|
|
2437
|
+
* Run once at the start of the next runtime flush (i.e. after queue.flush()).
|
|
2438
|
+
* Useful for resubscribing dependencies exactly once per source flush.
|
|
2439
|
+
*/
|
|
2440
|
+
scheduleAfterFlush(task) {
|
|
2441
|
+
let isActive = true;
|
|
2442
|
+
const wrapped = () => {
|
|
2443
|
+
if (!isActive) return;
|
|
2444
|
+
task();
|
|
2445
|
+
};
|
|
2446
|
+
this.afterFlushTasks.add(wrapped);
|
|
2447
|
+
if (!this.isFlushing) this.isFlushScheduled = true;
|
|
2448
|
+
return () => {
|
|
2449
|
+
if (!isActive) return;
|
|
2450
|
+
isActive = false;
|
|
2451
|
+
this.afterFlushTasks.delete(wrapped);
|
|
2452
|
+
};
|
|
2453
|
+
}
|
|
2454
|
+
flush() {
|
|
2455
|
+
this.isFlushScheduled = false;
|
|
2456
|
+
if (this.dirtyByLevel.size === 0 && this.afterFlushTasks.size === 0)
|
|
2457
|
+
return;
|
|
2458
|
+
this.isFlushing = true;
|
|
2459
|
+
try {
|
|
2460
|
+
if (this.afterFlushTasks.size > 0) {
|
|
2461
|
+
const snapshot = Array.from(this.afterFlushTasks);
|
|
2462
|
+
this.afterFlushTasks.clear();
|
|
2463
|
+
for (let i = 0; i < snapshot.length; i++) snapshot[i]();
|
|
2464
|
+
}
|
|
2465
|
+
if (this.dirtyByLevel.size === 0) return;
|
|
2466
|
+
let level = this.minLevel;
|
|
2467
|
+
let max = this.maxLevel;
|
|
2468
|
+
while (level <= max) {
|
|
2469
|
+
for (; ; ) {
|
|
2470
|
+
const bucket = this.dirtyByLevel.get(level);
|
|
2471
|
+
if (!bucket || bucket.size === 0) break;
|
|
2472
|
+
this.dirtyByLevel.delete(level);
|
|
2473
|
+
const snapshot = Array.from(bucket);
|
|
2474
|
+
for (let i = 0; i < snapshot.length; i++) snapshot[i]();
|
|
2475
|
+
}
|
|
2476
|
+
if (this.maxLevel > max) max = this.maxLevel;
|
|
2477
|
+
level++;
|
|
2478
|
+
}
|
|
2479
|
+
} finally {
|
|
2480
|
+
this.isFlushing = false;
|
|
2481
|
+
if (this.dirtyByLevel.size === 0) {
|
|
2482
|
+
this.minLevel = Infinity;
|
|
2483
|
+
this.maxLevel = -Infinity;
|
|
2484
|
+
} else {
|
|
2485
|
+
let nextMin = Infinity;
|
|
2486
|
+
let nextMax = -Infinity;
|
|
2487
|
+
this.dirtyByLevel.forEach((_bucket, lvl) => {
|
|
2488
|
+
if (lvl < nextMin) nextMin = lvl;
|
|
2489
|
+
if (lvl > nextMax) nextMax = lvl;
|
|
2490
|
+
});
|
|
2491
|
+
this.minLevel = nextMin;
|
|
2492
|
+
this.maxLevel = nextMax;
|
|
2493
|
+
this.isFlushScheduled = true;
|
|
2494
|
+
}
|
|
2495
|
+
}
|
|
2496
|
+
}
|
|
2497
|
+
};
|
|
2498
|
+
|
|
2499
|
+
// src/modules/selector/core/OIMSelector.ts
|
|
2500
|
+
var OIMSelector = class {
|
|
2501
|
+
constructor(runtime, sourceDeps, computedDeps = []) {
|
|
2502
|
+
this.runtime = runtime;
|
|
2503
|
+
this.sourceDeps = sourceDeps;
|
|
2504
|
+
this.computedDeps = computedDeps;
|
|
2505
|
+
this.listeners = /* @__PURE__ */ new Set();
|
|
2506
|
+
this.sourceUnsubscribers = [];
|
|
2507
|
+
this.computedUnsubscribers = [];
|
|
2508
|
+
this.isResubscribeEnqueued = false;
|
|
2509
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2510
|
+
this.isDeliveryEnqueued = false;
|
|
2511
|
+
this.hasLastValue = false;
|
|
2512
|
+
this.onSourceInvalidate = () => {
|
|
2513
|
+
if (this.listeners.size === 0) return;
|
|
2514
|
+
if (!this.isTemporarilyUnsubscribedForFlush) {
|
|
2515
|
+
this.isTemporarilyUnsubscribedForFlush = true;
|
|
2516
|
+
this.unsubscribeFromSourceDeps();
|
|
2517
|
+
this.ensureResubscribeAfterFlush();
|
|
2518
|
+
}
|
|
2519
|
+
if (this.isDeliveryEnqueued) return;
|
|
2520
|
+
this.isDeliveryEnqueued = true;
|
|
2521
|
+
this.dequeueDelivery = this.runtime.schedule(this.deliver);
|
|
2522
|
+
};
|
|
2523
|
+
this.onComputedInvalidate = () => {
|
|
2524
|
+
if (this.listeners.size === 0) return;
|
|
2525
|
+
if (this.isDeliveryEnqueued) return;
|
|
2526
|
+
this.isDeliveryEnqueued = true;
|
|
2527
|
+
this.dequeueDelivery = this.runtime.schedule(this.deliver);
|
|
2528
|
+
};
|
|
2529
|
+
this.deliver = () => {
|
|
2530
|
+
this.isDeliveryEnqueued = false;
|
|
2531
|
+
this.dequeueDelivery = void 0;
|
|
2532
|
+
if (this.listeners.size === 0) return;
|
|
2533
|
+
const next = this.getValue();
|
|
2534
|
+
if (this.hasLastValue && this.areEqual(this.lastValue, next)) return;
|
|
2535
|
+
this.setLastValue(next);
|
|
2536
|
+
const snapshot = Array.from(this.listeners);
|
|
2537
|
+
for (let i = 0; i < snapshot.length; i++) {
|
|
2538
|
+
const listener = snapshot[i];
|
|
2539
|
+
if (this.listeners.has(listener)) listener(next);
|
|
2540
|
+
}
|
|
2541
|
+
};
|
|
2542
|
+
this.onAfterFlush = () => {
|
|
2543
|
+
if (!this.isResubscribeEnqueued) return;
|
|
2544
|
+
this.isResubscribeEnqueued = false;
|
|
2545
|
+
this.dequeueResubscribe = void 0;
|
|
2546
|
+
if (this.listeners.size === 0) return;
|
|
2547
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2548
|
+
if (this.sourceUnsubscribers.length === 0) {
|
|
2549
|
+
for (const dep of this.sourceDeps) {
|
|
2550
|
+
this.sourceUnsubscribers.push(
|
|
2551
|
+
dep.subscribe(this.onSourceInvalidate)
|
|
2552
|
+
);
|
|
2553
|
+
}
|
|
2554
|
+
}
|
|
2555
|
+
};
|
|
2556
|
+
}
|
|
2557
|
+
get queue() {
|
|
2558
|
+
return this.runtime.queue;
|
|
2559
|
+
}
|
|
2560
|
+
/**
|
|
2561
|
+
* Start watching this selector. The callback is called immediately with the current value,
|
|
2562
|
+
* then coalesced and delivered on `queue.flush()` when the selector invalidates.
|
|
2563
|
+
*/
|
|
2564
|
+
watch(onValue) {
|
|
2565
|
+
this.listeners.add(onValue);
|
|
2566
|
+
if (this.listeners.size === 1) {
|
|
2567
|
+
this.subscribeToDeps();
|
|
2568
|
+
}
|
|
2569
|
+
const current = this.getValue();
|
|
2570
|
+
this.setLastValue(current);
|
|
2571
|
+
onValue(current);
|
|
2572
|
+
return () => {
|
|
2573
|
+
this.listeners.delete(onValue);
|
|
2574
|
+
if (this.listeners.size > 0) return;
|
|
2575
|
+
this.unsubscribeFromAllDeps();
|
|
2576
|
+
if (this.dequeueResubscribe) {
|
|
2577
|
+
this.dequeueResubscribe();
|
|
2578
|
+
this.dequeueResubscribe = void 0;
|
|
2579
|
+
}
|
|
2580
|
+
this.isResubscribeEnqueued = false;
|
|
2581
|
+
this.isTemporarilyUnsubscribedForFlush = false;
|
|
2582
|
+
if (this.dequeueDelivery) {
|
|
2583
|
+
this.dequeueDelivery();
|
|
2584
|
+
this.dequeueDelivery = void 0;
|
|
2585
|
+
}
|
|
2586
|
+
this.isDeliveryEnqueued = false;
|
|
2587
|
+
this.hasLastValue = false;
|
|
2588
|
+
};
|
|
2589
|
+
}
|
|
2590
|
+
areEqual(prev, next) {
|
|
2591
|
+
return Object.is(prev, next);
|
|
2592
|
+
}
|
|
2593
|
+
setLastValue(value) {
|
|
2594
|
+
this.lastValue = value;
|
|
2595
|
+
this.hasLastValue = true;
|
|
2596
|
+
}
|
|
2597
|
+
subscribeToDeps() {
|
|
2598
|
+
if (this.sourceUnsubscribers.length > 0 || this.computedUnsubscribers.length > 0)
|
|
2599
|
+
return;
|
|
2600
|
+
for (const dep of this.sourceDeps) {
|
|
2601
|
+
this.sourceUnsubscribers.push(
|
|
2602
|
+
dep.subscribe(this.onSourceInvalidate)
|
|
2603
|
+
);
|
|
2604
|
+
}
|
|
2605
|
+
for (const dep of this.computedDeps) {
|
|
2606
|
+
this.computedUnsubscribers.push(
|
|
2607
|
+
dep.subscribe(this.onComputedInvalidate)
|
|
2608
|
+
);
|
|
2609
|
+
}
|
|
2610
|
+
}
|
|
2611
|
+
unsubscribeFromSourceDeps() {
|
|
2612
|
+
if (this.sourceUnsubscribers.length === 0) return;
|
|
2613
|
+
for (const unsub of this.sourceUnsubscribers) unsub();
|
|
2614
|
+
this.sourceUnsubscribers = [];
|
|
2615
|
+
}
|
|
2616
|
+
unsubscribeFromAllDeps() {
|
|
2617
|
+
this.unsubscribeFromSourceDeps();
|
|
2618
|
+
if (this.computedUnsubscribers.length === 0) return;
|
|
2619
|
+
for (const unsub of this.computedUnsubscribers) unsub();
|
|
2620
|
+
this.computedUnsubscribers = [];
|
|
2621
|
+
}
|
|
2622
|
+
ensureResubscribeAfterFlush() {
|
|
2623
|
+
if (this.isResubscribeEnqueued) return;
|
|
2624
|
+
this.isResubscribeEnqueued = true;
|
|
2625
|
+
this.dequeueResubscribe = this.runtime.scheduleAfterFlush(
|
|
2626
|
+
this.onAfterFlush
|
|
2627
|
+
);
|
|
2628
|
+
}
|
|
2629
|
+
};
|
|
2630
|
+
|
|
2631
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyUpdateEventEmitterKey.ts
|
|
2632
|
+
var OIMSelectorSourceDependencyUpdateEventEmitterKey = class {
|
|
2633
|
+
constructor(subscription, key) {
|
|
2634
|
+
this.subscription = subscription;
|
|
2635
|
+
this.key = key;
|
|
2636
|
+
}
|
|
2637
|
+
subscribe(onUpdate) {
|
|
2638
|
+
return this.subscription.subscribeOnKey(this.key, onUpdate);
|
|
2639
|
+
}
|
|
2640
|
+
};
|
|
2641
|
+
|
|
2642
|
+
// src/modules/selector/core/OIMCollectionByPkSelector.ts
|
|
2643
|
+
var OIMCollectionByPkSelector = class extends OIMSelector {
|
|
2644
|
+
constructor(runtime, collection, pk) {
|
|
2645
|
+
super(runtime, [
|
|
2646
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKey(
|
|
2647
|
+
collection,
|
|
2648
|
+
pk
|
|
2649
|
+
)
|
|
2650
|
+
]);
|
|
2651
|
+
this.collection = collection;
|
|
2652
|
+
this.pk = pk;
|
|
2653
|
+
}
|
|
2654
|
+
getValue() {
|
|
2655
|
+
return this.collection.getOneByPk(this.pk);
|
|
2656
|
+
}
|
|
2657
|
+
};
|
|
2658
|
+
|
|
2659
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyUpdateEventEmitterKeys.ts
|
|
2660
|
+
var OIMSelectorSourceDependencyUpdateEventEmitterKeys = class {
|
|
2661
|
+
constructor(subscription, keys) {
|
|
2662
|
+
this.subscription = subscription;
|
|
2663
|
+
this.keys = keys;
|
|
2664
|
+
}
|
|
2665
|
+
subscribe(onUpdate) {
|
|
2666
|
+
return this.subscription.subscribeOnKeys(this.keys, onUpdate);
|
|
2667
|
+
}
|
|
2668
|
+
};
|
|
2669
|
+
|
|
2670
|
+
// src/modules/selector/core/OIMCollectionByPksSelector.ts
|
|
2671
|
+
var OIMCollectionByPksSelector = class extends OIMSelector {
|
|
2672
|
+
constructor(runtime, collection, pks) {
|
|
2673
|
+
super(runtime, [
|
|
2674
|
+
new OIMSelectorSourceDependencyUpdateEventEmitterKeys(
|
|
2675
|
+
collection,
|
|
2676
|
+
pks
|
|
2677
|
+
)
|
|
2678
|
+
]);
|
|
2679
|
+
this.collection = collection;
|
|
2680
|
+
this.pks = pks;
|
|
2681
|
+
}
|
|
2682
|
+
getValue() {
|
|
2683
|
+
return this.pks.map((pk) => this.collection.getOneByPk(pk));
|
|
2684
|
+
}
|
|
2685
|
+
areEqual(prev, next) {
|
|
2686
|
+
if (prev === next) return true;
|
|
2687
|
+
if (prev.length !== next.length) return false;
|
|
2688
|
+
for (let i = 0; i < prev.length; i++) {
|
|
2689
|
+
if (prev[i] !== next[i]) return false;
|
|
2690
|
+
}
|
|
2691
|
+
return true;
|
|
2692
|
+
}
|
|
2693
|
+
};
|
|
2694
|
+
|
|
2695
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyEntitiesByIndexKeyArrayBased.ts
|
|
2696
|
+
var OIMSelectorSourceDependencyEntitiesByIndexKeyArrayBased = class {
|
|
2697
|
+
constructor(collection, reactiveIndex, key) {
|
|
2698
|
+
this.collection = collection;
|
|
2699
|
+
this.reactiveIndex = reactiveIndex;
|
|
2700
|
+
this.key = key;
|
|
2701
|
+
this.currentPks = [];
|
|
2702
|
+
}
|
|
2703
|
+
subscribe(onUpdate) {
|
|
2704
|
+
const resubscribeCollection = () => {
|
|
2705
|
+
const nextPks = this.reactiveIndex.getPksByKey(this.key);
|
|
2706
|
+
if (this.sameArray(this.currentPks, nextPks)) return;
|
|
2707
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
2708
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
2709
|
+
this.currentPks = nextPks;
|
|
2710
|
+
if (this.currentPks.length === 0) return;
|
|
2711
|
+
this.unsubscribeFromCollectionKeys = this.collection.subscribeOnKeys(this.currentPks, onUpdate);
|
|
2712
|
+
};
|
|
2713
|
+
const onIndexUpdate = () => {
|
|
2714
|
+
resubscribeCollection();
|
|
2715
|
+
onUpdate();
|
|
2716
|
+
};
|
|
2717
|
+
resubscribeCollection();
|
|
2718
|
+
const unsubscribeFromIndex = this.reactiveIndex.subscribeOnKey(
|
|
2719
|
+
this.key,
|
|
2720
|
+
onIndexUpdate
|
|
2721
|
+
);
|
|
2722
|
+
return () => {
|
|
2723
|
+
unsubscribeFromIndex();
|
|
2724
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
2725
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
2726
|
+
this.currentPks = [];
|
|
2727
|
+
};
|
|
2728
|
+
}
|
|
2729
|
+
sameArray(a, b) {
|
|
2730
|
+
if (a === b) return true;
|
|
2731
|
+
if (a.length !== b.length) return false;
|
|
2732
|
+
for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return false;
|
|
2733
|
+
return true;
|
|
2734
|
+
}
|
|
2735
|
+
};
|
|
2736
|
+
|
|
2737
|
+
// src/modules/selector/core/OIMEntitiesByIndexKeyArrayBasedSelector.ts
|
|
2738
|
+
var OIMEntitiesByIndexKeyArrayBasedSelector = class extends OIMSelector {
|
|
2739
|
+
constructor(runtime, collection, reactiveIndex, key) {
|
|
2740
|
+
super(runtime, [
|
|
2741
|
+
new OIMSelectorSourceDependencyEntitiesByIndexKeyArrayBased(collection, reactiveIndex, key)
|
|
2742
|
+
]);
|
|
2743
|
+
this.collection = collection;
|
|
2744
|
+
this.reactiveIndex = reactiveIndex;
|
|
2745
|
+
this.key = key;
|
|
2746
|
+
}
|
|
2747
|
+
getValue() {
|
|
2748
|
+
const pks = this.reactiveIndex.getPksByKey(this.key);
|
|
2749
|
+
const entities = [];
|
|
2750
|
+
entities.length = pks.length;
|
|
2751
|
+
for (let i = 0; i < pks.length; i++) {
|
|
2752
|
+
entities[i] = this.collection.getOneByPk(pks[i]);
|
|
2753
|
+
}
|
|
2754
|
+
return entities;
|
|
2755
|
+
}
|
|
2756
|
+
areEqual(prev, next) {
|
|
2757
|
+
if (prev === next) return true;
|
|
2758
|
+
if (prev.length !== next.length) return false;
|
|
2759
|
+
for (let i = 0; i < prev.length; i++)
|
|
2760
|
+
if (prev[i] !== next[i]) return false;
|
|
2761
|
+
return true;
|
|
2762
|
+
}
|
|
2763
|
+
};
|
|
2764
|
+
|
|
2765
|
+
// src/modules/selector/core/OIMSelectorSourceDependencyEntitiesByIndexKeySetBased.ts
|
|
2766
|
+
var OIMSelectorSourceDependencyEntitiesByIndexKeySetBased = class {
|
|
2767
|
+
constructor(collection, reactiveIndex, key) {
|
|
2768
|
+
this.collection = collection;
|
|
2769
|
+
this.reactiveIndex = reactiveIndex;
|
|
2770
|
+
this.key = key;
|
|
2771
|
+
this.currentPks = [];
|
|
2772
|
+
}
|
|
2773
|
+
subscribe(onUpdate) {
|
|
2774
|
+
const resubscribeCollection = () => {
|
|
2775
|
+
const nextPks = Array.from(this.reactiveIndex.getPksByKey(this.key));
|
|
2776
|
+
if (this.sameArray(this.currentPks, nextPks)) return;
|
|
2777
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
2778
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
2779
|
+
this.currentPks = nextPks;
|
|
2780
|
+
if (this.currentPks.length === 0) return;
|
|
2781
|
+
this.unsubscribeFromCollectionKeys = this.collection.subscribeOnKeys(this.currentPks, onUpdate);
|
|
2782
|
+
};
|
|
2783
|
+
const onIndexUpdate = () => {
|
|
2784
|
+
resubscribeCollection();
|
|
2785
|
+
onUpdate();
|
|
2786
|
+
};
|
|
2787
|
+
resubscribeCollection();
|
|
2788
|
+
const unsubscribeFromIndex = this.reactiveIndex.subscribeOnKey(
|
|
2789
|
+
this.key,
|
|
2790
|
+
onIndexUpdate
|
|
2791
|
+
);
|
|
2792
|
+
return () => {
|
|
2793
|
+
unsubscribeFromIndex();
|
|
2794
|
+
this.unsubscribeFromCollectionKeys?.();
|
|
2795
|
+
this.unsubscribeFromCollectionKeys = void 0;
|
|
2796
|
+
this.currentPks = [];
|
|
2797
|
+
};
|
|
2798
|
+
}
|
|
2799
|
+
sameArray(a, b) {
|
|
2800
|
+
if (a === b) return true;
|
|
2801
|
+
if (a.length !== b.length) return false;
|
|
2802
|
+
for (let i = 0; i < a.length; i++) if (a[i] !== b[i]) return false;
|
|
2803
|
+
return true;
|
|
1911
2804
|
}
|
|
1912
2805
|
};
|
|
1913
2806
|
|
|
1914
|
-
// src/core/
|
|
1915
|
-
var
|
|
1916
|
-
constructor() {
|
|
1917
|
-
|
|
1918
|
-
|
|
1919
|
-
|
|
1920
|
-
|
|
1921
|
-
|
|
2807
|
+
// src/modules/selector/core/OIMEntitiesByIndexKeySetBasedSelector.ts
|
|
2808
|
+
var OIMEntitiesByIndexKeySetBasedSelector = class extends OIMSelector {
|
|
2809
|
+
constructor(runtime, collection, reactiveIndex, key) {
|
|
2810
|
+
super(runtime, [
|
|
2811
|
+
new OIMSelectorSourceDependencyEntitiesByIndexKeySetBased(collection, reactiveIndex, key)
|
|
2812
|
+
]);
|
|
2813
|
+
this.collection = collection;
|
|
2814
|
+
this.reactiveIndex = reactiveIndex;
|
|
2815
|
+
this.key = key;
|
|
1922
2816
|
}
|
|
1923
|
-
|
|
1924
|
-
|
|
1925
|
-
|
|
1926
|
-
|
|
1927
|
-
|
|
2817
|
+
getValue() {
|
|
2818
|
+
const pks = this.reactiveIndex.getPksByKey(this.key);
|
|
2819
|
+
const entities = [];
|
|
2820
|
+
entities.length = pks.size;
|
|
2821
|
+
let writeIndex = 0;
|
|
2822
|
+
for (const pk of pks) {
|
|
2823
|
+
entities[writeIndex++] = this.collection.getOneByPk(pk);
|
|
1928
2824
|
}
|
|
1929
|
-
|
|
1930
|
-
m.set(k2, v);
|
|
2825
|
+
return entities;
|
|
1931
2826
|
}
|
|
1932
|
-
|
|
1933
|
-
|
|
2827
|
+
areEqual(prev, next) {
|
|
2828
|
+
if (prev === next) return true;
|
|
2829
|
+
if (prev.length !== next.length) return false;
|
|
2830
|
+
for (let i = 0; i < prev.length; i++)
|
|
2831
|
+
if (prev[i] !== next[i]) return false;
|
|
2832
|
+
return true;
|
|
1934
2833
|
}
|
|
1935
|
-
|
|
1936
|
-
|
|
2834
|
+
};
|
|
2835
|
+
|
|
2836
|
+
// src/dx/OIMCollectionSelectors.ts
|
|
2837
|
+
var OIMCollectionSelectors = class {
|
|
2838
|
+
constructor(queue, collection) {
|
|
2839
|
+
this.collection = collection;
|
|
2840
|
+
this.runtime = new OIMComputeRuntime(queue);
|
|
1937
2841
|
}
|
|
1938
|
-
|
|
1939
|
-
|
|
1940
|
-
if (!m) return false;
|
|
1941
|
-
const had = m.delete(k2);
|
|
1942
|
-
if (had) {
|
|
1943
|
-
this._size--;
|
|
1944
|
-
if (m.size === 0) this.map.delete(k1);
|
|
1945
|
-
}
|
|
1946
|
-
return had;
|
|
2842
|
+
byPk(pk) {
|
|
2843
|
+
return new OIMCollectionByPkSelector(this.runtime, this.collection, pk);
|
|
1947
2844
|
}
|
|
1948
|
-
|
|
1949
|
-
|
|
1950
|
-
|
|
2845
|
+
byPks(pks) {
|
|
2846
|
+
return new OIMCollectionByPksSelector(
|
|
2847
|
+
this.runtime,
|
|
2848
|
+
this.collection,
|
|
2849
|
+
pks
|
|
2850
|
+
);
|
|
2851
|
+
}
|
|
2852
|
+
entitiesBySetIndexKey(index, key) {
|
|
2853
|
+
return new OIMEntitiesByIndexKeySetBasedSelector(
|
|
2854
|
+
this.runtime,
|
|
2855
|
+
this.collection,
|
|
2856
|
+
index,
|
|
2857
|
+
key
|
|
2858
|
+
);
|
|
2859
|
+
}
|
|
2860
|
+
entitiesByArrayIndexKey(index, key) {
|
|
2861
|
+
return new OIMEntitiesByIndexKeyArrayBasedSelector(
|
|
2862
|
+
this.runtime,
|
|
2863
|
+
this.collection,
|
|
2864
|
+
index,
|
|
2865
|
+
key
|
|
2866
|
+
);
|
|
1951
2867
|
}
|
|
1952
2868
|
};
|
|
1953
2869
|
|
|
1954
|
-
// src/
|
|
1955
|
-
|
|
2870
|
+
// src/dx/OIMCollectionContext.ts
|
|
2871
|
+
function createOIMCollectionContext(queue, opts) {
|
|
2872
|
+
const collection = new OIMReactiveCollection(queue, opts);
|
|
2873
|
+
const indexFactory = new OIMCollectionIndexFactory(queue, collection);
|
|
2874
|
+
const select = new OIMCollectionSelectors(queue, collection);
|
|
2875
|
+
return { queue, collection, indexFactory, select };
|
|
2876
|
+
}
|
|
2877
|
+
|
|
2878
|
+
// src/modules/wrapper/collection/OIMCollectionChangedFields.ts
|
|
2879
|
+
var OIMCollectionChangedFields = class {
|
|
1956
2880
|
constructor(queue, collection, opts) {
|
|
1957
2881
|
this.isInWrite = false;
|
|
1958
2882
|
this.lastEntitySnapshotByPk = /* @__PURE__ */ new Map();
|
|
@@ -1972,7 +2896,7 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
1972
2896
|
this.collection = collection;
|
|
1973
2897
|
this.selectPk = opts?.selectPk ?? (() => {
|
|
1974
2898
|
throw new Error(
|
|
1975
|
-
`[
|
|
2899
|
+
`[OIMCollectionChangedFields]: selectPk was not provided. Use upsertOneByPk(...) or pass opts.selectPk.`
|
|
1976
2900
|
);
|
|
1977
2901
|
});
|
|
1978
2902
|
this.changedPksEventEmitter = new OIMUpdateEventEmitter(
|
|
@@ -1995,31 +2919,34 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
1995
2919
|
);
|
|
1996
2920
|
}
|
|
1997
2921
|
upsertOneByPk(pk, patch) {
|
|
1998
|
-
this.withWrite(() => {
|
|
2922
|
+
const slot = this.withWrite(() => {
|
|
1999
2923
|
this.trackPatch(pk, patch);
|
|
2000
|
-
this.collection.upsertOneByPk(pk, patch);
|
|
2924
|
+
return this.collection.upsertOneByPk(pk, patch);
|
|
2001
2925
|
});
|
|
2002
2926
|
this.updateEntitySnapshot(pk);
|
|
2927
|
+
return slot;
|
|
2003
2928
|
}
|
|
2004
2929
|
upsertOne(entity) {
|
|
2005
|
-
this.withWrite(() => {
|
|
2930
|
+
const slot = this.withWrite(() => {
|
|
2006
2931
|
const pk = this.selectPk(entity);
|
|
2007
2932
|
this.trackPatch(pk, entity);
|
|
2008
|
-
this.collection.upsertOne(entity);
|
|
2933
|
+
return this.collection.upsertOne(entity);
|
|
2009
2934
|
});
|
|
2010
|
-
this.updateEntitySnapshot(
|
|
2935
|
+
this.updateEntitySnapshot(slot.pk);
|
|
2936
|
+
return slot;
|
|
2011
2937
|
}
|
|
2012
2938
|
upsertMany(entities) {
|
|
2013
2939
|
const pks = [];
|
|
2014
|
-
this.withWrite(() => {
|
|
2940
|
+
const slots = this.withWrite(() => {
|
|
2015
2941
|
for (const entity of entities) {
|
|
2016
2942
|
const pk = this.selectPk(entity);
|
|
2017
2943
|
pks.push(pk);
|
|
2018
2944
|
this.trackPatch(pk, entity);
|
|
2019
2945
|
}
|
|
2020
|
-
this.collection.upsertMany(entities);
|
|
2946
|
+
return this.collection.upsertMany(entities);
|
|
2021
2947
|
});
|
|
2022
2948
|
for (let i = 0; i < pks.length; i++) this.updateEntitySnapshot(pks[i]);
|
|
2949
|
+
return slots;
|
|
2023
2950
|
}
|
|
2024
2951
|
getChangedFieldsByPk(pk) {
|
|
2025
2952
|
return this.changedFieldsByPk.get(pk) ?? /* @__PURE__ */ new Set();
|
|
@@ -2050,12 +2977,11 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
2050
2977
|
}
|
|
2051
2978
|
withWrite(fn) {
|
|
2052
2979
|
if (this.isInWrite) {
|
|
2053
|
-
fn();
|
|
2054
|
-
return;
|
|
2980
|
+
return fn();
|
|
2055
2981
|
}
|
|
2056
2982
|
this.isInWrite = true;
|
|
2057
2983
|
try {
|
|
2058
|
-
fn();
|
|
2984
|
+
return fn();
|
|
2059
2985
|
} finally {
|
|
2060
2986
|
this.isInWrite = false;
|
|
2061
2987
|
}
|
|
@@ -2087,248 +3013,43 @@ var OIMCollectionChangedFieldsWrapper = class {
|
|
|
2087
3013
|
});
|
|
2088
3014
|
return changed;
|
|
2089
3015
|
}
|
|
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) {
|
|
2101
|
-
let pkFields = this.changedFieldsByPk.get(pk);
|
|
2102
|
-
if (!pkFields) {
|
|
2103
|
-
pkFields = /* @__PURE__ */ new Set();
|
|
2104
|
-
this.changedFieldsByPk.set(pk, pkFields);
|
|
2105
|
-
}
|
|
2106
|
-
for (const key of keys) {
|
|
2107
|
-
pkFields.add(key);
|
|
2108
|
-
let fieldPks = this.changedPksByField.get(key);
|
|
2109
|
-
if (!fieldPks) {
|
|
2110
|
-
fieldPks = /* @__PURE__ */ new Set();
|
|
2111
|
-
this.changedPksByField.set(key, fieldPks);
|
|
2112
|
-
}
|
|
2113
|
-
fieldPks.add(pk);
|
|
2114
|
-
}
|
|
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);
|
|
2127
|
-
}
|
|
2128
|
-
};
|
|
2129
|
-
|
|
2130
|
-
// src/modules/wrapper/index/OIMIndexManualOrderedArrayBased.ts
|
|
2131
|
-
var OIMIndexManualOrderedArrayBased = class extends OIMIndexArrayBased {
|
|
2132
|
-
clear(key) {
|
|
2133
|
-
if (key === void 0) {
|
|
2134
|
-
const keys = this.getKeys();
|
|
2135
|
-
if (keys.length > 0) {
|
|
2136
|
-
this.store.clear();
|
|
2137
|
-
this.emitUpdate(Array.from(keys));
|
|
2138
|
-
}
|
|
2139
|
-
return;
|
|
2140
|
-
}
|
|
2141
|
-
if (this.store.getOneByKey(key) !== void 0) {
|
|
2142
|
-
this.store.removeOneByKey(key);
|
|
2143
|
-
this.emitUpdate([key]);
|
|
2144
|
-
}
|
|
2145
|
-
}
|
|
2146
|
-
push(key, itemKey) {
|
|
2147
|
-
const list = this.getOrCreateList(key);
|
|
2148
|
-
const index = list.length;
|
|
2149
|
-
list.push(this.getOrCreateSlot(itemKey));
|
|
2150
|
-
this.emitUpdate([key]);
|
|
2151
|
-
return index;
|
|
2152
|
-
}
|
|
2153
|
-
insertAt(key, index, itemKey) {
|
|
2154
|
-
const list = this.getOrCreateList(key);
|
|
2155
|
-
const safeIndex = Math.max(0, Math.min(index, list.length));
|
|
2156
|
-
list.splice(safeIndex, 0, this.getOrCreateSlot(itemKey));
|
|
2157
|
-
this.emitUpdate([key]);
|
|
2158
|
-
}
|
|
2159
|
-
removeAt(key, index) {
|
|
2160
|
-
const list = this.store.getOneByKey(key);
|
|
2161
|
-
if (!list) return void 0;
|
|
2162
|
-
if (index < 0 || index >= list.length) return void 0;
|
|
2163
|
-
const [removed] = list.splice(index, 1);
|
|
2164
|
-
if (list.length === 0) {
|
|
2165
|
-
this.store.removeOneByKey(key);
|
|
2166
|
-
}
|
|
2167
|
-
this.emitUpdate([key]);
|
|
2168
|
-
return removed?.pk;
|
|
2169
|
-
}
|
|
2170
|
-
move(key, fromIndex, toIndex) {
|
|
2171
|
-
const list = this.store.getOneByKey(key);
|
|
2172
|
-
if (!list) return void 0;
|
|
2173
|
-
if (fromIndex < 0 || fromIndex >= list.length) return void 0;
|
|
2174
|
-
if (toIndex < 0 || toIndex >= list.length) return void 0;
|
|
2175
|
-
if (fromIndex === toIndex) return list[fromIndex]?.pk;
|
|
2176
|
-
const [itemKey] = list.splice(fromIndex, 1);
|
|
2177
|
-
if (itemKey === void 0) return void 0;
|
|
2178
|
-
list.splice(toIndex, 0, itemKey);
|
|
2179
|
-
this.emitUpdate([key]);
|
|
2180
|
-
return itemKey.pk;
|
|
2181
|
-
}
|
|
2182
|
-
reset(key, itemKeys) {
|
|
2183
|
-
if (itemKeys.length === 0) {
|
|
2184
|
-
if (this.store.getOneByKey(key) !== void 0) {
|
|
2185
|
-
this.store.removeOneByKey(key);
|
|
2186
|
-
this.emitUpdate([key]);
|
|
2187
|
-
}
|
|
2188
|
-
return;
|
|
2189
|
-
}
|
|
2190
|
-
this.store.setOneByKey(key, this.resolveSlots(itemKeys));
|
|
2191
|
-
this.emitUpdate([key]);
|
|
2192
|
-
}
|
|
2193
|
-
getOrCreateList(key) {
|
|
2194
|
-
let list = this.store.getOneByKey(key);
|
|
2195
|
-
if (!list) {
|
|
2196
|
-
list = [];
|
|
2197
|
-
this.store.setOneByKey(key, list);
|
|
2198
|
-
}
|
|
2199
|
-
return list;
|
|
2200
|
-
}
|
|
2201
|
-
};
|
|
2202
|
-
|
|
2203
|
-
// src/modules/wrapper/index/OIMOrderedListIndexCommandStreamWrapper.ts
|
|
2204
|
-
var OIMOrderedListIndexCommandStreamWrapper = class {
|
|
2205
|
-
constructor(queue, index) {
|
|
2206
|
-
this.isInWrite = false;
|
|
2207
|
-
this.commandsByKey = /* @__PURE__ */ new Map();
|
|
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
|
-
);
|
|
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
|
-
);
|
|
2233
|
-
}
|
|
2234
|
-
getPksByKey(key) {
|
|
2235
|
-
return this.index.getPksByKey(key);
|
|
2236
|
-
}
|
|
2237
|
-
hasKey(key) {
|
|
2238
|
-
return this.index.hasKey(key);
|
|
2239
|
-
}
|
|
2240
|
-
getKeys() {
|
|
2241
|
-
return this.index.getKeys();
|
|
2242
|
-
}
|
|
2243
|
-
push(key, itemKey) {
|
|
2244
|
-
this.withWrite(() => {
|
|
2245
|
-
const index = this.index.push(key, itemKey);
|
|
2246
|
-
this.appendCommand(key, { type: "add", key: itemKey, index });
|
|
2247
|
-
});
|
|
2248
|
-
}
|
|
2249
|
-
removeAt(key, index) {
|
|
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
|
-
});
|
|
2255
|
-
}
|
|
2256
|
-
move(key, fromIndex, toIndex) {
|
|
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
|
-
});
|
|
2266
|
-
});
|
|
2267
|
-
}
|
|
2268
|
-
set(key, keys) {
|
|
2269
|
-
this.withWrite(() => {
|
|
2270
|
-
this.index.reset(key, keys);
|
|
2271
|
-
this.appendCommand(key, { type: "set", keys });
|
|
2272
|
-
});
|
|
2273
|
-
}
|
|
2274
|
-
/**
|
|
2275
|
-
* Read-only peek at buffered commands without clearing them.
|
|
2276
|
-
*/
|
|
2277
|
-
getBufferedCommands(key) {
|
|
2278
|
-
return this.commandsByKey.get(key) ?? [];
|
|
2279
|
-
}
|
|
2280
|
-
/**
|
|
2281
|
-
* Drain buffered commands for a key, preserving order.
|
|
2282
|
-
* Intended usage: call inside a `commandsEventEmitter.subscribeOnKey(key, ...)` handler.
|
|
2283
|
-
*/
|
|
2284
|
-
consumeCommands(key) {
|
|
2285
|
-
const cmds = this.commandsByKey.get(key);
|
|
2286
|
-
if (!cmds || cmds.length === 0) return [];
|
|
2287
|
-
return cmds.slice();
|
|
2288
|
-
}
|
|
2289
|
-
clear(key) {
|
|
2290
|
-
if (key === void 0) {
|
|
2291
|
-
this.index.destroy();
|
|
2292
|
-
this.commandsByKey.clear();
|
|
2293
|
-
return;
|
|
2294
|
-
}
|
|
2295
|
-
this.index.clear(key);
|
|
2296
|
-
this.commandsByKey.delete(key);
|
|
2297
|
-
}
|
|
2298
|
-
destroy() {
|
|
2299
|
-
this.commandsEventEmitter.destroy();
|
|
2300
|
-
this.unsubscribeAfterFlush();
|
|
2301
|
-
this.unsubscribeFromIndexEmitter();
|
|
2302
|
-
this.clear();
|
|
2303
|
-
}
|
|
2304
|
-
withWrite(fn) {
|
|
2305
|
-
if (this.isInWrite) {
|
|
2306
|
-
fn();
|
|
3016
|
+
updateEntitySnapshot(pk) {
|
|
3017
|
+
const entity = this.collection.getOneByPk(pk);
|
|
3018
|
+
if (!entity) {
|
|
3019
|
+
this.lastEntitySnapshotByPk.delete(pk);
|
|
2307
3020
|
return;
|
|
2308
3021
|
}
|
|
2309
|
-
this.
|
|
2310
|
-
|
|
2311
|
-
|
|
2312
|
-
} finally {
|
|
2313
|
-
this.isInWrite = false;
|
|
2314
|
-
}
|
|
3022
|
+
this.lastEntitySnapshotByPk.set(pk, {
|
|
3023
|
+
...entity
|
|
3024
|
+
});
|
|
2315
3025
|
}
|
|
2316
|
-
|
|
2317
|
-
let
|
|
2318
|
-
if (!
|
|
2319
|
-
|
|
2320
|
-
this.
|
|
3026
|
+
trackChangedKeys(pk, keys) {
|
|
3027
|
+
let pkFields = this.changedFieldsByPk.get(pk);
|
|
3028
|
+
if (!pkFields) {
|
|
3029
|
+
pkFields = /* @__PURE__ */ new Set();
|
|
3030
|
+
this.changedFieldsByPk.set(pk, pkFields);
|
|
2321
3031
|
}
|
|
2322
|
-
|
|
2323
|
-
|
|
2324
|
-
|
|
2325
|
-
|
|
2326
|
-
|
|
2327
|
-
|
|
2328
|
-
|
|
2329
|
-
|
|
3032
|
+
for (const key of keys) {
|
|
3033
|
+
pkFields.add(key);
|
|
3034
|
+
let fieldPks = this.changedPksByField.get(key);
|
|
3035
|
+
if (!fieldPks) {
|
|
3036
|
+
fieldPks = /* @__PURE__ */ new Set();
|
|
3037
|
+
this.changedPksByField.set(key, fieldPks);
|
|
3038
|
+
}
|
|
3039
|
+
fieldPks.add(pk);
|
|
2330
3040
|
}
|
|
2331
|
-
this.
|
|
3041
|
+
this.changedPksEventEmitter.markUpdatedKeys([pk]);
|
|
3042
|
+
this.changedFieldsEventEmitter.markUpdatedKeys(keys);
|
|
3043
|
+
}
|
|
3044
|
+
trackPatch(pk, patch) {
|
|
3045
|
+
if (pk === void 0 || pk === null || pk === "") {
|
|
3046
|
+
throw new Error(
|
|
3047
|
+
`[OIMCollectionChangedFields]: PK is required to track changes.`
|
|
3048
|
+
);
|
|
3049
|
+
}
|
|
3050
|
+
const keys = Object.keys(patch);
|
|
3051
|
+
if (keys.length === 0) return;
|
|
3052
|
+
this.trackChangedKeys(pk, keys);
|
|
2332
3053
|
}
|
|
2333
3054
|
};
|
|
2334
3055
|
|
|
@@ -2444,7 +3165,9 @@ var OIMEventQueueSchedulerImmediate = class extends OIMEventQueueScheduler {
|
|
|
2444
3165
|
cancel() {
|
|
2445
3166
|
if (this.immediateId === void 0) return;
|
|
2446
3167
|
if (this.useSetImmediate) {
|
|
2447
|
-
clearImmediate(
|
|
3168
|
+
clearImmediate(
|
|
3169
|
+
this.immediateId
|
|
3170
|
+
);
|
|
2448
3171
|
} else if (this.useMessageChannel) {
|
|
2449
3172
|
this.pendingCallback = void 0;
|
|
2450
3173
|
} else {
|
|
@@ -2501,7 +3224,7 @@ var OIMEventQueueSchedulerFactory = class {
|
|
|
2501
3224
|
}
|
|
2502
3225
|
};
|
|
2503
3226
|
|
|
2504
|
-
// src/
|
|
3227
|
+
// src/constants/OIMDBSettings.ts
|
|
2505
3228
|
var OIMDBSettings = class {
|
|
2506
3229
|
};
|
|
2507
3230
|
/**
|
|
@@ -2513,11 +3236,11 @@ OIMDBSettings.FLUSHING_KEYS_INDEX_KEY = "__flushingKeys__";
|
|
|
2513
3236
|
|
|
2514
3237
|
// src/modules/effect/core/OIMEffectDependencyComputed.ts
|
|
2515
3238
|
var OIMEffectDependencyComputed = class {
|
|
2516
|
-
constructor(
|
|
2517
|
-
this.
|
|
3239
|
+
constructor(source) {
|
|
3240
|
+
this.source = source;
|
|
2518
3241
|
}
|
|
2519
3242
|
subscribe(onUpdate) {
|
|
2520
|
-
return this.
|
|
3243
|
+
return this.source.emitter.on("update", onUpdate);
|
|
2521
3244
|
}
|
|
2522
3245
|
};
|
|
2523
3246
|
|
|
@@ -2629,7 +3352,7 @@ var OIMEffect = class {
|
|
|
2629
3352
|
}
|
|
2630
3353
|
};
|
|
2631
3354
|
|
|
2632
|
-
// src/modules/computed/
|
|
3355
|
+
// src/modules/computed/enums/EOIMComputedEventType.ts
|
|
2633
3356
|
var EOIMComputedEventType = /* @__PURE__ */ ((EOIMComputedEventType2) => {
|
|
2634
3357
|
EOIMComputedEventType2["UPDATE"] = "update";
|
|
2635
3358
|
return EOIMComputedEventType2;
|
|
@@ -2644,13 +3367,13 @@ var OIMComputed = class {
|
|
|
2644
3367
|
this.runtime = runtime;
|
|
2645
3368
|
this.compute = opts.compute;
|
|
2646
3369
|
this.compare = opts.compare ?? Object.is;
|
|
2647
|
-
this.
|
|
3370
|
+
this._deps = opts.deps ?? [];
|
|
2648
3371
|
this.updateEventEmitter = new OIMUpdateEventEmitter(
|
|
2649
3372
|
this.runtime.queue,
|
|
2650
3373
|
"immediate"
|
|
2651
3374
|
);
|
|
2652
3375
|
this.effect = new OIMEffect(this.runtime, {
|
|
2653
|
-
deps: this.
|
|
3376
|
+
deps: this._deps,
|
|
2654
3377
|
onUpdate: () => {
|
|
2655
3378
|
this.isDirty = true;
|
|
2656
3379
|
},
|
|
@@ -2659,6 +3382,15 @@ var OIMComputed = class {
|
|
|
2659
3382
|
}
|
|
2660
3383
|
});
|
|
2661
3384
|
}
|
|
3385
|
+
get needsRecompute() {
|
|
3386
|
+
return this.isDirty;
|
|
3387
|
+
}
|
|
3388
|
+
get isReady() {
|
|
3389
|
+
return this.hasValue;
|
|
3390
|
+
}
|
|
3391
|
+
get deps() {
|
|
3392
|
+
return this._deps;
|
|
3393
|
+
}
|
|
2662
3394
|
get() {
|
|
2663
3395
|
this.recomputeAndEmitIfChanged();
|
|
2664
3396
|
return this.value;
|
|
@@ -2693,8 +3425,8 @@ function isReadonlyArray(value) {
|
|
|
2693
3425
|
return Array.isArray(value);
|
|
2694
3426
|
}
|
|
2695
3427
|
var OIMEffectDependencyKeyed = class {
|
|
2696
|
-
constructor(
|
|
2697
|
-
this.
|
|
3428
|
+
constructor(source, keyOrKeys) {
|
|
3429
|
+
this.source = source;
|
|
2698
3430
|
if (isReadonlyArray(keyOrKeys)) {
|
|
2699
3431
|
this.keys = keyOrKeys;
|
|
2700
3432
|
} else {
|
|
@@ -2703,11 +3435,11 @@ var OIMEffectDependencyKeyed = class {
|
|
|
2703
3435
|
}
|
|
2704
3436
|
subscribe(onUpdate) {
|
|
2705
3437
|
if (this.keys !== void 0) {
|
|
2706
|
-
return this.
|
|
3438
|
+
return this.source.subscribeOnKeys(this.keys, onUpdate);
|
|
2707
3439
|
}
|
|
2708
3440
|
if (this.key === void 0) return () => {
|
|
2709
3441
|
};
|
|
2710
|
-
return this.
|
|
3442
|
+
return this.source.subscribeOnKey(this.key, onUpdate);
|
|
2711
3443
|
}
|
|
2712
3444
|
};
|
|
2713
3445
|
|
|
@@ -2719,6 +3451,9 @@ var OIMEffectDependencyKeyedObject = class {
|
|
|
2719
3451
|
keyOrKeys
|
|
2720
3452
|
);
|
|
2721
3453
|
}
|
|
3454
|
+
get source() {
|
|
3455
|
+
return this.dep.source;
|
|
3456
|
+
}
|
|
2722
3457
|
subscribe(onUpdate) {
|
|
2723
3458
|
return this.dep.subscribe(onUpdate);
|
|
2724
3459
|
}
|
|
@@ -2732,217 +3467,27 @@ var OIMEffectDependencyKeyedCollection = class {
|
|
|
2732
3467
|
pkOrPks
|
|
2733
3468
|
);
|
|
2734
3469
|
}
|
|
2735
|
-
|
|
2736
|
-
return this.dep.
|
|
2737
|
-
}
|
|
2738
|
-
};
|
|
2739
|
-
|
|
2740
|
-
// src/modules/effect/core/OIMEffectDependencyKeyedIndex.ts
|
|
2741
|
-
var OIMEffectDependencyKeyedIndex = class {
|
|
2742
|
-
constructor(index, keyOrKeys) {
|
|
2743
|
-
this.dep = new OIMEffectDependencyKeyed(
|
|
2744
|
-
index,
|
|
2745
|
-
keyOrKeys
|
|
2746
|
-
);
|
|
3470
|
+
get source() {
|
|
3471
|
+
return this.dep.source;
|
|
2747
3472
|
}
|
|
2748
3473
|
subscribe(onUpdate) {
|
|
2749
3474
|
return this.dep.subscribe(onUpdate);
|
|
2750
3475
|
}
|
|
2751
|
-
};
|
|
2752
|
-
|
|
2753
|
-
// src/modules/
|
|
2754
|
-
var
|
|
2755
|
-
constructor(
|
|
2756
|
-
this.
|
|
2757
|
-
|
|
2758
|
-
|
|
2759
|
-
|
|
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;
|
|
3476
|
+
};
|
|
3477
|
+
|
|
3478
|
+
// src/modules/effect/core/OIMEffectDependencyKeyedIndex.ts
|
|
3479
|
+
var OIMEffectDependencyKeyedIndex = class {
|
|
3480
|
+
constructor(index, keyOrKeys) {
|
|
3481
|
+
this.dep = new OIMEffectDependencyKeyed(
|
|
3482
|
+
index,
|
|
3483
|
+
keyOrKeys
|
|
3484
|
+
);
|
|
2935
3485
|
}
|
|
2936
|
-
|
|
2937
|
-
return this.
|
|
3486
|
+
get source() {
|
|
3487
|
+
return this.dep.source;
|
|
2938
3488
|
}
|
|
2939
|
-
|
|
2940
|
-
|
|
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;
|
|
3489
|
+
subscribe(onUpdate) {
|
|
3490
|
+
return this.dep.subscribe(onUpdate);
|
|
2946
3491
|
}
|
|
2947
3492
|
};
|
|
2948
3493
|
|
|
@@ -3076,259 +3621,6 @@ var OIMIndexPksByKeysArrayBasedSelector = class extends OIMSelector {
|
|
|
3076
3621
|
return true;
|
|
3077
3622
|
}
|
|
3078
3623
|
};
|
|
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
|
-
};
|
|
3116
|
-
}
|
|
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;
|
|
3145
|
-
}
|
|
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)
|
|
3210
|
-
);
|
|
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
|
-
}
|
|
3331
|
-
};
|
|
3332
3624
|
export {
|
|
3333
3625
|
EOIMCollectionEventType,
|
|
3334
3626
|
EOIMComputedEventType,
|
|
@@ -3339,13 +3631,19 @@ export {
|
|
|
3339
3631
|
OIMCollection,
|
|
3340
3632
|
OIMCollectionByPkSelector,
|
|
3341
3633
|
OIMCollectionByPksSelector,
|
|
3342
|
-
|
|
3634
|
+
OIMCollectionChangedFields,
|
|
3635
|
+
OIMCollectionIndexFactory,
|
|
3636
|
+
OIMCollectionIndexManualOrderedArrayBased,
|
|
3637
|
+
OIMCollectionOrderedListCommandStream,
|
|
3638
|
+
OIMCollectionSelectors,
|
|
3343
3639
|
OIMCollectionStore,
|
|
3344
3640
|
OIMCollectionStoreMapDriven,
|
|
3345
3641
|
OIMComparatorFactory,
|
|
3346
|
-
|
|
3642
|
+
OIMComputeRuntime,
|
|
3347
3643
|
OIMComputed,
|
|
3348
3644
|
OIMDBSettings,
|
|
3645
|
+
OIMDerivedCollectionIndexArrayBased,
|
|
3646
|
+
OIMDerivedCollectionIndexSetBased,
|
|
3349
3647
|
OIMEffect,
|
|
3350
3648
|
OIMEffectDependencyComputed,
|
|
3351
3649
|
OIMEffectDependencyKeyed,
|
|
@@ -3363,6 +3661,7 @@ export {
|
|
|
3363
3661
|
OIMEventQueueSchedulerImmediate,
|
|
3364
3662
|
OIMEventQueueSchedulerMicrotask,
|
|
3365
3663
|
OIMEventQueueSchedulerTimeout,
|
|
3664
|
+
OIMIndex,
|
|
3366
3665
|
OIMIndexArrayBased,
|
|
3367
3666
|
OIMIndexComparatorFactory,
|
|
3368
3667
|
OIMIndexManualArrayBased,
|
|
@@ -3384,14 +3683,18 @@ export {
|
|
|
3384
3683
|
OIMObjectStoreRecordDriven,
|
|
3385
3684
|
OIMObjectValueByKeySelector,
|
|
3386
3685
|
OIMObjectValuesByKeysSelector,
|
|
3387
|
-
|
|
3686
|
+
OIMOrderedListCommandStream,
|
|
3388
3687
|
OIMPkSelectorFactory,
|
|
3389
|
-
OIMRICollection,
|
|
3390
3688
|
OIMReactiveCollection,
|
|
3689
|
+
OIMReactiveCollectionIndexManualArrayBased,
|
|
3690
|
+
OIMReactiveCollectionIndexManualSetBased,
|
|
3691
|
+
OIMReactiveIndex,
|
|
3391
3692
|
OIMReactiveIndexArrayBased,
|
|
3392
3693
|
OIMReactiveIndexManualArrayBased,
|
|
3393
3694
|
OIMReactiveIndexManualSetBased,
|
|
3394
3695
|
OIMReactiveIndexSetBased,
|
|
3395
3696
|
OIMReactiveObject,
|
|
3396
|
-
OIMSelector
|
|
3697
|
+
OIMSelector,
|
|
3698
|
+
createOIMCollectionContext,
|
|
3699
|
+
createOIMCollectionIndexFactory
|
|
3397
3700
|
};
|