@liveblocks/core 2.15.0 → 2.15.2
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/dist/index.d.mts +45 -10
- package/dist/index.d.ts +45 -10
- package/dist/index.js +2878 -2823
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +410 -355
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -6,7 +6,7 @@ var __export = (target, all) => {
|
|
|
6
6
|
|
|
7
7
|
// src/version.ts
|
|
8
8
|
var PKG_NAME = "@liveblocks/core";
|
|
9
|
-
var PKG_VERSION = "2.15.
|
|
9
|
+
var PKG_VERSION = "2.15.2";
|
|
10
10
|
var PKG_FORMAT = "esm";
|
|
11
11
|
|
|
12
12
|
// src/dupe-detection.ts
|
|
@@ -385,19 +385,319 @@ function makeBufferableEventSource() {
|
|
|
385
385
|
};
|
|
386
386
|
}
|
|
387
387
|
|
|
388
|
+
// src/lib/freeze.ts
|
|
389
|
+
var freeze = process.env.NODE_ENV === "production" ? (
|
|
390
|
+
/* istanbul ignore next */
|
|
391
|
+
(x) => x
|
|
392
|
+
) : Object.freeze;
|
|
393
|
+
|
|
394
|
+
// src/lib/signals.ts
|
|
395
|
+
var kSinks = Symbol("kSinks");
|
|
396
|
+
var kTrigger = Symbol("kTrigger");
|
|
397
|
+
var signalsToTrigger = null;
|
|
398
|
+
var trackedReads = null;
|
|
399
|
+
function batch(callback) {
|
|
400
|
+
if (signalsToTrigger !== null) {
|
|
401
|
+
callback();
|
|
402
|
+
return;
|
|
403
|
+
}
|
|
404
|
+
signalsToTrigger = /* @__PURE__ */ new Set();
|
|
405
|
+
try {
|
|
406
|
+
callback();
|
|
407
|
+
} finally {
|
|
408
|
+
for (const signal of signalsToTrigger) {
|
|
409
|
+
signal[kTrigger]();
|
|
410
|
+
}
|
|
411
|
+
signalsToTrigger = null;
|
|
412
|
+
}
|
|
413
|
+
}
|
|
414
|
+
function enqueueTrigger(signal) {
|
|
415
|
+
if (!signalsToTrigger) raise("Expected to be in an active batch");
|
|
416
|
+
signalsToTrigger.add(signal);
|
|
417
|
+
}
|
|
418
|
+
function merge(target, patch) {
|
|
419
|
+
let updated = false;
|
|
420
|
+
const newValue = { ...target };
|
|
421
|
+
Object.keys(patch).forEach((k) => {
|
|
422
|
+
const key = k;
|
|
423
|
+
const val = patch[key];
|
|
424
|
+
if (newValue[key] !== val) {
|
|
425
|
+
if (val === void 0) {
|
|
426
|
+
delete newValue[key];
|
|
427
|
+
} else {
|
|
428
|
+
newValue[key] = val;
|
|
429
|
+
}
|
|
430
|
+
updated = true;
|
|
431
|
+
}
|
|
432
|
+
});
|
|
433
|
+
return updated ? newValue : target;
|
|
434
|
+
}
|
|
435
|
+
var AbstractSignal = class {
|
|
436
|
+
/** @internal */
|
|
437
|
+
equals;
|
|
438
|
+
#eventSource;
|
|
439
|
+
/** @internal */
|
|
440
|
+
[kSinks];
|
|
441
|
+
constructor(equals) {
|
|
442
|
+
this.equals = equals ?? Object.is;
|
|
443
|
+
this.#eventSource = makeEventSource();
|
|
444
|
+
this[kSinks] = /* @__PURE__ */ new Set();
|
|
445
|
+
this.get = this.get.bind(this);
|
|
446
|
+
this.subscribe = this.subscribe.bind(this);
|
|
447
|
+
this.subscribeOnce = this.subscribeOnce.bind(this);
|
|
448
|
+
}
|
|
449
|
+
[Symbol.dispose]() {
|
|
450
|
+
this.#eventSource[Symbol.dispose]();
|
|
451
|
+
this.#eventSource = "(disposed)";
|
|
452
|
+
this.equals = "(disposed)";
|
|
453
|
+
}
|
|
454
|
+
get hasWatchers() {
|
|
455
|
+
if (this.#eventSource.count() > 0) return true;
|
|
456
|
+
for (const sink of this[kSinks]) {
|
|
457
|
+
if (sink.hasWatchers) {
|
|
458
|
+
return true;
|
|
459
|
+
}
|
|
460
|
+
}
|
|
461
|
+
return false;
|
|
462
|
+
}
|
|
463
|
+
[kTrigger]() {
|
|
464
|
+
this.#eventSource.notify();
|
|
465
|
+
for (const sink of this[kSinks]) {
|
|
466
|
+
enqueueTrigger(sink);
|
|
467
|
+
}
|
|
468
|
+
}
|
|
469
|
+
subscribe(callback) {
|
|
470
|
+
if (this.#eventSource.count() === 0) {
|
|
471
|
+
this.get();
|
|
472
|
+
}
|
|
473
|
+
return this.#eventSource.subscribe(callback);
|
|
474
|
+
}
|
|
475
|
+
subscribeOnce(callback) {
|
|
476
|
+
const unsub = this.subscribe(() => {
|
|
477
|
+
unsub();
|
|
478
|
+
return callback();
|
|
479
|
+
});
|
|
480
|
+
return unsub;
|
|
481
|
+
}
|
|
482
|
+
waitUntil() {
|
|
483
|
+
throw new Error("waitUntil not supported on Signals");
|
|
484
|
+
}
|
|
485
|
+
markSinksDirty() {
|
|
486
|
+
for (const sink of this[kSinks]) {
|
|
487
|
+
sink.markDirty();
|
|
488
|
+
}
|
|
489
|
+
}
|
|
490
|
+
addSink(sink) {
|
|
491
|
+
this[kSinks].add(sink);
|
|
492
|
+
}
|
|
493
|
+
removeSink(sink) {
|
|
494
|
+
this[kSinks].delete(sink);
|
|
495
|
+
}
|
|
496
|
+
asReadonly() {
|
|
497
|
+
return this;
|
|
498
|
+
}
|
|
499
|
+
};
|
|
500
|
+
var Signal = class extends AbstractSignal {
|
|
501
|
+
#value;
|
|
502
|
+
constructor(value, equals) {
|
|
503
|
+
super(equals);
|
|
504
|
+
this.#value = freeze(value);
|
|
505
|
+
}
|
|
506
|
+
[Symbol.dispose]() {
|
|
507
|
+
super[Symbol.dispose]();
|
|
508
|
+
this.#value = "(disposed)";
|
|
509
|
+
}
|
|
510
|
+
get() {
|
|
511
|
+
trackedReads?.add(this);
|
|
512
|
+
return this.#value;
|
|
513
|
+
}
|
|
514
|
+
set(newValue) {
|
|
515
|
+
batch(() => {
|
|
516
|
+
if (typeof newValue === "function") {
|
|
517
|
+
newValue = newValue(this.#value);
|
|
518
|
+
}
|
|
519
|
+
if (!this.equals(this.#value, newValue)) {
|
|
520
|
+
this.#value = freeze(newValue);
|
|
521
|
+
this.markSinksDirty();
|
|
522
|
+
enqueueTrigger(this);
|
|
523
|
+
}
|
|
524
|
+
});
|
|
525
|
+
}
|
|
526
|
+
};
|
|
527
|
+
var PatchableSignal = class extends Signal {
|
|
528
|
+
constructor(data) {
|
|
529
|
+
super(freeze(compactObject(data)));
|
|
530
|
+
}
|
|
531
|
+
set() {
|
|
532
|
+
throw new Error("Don't call .set() directly, use .patch()");
|
|
533
|
+
}
|
|
534
|
+
/**
|
|
535
|
+
* Patches the current object.
|
|
536
|
+
*/
|
|
537
|
+
patch(patch) {
|
|
538
|
+
super.set((old) => merge(old, patch));
|
|
539
|
+
}
|
|
540
|
+
};
|
|
541
|
+
var INITIAL = Symbol();
|
|
542
|
+
var DerivedSignal = class _DerivedSignal extends AbstractSignal {
|
|
543
|
+
#prevValue;
|
|
544
|
+
#dirty;
|
|
545
|
+
// When true, the value in #value may not be up-to-date and needs re-checking
|
|
546
|
+
#sources;
|
|
547
|
+
#deps;
|
|
548
|
+
#transform;
|
|
549
|
+
// prettier-ignore
|
|
550
|
+
static from(...args) {
|
|
551
|
+
const last = args.pop();
|
|
552
|
+
if (typeof last !== "function")
|
|
553
|
+
raise("Invalid .from() call, last argument expected to be a function");
|
|
554
|
+
if (typeof args[args.length - 1] === "function") {
|
|
555
|
+
const equals = last;
|
|
556
|
+
const transform = args.pop();
|
|
557
|
+
return new _DerivedSignal(args, transform, equals);
|
|
558
|
+
} else {
|
|
559
|
+
const transform = last;
|
|
560
|
+
return new _DerivedSignal(args, transform);
|
|
561
|
+
}
|
|
562
|
+
}
|
|
563
|
+
constructor(deps, transform, equals) {
|
|
564
|
+
super(equals);
|
|
565
|
+
this.#dirty = true;
|
|
566
|
+
this.#prevValue = INITIAL;
|
|
567
|
+
this.#deps = deps;
|
|
568
|
+
this.#sources = /* @__PURE__ */ new Set();
|
|
569
|
+
this.#transform = transform;
|
|
570
|
+
}
|
|
571
|
+
[Symbol.dispose]() {
|
|
572
|
+
for (const src of this.#sources) {
|
|
573
|
+
src.removeSink(this);
|
|
574
|
+
}
|
|
575
|
+
this.#prevValue = "(disposed)";
|
|
576
|
+
this.#sources = "(disposed)";
|
|
577
|
+
this.#deps = "(disposed)";
|
|
578
|
+
this.#transform = "(disposed)";
|
|
579
|
+
}
|
|
580
|
+
get isDirty() {
|
|
581
|
+
return this.#dirty;
|
|
582
|
+
}
|
|
583
|
+
#recompute() {
|
|
584
|
+
const oldTrackedReads = trackedReads;
|
|
585
|
+
let derived;
|
|
586
|
+
trackedReads = /* @__PURE__ */ new Set();
|
|
587
|
+
try {
|
|
588
|
+
derived = this.#transform(...this.#deps.map((p) => p.get()));
|
|
589
|
+
} finally {
|
|
590
|
+
const oldSources = this.#sources;
|
|
591
|
+
this.#sources = /* @__PURE__ */ new Set();
|
|
592
|
+
for (const sig of trackedReads) {
|
|
593
|
+
this.#sources.add(sig);
|
|
594
|
+
oldSources.delete(sig);
|
|
595
|
+
}
|
|
596
|
+
for (const oldSource of oldSources) {
|
|
597
|
+
oldSource.removeSink(this);
|
|
598
|
+
}
|
|
599
|
+
for (const newSource of this.#sources) {
|
|
600
|
+
newSource.addSink(this);
|
|
601
|
+
}
|
|
602
|
+
trackedReads = oldTrackedReads;
|
|
603
|
+
}
|
|
604
|
+
this.#dirty = false;
|
|
605
|
+
if (!this.equals(this.#prevValue, derived)) {
|
|
606
|
+
this.#prevValue = derived;
|
|
607
|
+
return true;
|
|
608
|
+
}
|
|
609
|
+
return false;
|
|
610
|
+
}
|
|
611
|
+
markDirty() {
|
|
612
|
+
if (!this.#dirty) {
|
|
613
|
+
this.#dirty = true;
|
|
614
|
+
this.markSinksDirty();
|
|
615
|
+
}
|
|
616
|
+
}
|
|
617
|
+
get() {
|
|
618
|
+
if (this.#dirty) {
|
|
619
|
+
this.#recompute();
|
|
620
|
+
}
|
|
621
|
+
trackedReads?.add(this);
|
|
622
|
+
return this.#prevValue;
|
|
623
|
+
}
|
|
624
|
+
/**
|
|
625
|
+
* Called by the Signal system if one or more of the dependent signals have
|
|
626
|
+
* changed. In the case of a DerivedSignal, we'll only want to re-evaluate
|
|
627
|
+
* the actual value if it's being watched, or any of their sinks are being
|
|
628
|
+
* watched actively.
|
|
629
|
+
*/
|
|
630
|
+
[kTrigger]() {
|
|
631
|
+
if (!this.hasWatchers) {
|
|
632
|
+
return;
|
|
633
|
+
}
|
|
634
|
+
const updated = this.#recompute();
|
|
635
|
+
if (updated) {
|
|
636
|
+
super[kTrigger]();
|
|
637
|
+
}
|
|
638
|
+
}
|
|
639
|
+
};
|
|
640
|
+
var MutableSignal = class extends AbstractSignal {
|
|
641
|
+
#state;
|
|
642
|
+
constructor(initialState) {
|
|
643
|
+
super();
|
|
644
|
+
this.#state = initialState;
|
|
645
|
+
}
|
|
646
|
+
[Symbol.dispose]() {
|
|
647
|
+
super[Symbol.dispose]();
|
|
648
|
+
this.#state = "(disposed)";
|
|
649
|
+
}
|
|
650
|
+
get() {
|
|
651
|
+
trackedReads?.add(this);
|
|
652
|
+
return this.#state;
|
|
653
|
+
}
|
|
654
|
+
/**
|
|
655
|
+
* Invokes a callback function that is allowed to mutate the given state
|
|
656
|
+
* value. Do not change the value outside of the callback.
|
|
657
|
+
*
|
|
658
|
+
* If the callback explicitly returns `false`, it's assumed that the state
|
|
659
|
+
* was not changed.
|
|
660
|
+
*/
|
|
661
|
+
mutate(callback) {
|
|
662
|
+
batch(() => {
|
|
663
|
+
const result = callback ? callback(this.#state) : true;
|
|
664
|
+
if (result !== null && typeof result === "object" && "then" in result) {
|
|
665
|
+
raise("MutableSignal.mutate() does not support async callbacks");
|
|
666
|
+
}
|
|
667
|
+
if (result !== false) {
|
|
668
|
+
this.markSinksDirty();
|
|
669
|
+
enqueueTrigger(this);
|
|
670
|
+
}
|
|
671
|
+
});
|
|
672
|
+
}
|
|
673
|
+
};
|
|
674
|
+
|
|
388
675
|
// src/lib/stringify.ts
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
676
|
+
var EXPLICIT_UNDEFINED_PLACEHOLDER = "_explicit_undefined";
|
|
677
|
+
function replacer(_key, value) {
|
|
678
|
+
return value !== null && typeof value === "object" && !Array.isArray(value) ? Object.keys(value).sort().reduce((sorted, key) => {
|
|
679
|
+
sorted[key] = value[key];
|
|
680
|
+
return sorted;
|
|
681
|
+
}, {}) : value === void 0 ? EXPLICIT_UNDEFINED_PLACEHOLDER : value;
|
|
682
|
+
}
|
|
683
|
+
function reviver(key, value) {
|
|
684
|
+
if (!key && value === EXPLICIT_UNDEFINED_PLACEHOLDER) {
|
|
685
|
+
return void 0;
|
|
686
|
+
}
|
|
687
|
+
if (value && typeof value === "object") {
|
|
688
|
+
for (const k in value) {
|
|
689
|
+
if (value[k] === EXPLICIT_UNDEFINED_PLACEHOLDER) {
|
|
690
|
+
Object.defineProperty(value, k, { value: void 0 });
|
|
691
|
+
}
|
|
692
|
+
}
|
|
693
|
+
}
|
|
694
|
+
return value;
|
|
695
|
+
}
|
|
696
|
+
function stringify(value) {
|
|
697
|
+
return JSON.stringify(value, replacer);
|
|
698
|
+
}
|
|
699
|
+
function unstringify(value) {
|
|
700
|
+
return JSON.parse(value, reviver);
|
|
401
701
|
}
|
|
402
702
|
|
|
403
703
|
// src/lib/batch.ts
|
|
@@ -492,57 +792,58 @@ var Batch = class {
|
|
|
492
792
|
}
|
|
493
793
|
};
|
|
494
794
|
function createBatchStore(batch2) {
|
|
495
|
-
const
|
|
496
|
-
const eventSource2 = makeEventSource();
|
|
795
|
+
const signal = new MutableSignal(/* @__PURE__ */ new Map());
|
|
497
796
|
function getCacheKey(args) {
|
|
498
797
|
return stringify(args);
|
|
499
798
|
}
|
|
500
|
-
function
|
|
501
|
-
|
|
502
|
-
|
|
799
|
+
function update(cacheKey, state) {
|
|
800
|
+
signal.mutate((cache) => {
|
|
801
|
+
cache.set(cacheKey, state);
|
|
802
|
+
});
|
|
503
803
|
}
|
|
504
804
|
function invalidate(inputs) {
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
805
|
+
signal.mutate((cache) => {
|
|
806
|
+
if (Array.isArray(inputs)) {
|
|
807
|
+
for (const input of inputs) {
|
|
808
|
+
cache.delete(getCacheKey(input));
|
|
809
|
+
}
|
|
810
|
+
} else {
|
|
811
|
+
cache.clear();
|
|
508
812
|
}
|
|
509
|
-
}
|
|
510
|
-
cache.clear();
|
|
511
|
-
}
|
|
512
|
-
eventSource2.notify();
|
|
813
|
+
});
|
|
513
814
|
}
|
|
514
|
-
async function
|
|
815
|
+
async function enqueue(input) {
|
|
515
816
|
const cacheKey = getCacheKey(input);
|
|
817
|
+
const cache = signal.get();
|
|
516
818
|
if (cache.has(cacheKey)) {
|
|
517
819
|
return;
|
|
518
820
|
}
|
|
519
821
|
try {
|
|
520
|
-
|
|
822
|
+
update(cacheKey, { isLoading: true });
|
|
521
823
|
const result = await batch2.get(input);
|
|
522
|
-
|
|
824
|
+
update(cacheKey, { isLoading: false, data: result });
|
|
523
825
|
} catch (error3) {
|
|
524
|
-
|
|
826
|
+
update(cacheKey, {
|
|
525
827
|
isLoading: false,
|
|
526
828
|
error: error3
|
|
527
829
|
});
|
|
528
830
|
}
|
|
529
831
|
}
|
|
530
|
-
function
|
|
832
|
+
function getItemState(input) {
|
|
531
833
|
const cacheKey = getCacheKey(input);
|
|
834
|
+
const cache = signal.get();
|
|
532
835
|
return cache.get(cacheKey);
|
|
533
836
|
}
|
|
534
837
|
function _cacheKeys() {
|
|
838
|
+
const cache = signal.get();
|
|
535
839
|
return [...cache.keys()];
|
|
536
840
|
}
|
|
537
|
-
function getBatch() {
|
|
538
|
-
return batch2;
|
|
539
|
-
}
|
|
540
841
|
return {
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
842
|
+
subscribe: signal.subscribe,
|
|
843
|
+
enqueue,
|
|
844
|
+
getItemState,
|
|
544
845
|
invalidate,
|
|
545
|
-
|
|
846
|
+
batch: batch2,
|
|
546
847
|
_cacheKeys
|
|
547
848
|
};
|
|
548
849
|
}
|
|
@@ -583,6 +884,36 @@ function createInboxNotificationId() {
|
|
|
583
884
|
return createOptimisticId(INBOX_NOTIFICATION_ID_PREFIX);
|
|
584
885
|
}
|
|
585
886
|
|
|
887
|
+
// src/lib/DefaultMap.ts
|
|
888
|
+
var DefaultMap = class extends Map {
|
|
889
|
+
#defaultFn;
|
|
890
|
+
/**
|
|
891
|
+
* If the default function is not provided to the constructor, it has to be
|
|
892
|
+
* provided in each .getOrCreate() call individually.
|
|
893
|
+
*/
|
|
894
|
+
constructor(defaultFn, entries2) {
|
|
895
|
+
super(entries2);
|
|
896
|
+
this.#defaultFn = defaultFn;
|
|
897
|
+
}
|
|
898
|
+
/**
|
|
899
|
+
* Gets the value at the given key, or creates it.
|
|
900
|
+
*
|
|
901
|
+
* Difference from normal Map: if the key does not exist, it will be created
|
|
902
|
+
* on the fly using the factory function, and that value will get returned
|
|
903
|
+
* instead of `undefined`.
|
|
904
|
+
*/
|
|
905
|
+
getOrCreate(key, defaultFn) {
|
|
906
|
+
if (super.has(key)) {
|
|
907
|
+
return super.get(key);
|
|
908
|
+
} else {
|
|
909
|
+
const fn = defaultFn ?? this.#defaultFn ?? raise("DefaultMap used without a factory function");
|
|
910
|
+
const value = fn(key);
|
|
911
|
+
this.set(key, value);
|
|
912
|
+
return value;
|
|
913
|
+
}
|
|
914
|
+
}
|
|
915
|
+
};
|
|
916
|
+
|
|
586
917
|
// src/lib/objectToQuery.ts
|
|
587
918
|
var identifierRegex = /^[a-zA-Z_][a-zA-Z0-9_]*$/;
|
|
588
919
|
function objectToQuery(obj) {
|
|
@@ -1083,40 +1414,31 @@ function createApiClient({
|
|
|
1083
1414
|
}
|
|
1084
1415
|
}
|
|
1085
1416
|
}
|
|
1086
|
-
const
|
|
1417
|
+
const attachmentUrlsBatchStoresByRoom = new DefaultMap((roomId) => {
|
|
1418
|
+
const batch2 = new Batch(
|
|
1419
|
+
async (batchedAttachmentIds) => {
|
|
1420
|
+
const attachmentIds = batchedAttachmentIds.flat();
|
|
1421
|
+
const { urls } = await httpClient.post(
|
|
1422
|
+
url`/v2/c/rooms/${roomId}/attachments/presigned-urls`,
|
|
1423
|
+
await authManager.getAuthValue({
|
|
1424
|
+
requestedScope: "comments:read",
|
|
1425
|
+
roomId
|
|
1426
|
+
}),
|
|
1427
|
+
{ attachmentIds }
|
|
1428
|
+
);
|
|
1429
|
+
return urls.map(
|
|
1430
|
+
(url2) => url2 ?? new Error("There was an error while getting this attachment's URL")
|
|
1431
|
+
);
|
|
1432
|
+
},
|
|
1433
|
+
{ delay: 50 }
|
|
1434
|
+
);
|
|
1435
|
+
return createBatchStore(batch2);
|
|
1436
|
+
});
|
|
1087
1437
|
function getOrCreateAttachmentUrlsStore(roomId) {
|
|
1088
|
-
|
|
1089
|
-
if (store === void 0) {
|
|
1090
|
-
const batch2 = new Batch(
|
|
1091
|
-
async (batchedAttachmentIds) => {
|
|
1092
|
-
const attachmentIds = batchedAttachmentIds.flat();
|
|
1093
|
-
const { urls } = await httpClient.post(
|
|
1094
|
-
url`/v2/c/rooms/${roomId}/attachments/presigned-urls`,
|
|
1095
|
-
await authManager.getAuthValue({
|
|
1096
|
-
requestedScope: "comments:read",
|
|
1097
|
-
roomId
|
|
1098
|
-
}),
|
|
1099
|
-
{
|
|
1100
|
-
attachmentIds
|
|
1101
|
-
}
|
|
1102
|
-
);
|
|
1103
|
-
return urls.map(
|
|
1104
|
-
(url2) => url2 ?? new Error(
|
|
1105
|
-
"There was an error while getting this attachment's URL"
|
|
1106
|
-
)
|
|
1107
|
-
);
|
|
1108
|
-
},
|
|
1109
|
-
{
|
|
1110
|
-
delay: 50
|
|
1111
|
-
}
|
|
1112
|
-
);
|
|
1113
|
-
store = createBatchStore(batch2);
|
|
1114
|
-
getAttachmentUrlsBatchStoreByRoom.set(roomId, store);
|
|
1115
|
-
}
|
|
1116
|
-
return store;
|
|
1438
|
+
return attachmentUrlsBatchStoresByRoom.getOrCreate(roomId);
|
|
1117
1439
|
}
|
|
1118
1440
|
function getAttachmentUrl(options) {
|
|
1119
|
-
const batch2 = getOrCreateAttachmentUrlsStore(options.roomId).
|
|
1441
|
+
const batch2 = getOrCreateAttachmentUrlsStore(options.roomId).batch;
|
|
1120
1442
|
return batch2.get(options.attachmentId);
|
|
1121
1443
|
}
|
|
1122
1444
|
async function getNotificationSettings(options) {
|
|
@@ -1142,33 +1464,25 @@ function createApiClient({
|
|
|
1142
1464
|
options.settings
|
|
1143
1465
|
);
|
|
1144
1466
|
}
|
|
1145
|
-
const
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
{
|
|
1163
|
-
delay: 50
|
|
1164
|
-
}
|
|
1165
|
-
);
|
|
1166
|
-
markInboxNotificationsAsReadBatchByRoom.set(roomId, batch2);
|
|
1167
|
-
}
|
|
1168
|
-
return batch2;
|
|
1169
|
-
}
|
|
1467
|
+
const markAsReadBatchesByRoom = new DefaultMap(
|
|
1468
|
+
(roomId) => new Batch(
|
|
1469
|
+
async (batchedInboxNotificationIds) => {
|
|
1470
|
+
const inboxNotificationIds = batchedInboxNotificationIds.flat();
|
|
1471
|
+
await httpClient.post(
|
|
1472
|
+
url`/v2/c/rooms/${roomId}/inbox-notifications/read`,
|
|
1473
|
+
await authManager.getAuthValue({
|
|
1474
|
+
requestedScope: "comments:read",
|
|
1475
|
+
roomId
|
|
1476
|
+
}),
|
|
1477
|
+
{ inboxNotificationIds }
|
|
1478
|
+
);
|
|
1479
|
+
return inboxNotificationIds;
|
|
1480
|
+
},
|
|
1481
|
+
{ delay: 50 }
|
|
1482
|
+
)
|
|
1483
|
+
);
|
|
1170
1484
|
async function markRoomInboxNotificationAsRead(options) {
|
|
1171
|
-
const batch2 =
|
|
1485
|
+
const batch2 = markAsReadBatchesByRoom.getOrCreate(options.roomId);
|
|
1172
1486
|
return batch2.get(options.inboxNotificationId);
|
|
1173
1487
|
}
|
|
1174
1488
|
async function createTextMention(options) {
|
|
@@ -3214,267 +3528,6 @@ function unlinkDevTools(roomId) {
|
|
|
3214
3528
|
});
|
|
3215
3529
|
}
|
|
3216
3530
|
|
|
3217
|
-
// src/lib/freeze.ts
|
|
3218
|
-
var freeze = process.env.NODE_ENV === "production" ? (
|
|
3219
|
-
/* istanbul ignore next */
|
|
3220
|
-
(x) => x
|
|
3221
|
-
) : Object.freeze;
|
|
3222
|
-
|
|
3223
|
-
// src/lib/signals.ts
|
|
3224
|
-
var kSinks = Symbol("kSinks");
|
|
3225
|
-
var kTrigger = Symbol("kTrigger");
|
|
3226
|
-
var signalsToTrigger = null;
|
|
3227
|
-
function batch(callback) {
|
|
3228
|
-
if (signalsToTrigger !== null) {
|
|
3229
|
-
callback();
|
|
3230
|
-
return;
|
|
3231
|
-
}
|
|
3232
|
-
signalsToTrigger = /* @__PURE__ */ new Set();
|
|
3233
|
-
try {
|
|
3234
|
-
callback();
|
|
3235
|
-
} finally {
|
|
3236
|
-
for (const signal of signalsToTrigger) {
|
|
3237
|
-
signal[kTrigger]();
|
|
3238
|
-
}
|
|
3239
|
-
signalsToTrigger = null;
|
|
3240
|
-
}
|
|
3241
|
-
}
|
|
3242
|
-
function enqueueTrigger(signal) {
|
|
3243
|
-
if (!signalsToTrigger) raise("Expected to be in an active batch");
|
|
3244
|
-
signalsToTrigger.add(signal);
|
|
3245
|
-
}
|
|
3246
|
-
function merge(target, patch) {
|
|
3247
|
-
let updated = false;
|
|
3248
|
-
const newValue = { ...target };
|
|
3249
|
-
Object.keys(patch).forEach((k) => {
|
|
3250
|
-
const key = k;
|
|
3251
|
-
const val = patch[key];
|
|
3252
|
-
if (newValue[key] !== val) {
|
|
3253
|
-
if (val === void 0) {
|
|
3254
|
-
delete newValue[key];
|
|
3255
|
-
} else {
|
|
3256
|
-
newValue[key] = val;
|
|
3257
|
-
}
|
|
3258
|
-
updated = true;
|
|
3259
|
-
}
|
|
3260
|
-
});
|
|
3261
|
-
return updated ? newValue : target;
|
|
3262
|
-
}
|
|
3263
|
-
var AbstractSignal = class {
|
|
3264
|
-
/** @internal */
|
|
3265
|
-
equals;
|
|
3266
|
-
#eventSource;
|
|
3267
|
-
/** @internal */
|
|
3268
|
-
[kSinks];
|
|
3269
|
-
constructor(equals) {
|
|
3270
|
-
this.equals = equals ?? Object.is;
|
|
3271
|
-
this.#eventSource = makeEventSource();
|
|
3272
|
-
this[kSinks] = /* @__PURE__ */ new Set();
|
|
3273
|
-
this.get = this.get.bind(this);
|
|
3274
|
-
this.subscribe = this.subscribe.bind(this);
|
|
3275
|
-
this.subscribeOnce = this.subscribeOnce.bind(this);
|
|
3276
|
-
}
|
|
3277
|
-
[Symbol.dispose]() {
|
|
3278
|
-
this.#eventSource[Symbol.dispose]();
|
|
3279
|
-
this.#eventSource = "(disposed)";
|
|
3280
|
-
this.equals = "(disposed)";
|
|
3281
|
-
}
|
|
3282
|
-
get hasWatchers() {
|
|
3283
|
-
if (this.#eventSource.count() > 0) return true;
|
|
3284
|
-
for (const sink of this[kSinks]) {
|
|
3285
|
-
if (sink.hasWatchers) {
|
|
3286
|
-
return true;
|
|
3287
|
-
}
|
|
3288
|
-
}
|
|
3289
|
-
return false;
|
|
3290
|
-
}
|
|
3291
|
-
[kTrigger]() {
|
|
3292
|
-
this.#eventSource.notify();
|
|
3293
|
-
for (const sink of this[kSinks]) {
|
|
3294
|
-
enqueueTrigger(sink);
|
|
3295
|
-
}
|
|
3296
|
-
}
|
|
3297
|
-
subscribe(callback) {
|
|
3298
|
-
return this.#eventSource.subscribe(callback);
|
|
3299
|
-
}
|
|
3300
|
-
subscribeOnce(callback) {
|
|
3301
|
-
const unsub = this.subscribe(() => {
|
|
3302
|
-
unsub();
|
|
3303
|
-
return callback();
|
|
3304
|
-
});
|
|
3305
|
-
return unsub;
|
|
3306
|
-
}
|
|
3307
|
-
waitUntil() {
|
|
3308
|
-
throw new Error("waitUntil not supported on Signals");
|
|
3309
|
-
}
|
|
3310
|
-
markSinksDirty() {
|
|
3311
|
-
for (const sink of this[kSinks]) {
|
|
3312
|
-
sink.markDirty();
|
|
3313
|
-
}
|
|
3314
|
-
}
|
|
3315
|
-
addSink(sink) {
|
|
3316
|
-
this[kSinks].add(sink);
|
|
3317
|
-
}
|
|
3318
|
-
removeSink(sink) {
|
|
3319
|
-
this[kSinks].delete(sink);
|
|
3320
|
-
}
|
|
3321
|
-
asReadonly() {
|
|
3322
|
-
return this;
|
|
3323
|
-
}
|
|
3324
|
-
};
|
|
3325
|
-
var Signal = class extends AbstractSignal {
|
|
3326
|
-
#value;
|
|
3327
|
-
constructor(value, equals) {
|
|
3328
|
-
super(equals);
|
|
3329
|
-
this.#value = freeze(value);
|
|
3330
|
-
}
|
|
3331
|
-
[Symbol.dispose]() {
|
|
3332
|
-
super[Symbol.dispose]();
|
|
3333
|
-
this.#value = "(disposed)";
|
|
3334
|
-
}
|
|
3335
|
-
get() {
|
|
3336
|
-
return this.#value;
|
|
3337
|
-
}
|
|
3338
|
-
set(newValue) {
|
|
3339
|
-
batch(() => {
|
|
3340
|
-
if (typeof newValue === "function") {
|
|
3341
|
-
newValue = newValue(this.#value);
|
|
3342
|
-
}
|
|
3343
|
-
if (!this.equals(this.#value, newValue)) {
|
|
3344
|
-
this.#value = freeze(newValue);
|
|
3345
|
-
this.markSinksDirty();
|
|
3346
|
-
enqueueTrigger(this);
|
|
3347
|
-
}
|
|
3348
|
-
});
|
|
3349
|
-
}
|
|
3350
|
-
};
|
|
3351
|
-
var PatchableSignal = class extends Signal {
|
|
3352
|
-
constructor(data) {
|
|
3353
|
-
super(freeze(compactObject(data)));
|
|
3354
|
-
}
|
|
3355
|
-
set() {
|
|
3356
|
-
throw new Error("Don't call .set() directly, use .patch()");
|
|
3357
|
-
}
|
|
3358
|
-
/**
|
|
3359
|
-
* Patches the current object.
|
|
3360
|
-
*/
|
|
3361
|
-
patch(patch) {
|
|
3362
|
-
super.set((old) => merge(old, patch));
|
|
3363
|
-
}
|
|
3364
|
-
};
|
|
3365
|
-
var INITIAL = Symbol();
|
|
3366
|
-
var DerivedSignal = class _DerivedSignal extends AbstractSignal {
|
|
3367
|
-
#prevValue;
|
|
3368
|
-
#dirty;
|
|
3369
|
-
// When true, the value in #value may not be up-to-date and needs re-checking
|
|
3370
|
-
#parents;
|
|
3371
|
-
#transform;
|
|
3372
|
-
// prettier-ignore
|
|
3373
|
-
static from(...args) {
|
|
3374
|
-
const last = args.pop();
|
|
3375
|
-
if (typeof last !== "function")
|
|
3376
|
-
raise("Invalid .from() call, last argument expected to be a function");
|
|
3377
|
-
if (typeof args[args.length - 1] === "function") {
|
|
3378
|
-
const equals = last;
|
|
3379
|
-
const transform = args.pop();
|
|
3380
|
-
return new _DerivedSignal(args, transform, equals);
|
|
3381
|
-
} else {
|
|
3382
|
-
const transform = last;
|
|
3383
|
-
return new _DerivedSignal(args, transform);
|
|
3384
|
-
}
|
|
3385
|
-
}
|
|
3386
|
-
constructor(parents, transform, equals) {
|
|
3387
|
-
super(equals);
|
|
3388
|
-
this.#dirty = true;
|
|
3389
|
-
this.#prevValue = INITIAL;
|
|
3390
|
-
this.#parents = parents;
|
|
3391
|
-
this.#transform = transform;
|
|
3392
|
-
for (const parent of parents) {
|
|
3393
|
-
parent.addSink(this);
|
|
3394
|
-
}
|
|
3395
|
-
}
|
|
3396
|
-
[Symbol.dispose]() {
|
|
3397
|
-
for (const parent of this.#parents) {
|
|
3398
|
-
parent.removeSink(this);
|
|
3399
|
-
}
|
|
3400
|
-
this.#prevValue = "(disposed)";
|
|
3401
|
-
this.#parents = "(disposed)";
|
|
3402
|
-
this.#transform = "(disposed)";
|
|
3403
|
-
}
|
|
3404
|
-
get isDirty() {
|
|
3405
|
-
return this.#dirty;
|
|
3406
|
-
}
|
|
3407
|
-
#recompute() {
|
|
3408
|
-
const derived = this.#transform(...this.#parents.map((p) => p.get()));
|
|
3409
|
-
this.#dirty = false;
|
|
3410
|
-
if (!this.equals(this.#prevValue, derived)) {
|
|
3411
|
-
this.#prevValue = derived;
|
|
3412
|
-
return true;
|
|
3413
|
-
}
|
|
3414
|
-
return false;
|
|
3415
|
-
}
|
|
3416
|
-
markDirty() {
|
|
3417
|
-
if (!this.#dirty) {
|
|
3418
|
-
this.#dirty = true;
|
|
3419
|
-
this.markSinksDirty();
|
|
3420
|
-
}
|
|
3421
|
-
}
|
|
3422
|
-
get() {
|
|
3423
|
-
if (this.#dirty) {
|
|
3424
|
-
this.#recompute();
|
|
3425
|
-
}
|
|
3426
|
-
return this.#prevValue;
|
|
3427
|
-
}
|
|
3428
|
-
/**
|
|
3429
|
-
* Called by the Signal system if one or more of the dependent signals have
|
|
3430
|
-
* changed. In the case of a DerivedSignal, we'll only want to re-evaluate
|
|
3431
|
-
* the actual value if it's being watched, or any of their sinks are being
|
|
3432
|
-
* watched actively.
|
|
3433
|
-
*/
|
|
3434
|
-
[kTrigger]() {
|
|
3435
|
-
if (!this.hasWatchers) {
|
|
3436
|
-
return;
|
|
3437
|
-
}
|
|
3438
|
-
const updated = this.#recompute();
|
|
3439
|
-
if (updated) {
|
|
3440
|
-
super[kTrigger]();
|
|
3441
|
-
}
|
|
3442
|
-
}
|
|
3443
|
-
};
|
|
3444
|
-
var MutableSignal = class extends AbstractSignal {
|
|
3445
|
-
#state;
|
|
3446
|
-
constructor(initialState) {
|
|
3447
|
-
super();
|
|
3448
|
-
this.#state = initialState;
|
|
3449
|
-
}
|
|
3450
|
-
[Symbol.dispose]() {
|
|
3451
|
-
super[Symbol.dispose]();
|
|
3452
|
-
this.#state = "(disposed)";
|
|
3453
|
-
}
|
|
3454
|
-
get() {
|
|
3455
|
-
return this.#state;
|
|
3456
|
-
}
|
|
3457
|
-
/**
|
|
3458
|
-
* Invokes a callback function that is allowed to mutate the given state
|
|
3459
|
-
* value. Do not change the value outside of the callback.
|
|
3460
|
-
*
|
|
3461
|
-
* If the callback explicitly returns `false`, it's assumed that the state
|
|
3462
|
-
* was not changed.
|
|
3463
|
-
*/
|
|
3464
|
-
mutate(callback) {
|
|
3465
|
-
batch(() => {
|
|
3466
|
-
const result = callback ? callback(this.#state) : true;
|
|
3467
|
-
if (result !== null && typeof result === "object" && "then" in result) {
|
|
3468
|
-
raise("MutableSignal.mutate() does not support async callbacks");
|
|
3469
|
-
}
|
|
3470
|
-
if (result !== false) {
|
|
3471
|
-
this.markSinksDirty();
|
|
3472
|
-
enqueueTrigger(this);
|
|
3473
|
-
}
|
|
3474
|
-
});
|
|
3475
|
-
}
|
|
3476
|
-
};
|
|
3477
|
-
|
|
3478
3531
|
// src/lib/position.ts
|
|
3479
3532
|
var MIN_CODE = 32;
|
|
3480
3533
|
var MAX_CODE = 126;
|
|
@@ -8842,6 +8895,7 @@ export {
|
|
|
8842
8895
|
ClientMsgCode,
|
|
8843
8896
|
CommentsApiError,
|
|
8844
8897
|
CrdtType,
|
|
8898
|
+
DefaultMap,
|
|
8845
8899
|
DerivedSignal,
|
|
8846
8900
|
HttpError,
|
|
8847
8901
|
LiveList,
|
|
@@ -8917,6 +8971,7 @@ export {
|
|
|
8917
8971
|
toAbsoluteUrl,
|
|
8918
8972
|
toPlainLson,
|
|
8919
8973
|
tryParseJson,
|
|
8974
|
+
unstringify,
|
|
8920
8975
|
url,
|
|
8921
8976
|
urljoin,
|
|
8922
8977
|
wait,
|