@liveblocks/core 2.16.0-toolbars5 → 2.16.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/dist/index.d.mts +165 -75
- package/dist/index.d.ts +165 -75
- package/dist/index.js +302 -196
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +195 -89
- package/dist/index.mjs.map +1 -1
- package/package.json +2 -2
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.16.0
|
|
9
|
+
var PKG_VERSION = "2.16.0";
|
|
10
10
|
var PKG_FORMAT = "esm";
|
|
11
11
|
|
|
12
12
|
// src/dupe-detection.ts
|
|
@@ -166,6 +166,14 @@ function wrapWithTitle(method) {
|
|
|
166
166
|
var warnWithTitle = wrapWithTitle("warn");
|
|
167
167
|
var errorWithTitle = wrapWithTitle("error");
|
|
168
168
|
|
|
169
|
+
// src/lib/guards.ts
|
|
170
|
+
function isPlainObject(blob) {
|
|
171
|
+
return blob !== null && typeof blob === "object" && Object.prototype.toString.call(blob) === "[object Object]";
|
|
172
|
+
}
|
|
173
|
+
function isStartsWithOperator(blob) {
|
|
174
|
+
return isPlainObject(blob) && typeof blob.startsWith === "string";
|
|
175
|
+
}
|
|
176
|
+
|
|
169
177
|
// src/lib/utils.ts
|
|
170
178
|
function raise(msg) {
|
|
171
179
|
throw new Error(msg);
|
|
@@ -251,13 +259,48 @@ function memoizeOnSuccess(factoryFn) {
|
|
|
251
259
|
}
|
|
252
260
|
|
|
253
261
|
// src/lib/autoRetry.ts
|
|
254
|
-
var HttpError = class extends Error {
|
|
255
|
-
|
|
262
|
+
var HttpError = class _HttpError extends Error {
|
|
263
|
+
response;
|
|
264
|
+
details;
|
|
265
|
+
constructor(message, response, details) {
|
|
256
266
|
super(message);
|
|
257
|
-
this.
|
|
258
|
-
this.
|
|
267
|
+
this.name = "HttpError";
|
|
268
|
+
this.response = response;
|
|
259
269
|
this.details = details;
|
|
260
270
|
}
|
|
271
|
+
static async fromResponse(response) {
|
|
272
|
+
let bodyAsText;
|
|
273
|
+
try {
|
|
274
|
+
bodyAsText = await response.text();
|
|
275
|
+
} catch {
|
|
276
|
+
}
|
|
277
|
+
const bodyAsJson = bodyAsText ? tryParseJson(bodyAsText) : void 0;
|
|
278
|
+
let bodyAsJsonObject;
|
|
279
|
+
if (isPlainObject(bodyAsJson)) {
|
|
280
|
+
bodyAsJsonObject = bodyAsJson;
|
|
281
|
+
}
|
|
282
|
+
let message = "";
|
|
283
|
+
message ||= typeof bodyAsJsonObject?.message === "string" ? bodyAsJsonObject.message : "";
|
|
284
|
+
message ||= typeof bodyAsJsonObject?.error === "string" ? bodyAsJsonObject.error : "";
|
|
285
|
+
if (bodyAsJson === void 0) {
|
|
286
|
+
message ||= bodyAsText || "";
|
|
287
|
+
}
|
|
288
|
+
message ||= response.statusText;
|
|
289
|
+
let path;
|
|
290
|
+
try {
|
|
291
|
+
path = new URL(response.url).pathname;
|
|
292
|
+
} catch {
|
|
293
|
+
}
|
|
294
|
+
message += path !== void 0 ? ` (got status ${response.status} from ${path})` : ` (got status ${response.status})`;
|
|
295
|
+
const details = bodyAsJsonObject;
|
|
296
|
+
return new _HttpError(message, response, details);
|
|
297
|
+
}
|
|
298
|
+
/**
|
|
299
|
+
* Convenience accessor for response.status.
|
|
300
|
+
*/
|
|
301
|
+
get status() {
|
|
302
|
+
return this.response.status;
|
|
303
|
+
}
|
|
261
304
|
};
|
|
262
305
|
var DONT_RETRY_4XX = (x) => x instanceof HttpError && x.status >= 400 && x.status < 500;
|
|
263
306
|
async function autoRetry(promiseFn, maxTries, backoff, shouldStopRetrying = DONT_RETRY_4XX) {
|
|
@@ -323,7 +366,12 @@ function makeEventSource() {
|
|
|
323
366
|
}).finally(() => unsub?.());
|
|
324
367
|
}
|
|
325
368
|
function notify(event) {
|
|
326
|
-
|
|
369
|
+
let called = false;
|
|
370
|
+
for (const callback of _observers) {
|
|
371
|
+
callback(event);
|
|
372
|
+
called = true;
|
|
373
|
+
}
|
|
374
|
+
return called;
|
|
327
375
|
}
|
|
328
376
|
function count() {
|
|
329
377
|
return _observers.size;
|
|
@@ -364,8 +412,9 @@ function makeBufferableEventSource() {
|
|
|
364
412
|
function notifyOrBuffer(event) {
|
|
365
413
|
if (_buffer !== null) {
|
|
366
414
|
_buffer.push(event);
|
|
415
|
+
return false;
|
|
367
416
|
} else {
|
|
368
|
-
eventSource2.notify(event);
|
|
417
|
+
return eventSource2.notify(event);
|
|
369
418
|
}
|
|
370
419
|
}
|
|
371
420
|
return {
|
|
@@ -670,32 +719,15 @@ var MutableSignal = class extends AbstractSignal {
|
|
|
670
719
|
};
|
|
671
720
|
|
|
672
721
|
// src/lib/stringify.ts
|
|
673
|
-
var EXPLICIT_UNDEFINED_PLACEHOLDER = "_explicit_undefined";
|
|
674
722
|
function replacer(_key, value) {
|
|
675
723
|
return value !== null && typeof value === "object" && !Array.isArray(value) ? Object.keys(value).sort().reduce((sorted, key) => {
|
|
676
724
|
sorted[key] = value[key];
|
|
677
725
|
return sorted;
|
|
678
|
-
}, {}) : value
|
|
679
|
-
}
|
|
680
|
-
function reviver(key, value) {
|
|
681
|
-
if (!key && value === EXPLICIT_UNDEFINED_PLACEHOLDER) {
|
|
682
|
-
return void 0;
|
|
683
|
-
}
|
|
684
|
-
if (value && typeof value === "object") {
|
|
685
|
-
for (const k in value) {
|
|
686
|
-
if (value[k] === EXPLICIT_UNDEFINED_PLACEHOLDER) {
|
|
687
|
-
Object.defineProperty(value, k, { value: void 0 });
|
|
688
|
-
}
|
|
689
|
-
}
|
|
690
|
-
}
|
|
691
|
-
return value;
|
|
726
|
+
}, {}) : value;
|
|
692
727
|
}
|
|
693
728
|
function stringify(value) {
|
|
694
729
|
return JSON.stringify(value, replacer);
|
|
695
730
|
}
|
|
696
|
-
function unstringify(value) {
|
|
697
|
-
return JSON.parse(value, reviver);
|
|
698
|
-
}
|
|
699
731
|
|
|
700
732
|
// src/lib/batch.ts
|
|
701
733
|
var DEFAULT_SIZE = 50;
|
|
@@ -911,14 +943,6 @@ var DefaultMap = class extends Map {
|
|
|
911
943
|
}
|
|
912
944
|
};
|
|
913
945
|
|
|
914
|
-
// src/lib/guards.ts
|
|
915
|
-
function isPlainObject(blob) {
|
|
916
|
-
return blob !== null && typeof blob === "object" && Object.prototype.toString.call(blob) === "[object Object]";
|
|
917
|
-
}
|
|
918
|
-
function isStartsWithOperator(blob) {
|
|
919
|
-
return isPlainObject(blob) && typeof blob.startsWith === "string";
|
|
920
|
-
}
|
|
921
|
-
|
|
922
946
|
// src/lib/objectToQuery.ts
|
|
923
947
|
var identifierRegex = /^[a-zA-Z_][a-zA-Z0-9_]*$/;
|
|
924
948
|
function objectToQuery(obj) {
|
|
@@ -968,9 +992,7 @@ function objectToQuery(obj) {
|
|
|
968
992
|
...getFiltersFromKeyValuePairsWithOperator(nKeyValuePairsWithOperator)
|
|
969
993
|
];
|
|
970
994
|
});
|
|
971
|
-
return filterList.map(
|
|
972
|
-
({ key, operator, value }) => formatFilter(key, operator, formatFilterValue(value))
|
|
973
|
-
).join(" AND ");
|
|
995
|
+
return filterList.map(({ key, operator, value }) => `${key}${operator}${quote(value)}`).join(" ");
|
|
974
996
|
}
|
|
975
997
|
var getFiltersFromKeyValuePairs = (keyValuePairs) => {
|
|
976
998
|
const filters = [];
|
|
@@ -997,29 +1019,27 @@ var getFiltersFromKeyValuePairsWithOperator = (keyValuePairsWithOperator) => {
|
|
|
997
1019
|
return filters;
|
|
998
1020
|
};
|
|
999
1021
|
var isSimpleValue = (value) => {
|
|
1000
|
-
return typeof value === "string" || typeof value === "number" || typeof value === "boolean";
|
|
1001
|
-
};
|
|
1002
|
-
var formatFilter = (key, operator, value) => {
|
|
1003
|
-
return `${key}${operator}${value}`;
|
|
1022
|
+
return typeof value === "string" || typeof value === "number" || typeof value === "boolean" || value === null;
|
|
1004
1023
|
};
|
|
1005
1024
|
var formatFilterKey = (key, nestedKey) => {
|
|
1006
1025
|
if (nestedKey) {
|
|
1007
|
-
return `${key}[${
|
|
1026
|
+
return `${key}[${quote(nestedKey)}]`;
|
|
1008
1027
|
}
|
|
1009
1028
|
return key;
|
|
1010
1029
|
};
|
|
1011
|
-
var formatFilterValue = (value) => {
|
|
1012
|
-
if (typeof value === "string") {
|
|
1013
|
-
if (isStringEmpty(value)) {
|
|
1014
|
-
throw new Error("Value cannot be empty");
|
|
1015
|
-
}
|
|
1016
|
-
return JSON.stringify(value);
|
|
1017
|
-
}
|
|
1018
|
-
return value.toString();
|
|
1019
|
-
};
|
|
1020
1030
|
var isStringEmpty = (value) => {
|
|
1021
1031
|
return !value || value.toString().trim() === "";
|
|
1022
1032
|
};
|
|
1033
|
+
function quote(input) {
|
|
1034
|
+
const result = JSON.stringify(input);
|
|
1035
|
+
if (typeof input !== "string") {
|
|
1036
|
+
return result;
|
|
1037
|
+
}
|
|
1038
|
+
if (result.includes("'")) {
|
|
1039
|
+
return result;
|
|
1040
|
+
}
|
|
1041
|
+
return `'${result.slice(1, -1).replace(/\\"/g, '"')}'`;
|
|
1042
|
+
}
|
|
1023
1043
|
|
|
1024
1044
|
// src/lib/url.ts
|
|
1025
1045
|
function toURLSearchParams(params) {
|
|
@@ -1844,14 +1864,7 @@ var HttpClient = class {
|
|
|
1844
1864
|
async #fetch(endpoint, authValue, options, params) {
|
|
1845
1865
|
const response = await this.#rawFetch(endpoint, authValue, options, params);
|
|
1846
1866
|
if (!response.ok) {
|
|
1847
|
-
|
|
1848
|
-
try {
|
|
1849
|
-
const errorBody = await response.json();
|
|
1850
|
-
error3 = new HttpError(errorBody.message, response.status, errorBody);
|
|
1851
|
-
} catch {
|
|
1852
|
-
error3 = new HttpError(response.statusText, response.status);
|
|
1853
|
-
}
|
|
1854
|
-
throw error3;
|
|
1867
|
+
throw await HttpError.fromResponse(response);
|
|
1855
1868
|
}
|
|
1856
1869
|
let body;
|
|
1857
1870
|
try {
|
|
@@ -2495,13 +2508,6 @@ var StopRetrying = class extends Error {
|
|
|
2495
2508
|
super(reason);
|
|
2496
2509
|
}
|
|
2497
2510
|
};
|
|
2498
|
-
var LiveblocksError = class extends Error {
|
|
2499
|
-
/** @internal */
|
|
2500
|
-
constructor(message, code) {
|
|
2501
|
-
super(message);
|
|
2502
|
-
this.code = code;
|
|
2503
|
-
}
|
|
2504
|
-
};
|
|
2505
2511
|
function nextBackoffDelay(currentDelay, delays) {
|
|
2506
2512
|
return delays.find((delay) => delay > currentDelay) ?? delays[delays.length - 1];
|
|
2507
2513
|
}
|
|
@@ -2611,11 +2617,10 @@ var assign = (patch) => (ctx) => ctx.patch(patch);
|
|
|
2611
2617
|
function createConnectionStateMachine(delegates, options) {
|
|
2612
2618
|
const onMessage = makeBufferableEventSource();
|
|
2613
2619
|
onMessage.pause();
|
|
2614
|
-
const
|
|
2615
|
-
function fireErrorEvent(
|
|
2620
|
+
const onConnectionError = makeEventSource();
|
|
2621
|
+
function fireErrorEvent(message, code) {
|
|
2616
2622
|
return () => {
|
|
2617
|
-
|
|
2618
|
-
onLiveblocksError.notify(err);
|
|
2623
|
+
onConnectionError.notify({ message, code });
|
|
2619
2624
|
};
|
|
2620
2625
|
}
|
|
2621
2626
|
const initialContext = {
|
|
@@ -2973,7 +2978,7 @@ function createConnectionStateMachine(delegates, options) {
|
|
|
2973
2978
|
didConnect,
|
|
2974
2979
|
didDisconnect,
|
|
2975
2980
|
onMessage: onMessage.observable,
|
|
2976
|
-
|
|
2981
|
+
onConnectionError: onConnectionError.observable
|
|
2977
2982
|
}
|
|
2978
2983
|
};
|
|
2979
2984
|
}
|
|
@@ -6237,6 +6242,83 @@ var ManagedOthers = class {
|
|
|
6237
6242
|
}
|
|
6238
6243
|
};
|
|
6239
6244
|
|
|
6245
|
+
// src/types/LiveblocksError.ts
|
|
6246
|
+
var LiveblocksError = class _LiveblocksError extends Error {
|
|
6247
|
+
context;
|
|
6248
|
+
constructor(message, context, cause) {
|
|
6249
|
+
super(message, { cause });
|
|
6250
|
+
this.context = context;
|
|
6251
|
+
this.name = "LiveblocksError";
|
|
6252
|
+
}
|
|
6253
|
+
/** Convenience accessor for error.context.roomId (if available) */
|
|
6254
|
+
get roomId() {
|
|
6255
|
+
return this.context.roomId;
|
|
6256
|
+
}
|
|
6257
|
+
/** @deprecated Prefer using `context.code` instead, to enable type narrowing */
|
|
6258
|
+
get code() {
|
|
6259
|
+
return this.context.code;
|
|
6260
|
+
}
|
|
6261
|
+
/**
|
|
6262
|
+
* Creates a LiveblocksError from a generic error, by attaching Liveblocks
|
|
6263
|
+
* contextual information like room ID, thread ID, etc.
|
|
6264
|
+
*/
|
|
6265
|
+
static from(context, cause) {
|
|
6266
|
+
return new _LiveblocksError(
|
|
6267
|
+
defaultMessageFromContext(context),
|
|
6268
|
+
context,
|
|
6269
|
+
cause
|
|
6270
|
+
);
|
|
6271
|
+
}
|
|
6272
|
+
};
|
|
6273
|
+
function defaultMessageFromContext(context) {
|
|
6274
|
+
switch (context.type) {
|
|
6275
|
+
case "ROOM_CONNECTION_ERROR": {
|
|
6276
|
+
switch (context.code) {
|
|
6277
|
+
case 4001:
|
|
6278
|
+
return "Not allowed to connect to the room";
|
|
6279
|
+
case 4005:
|
|
6280
|
+
return "Room is already full";
|
|
6281
|
+
case 4006:
|
|
6282
|
+
return "Kicked out of the room, because the room ID changed";
|
|
6283
|
+
default:
|
|
6284
|
+
return "Could not connect to the room";
|
|
6285
|
+
}
|
|
6286
|
+
}
|
|
6287
|
+
case "CREATE_THREAD_ERROR":
|
|
6288
|
+
return "Could not create new thread";
|
|
6289
|
+
case "DELETE_THREAD_ERROR":
|
|
6290
|
+
return "Could not delete thread";
|
|
6291
|
+
case "EDIT_THREAD_METADATA_ERROR":
|
|
6292
|
+
return "Could not edit thread metadata";
|
|
6293
|
+
case "MARK_THREAD_AS_RESOLVED_ERROR":
|
|
6294
|
+
return "Could not mark thread as resolved";
|
|
6295
|
+
case "MARK_THREAD_AS_UNRESOLVED_ERROR":
|
|
6296
|
+
return "Could not mark thread as unresolved";
|
|
6297
|
+
case "CREATE_COMMENT_ERROR":
|
|
6298
|
+
return "Could not create new comment";
|
|
6299
|
+
case "EDIT_COMMENT_ERROR":
|
|
6300
|
+
return "Could not edit comment";
|
|
6301
|
+
case "DELETE_COMMENT_ERROR":
|
|
6302
|
+
return "Could not delete comment";
|
|
6303
|
+
case "ADD_REACTION_ERROR":
|
|
6304
|
+
return "Could not add reaction";
|
|
6305
|
+
case "REMOVE_REACTION_ERROR":
|
|
6306
|
+
return "Could not remove reaction";
|
|
6307
|
+
case "MARK_INBOX_NOTIFICATION_AS_READ_ERROR":
|
|
6308
|
+
return "Could not mark inbox notification as read";
|
|
6309
|
+
case "DELETE_INBOX_NOTIFICATION_ERROR":
|
|
6310
|
+
return "Could not delete inbox notification";
|
|
6311
|
+
case "MARK_ALL_INBOX_NOTIFICATIONS_AS_READ_ERROR":
|
|
6312
|
+
return "Could not mark all inbox notifications as read";
|
|
6313
|
+
case "DELETE_ALL_INBOX_NOTIFICATIONS_ERROR":
|
|
6314
|
+
return "Could not delete all inbox notifications";
|
|
6315
|
+
case "UPDATE_NOTIFICATION_SETTINGS_ERROR":
|
|
6316
|
+
return "Could not update notification settings";
|
|
6317
|
+
default:
|
|
6318
|
+
return assertNever(context, "Unhandled case");
|
|
6319
|
+
}
|
|
6320
|
+
}
|
|
6321
|
+
|
|
6240
6322
|
// src/room.ts
|
|
6241
6323
|
var MAX_SOCKET_MESSAGE_SIZE = 1024 * 1024 - 1024;
|
|
6242
6324
|
function makeIdFactory(connectionId) {
|
|
@@ -6401,13 +6483,17 @@ function createRoom(options, config) {
|
|
|
6401
6483
|
managedSocket.events.statusDidChange.subscribe(handleConnectionLossEvent);
|
|
6402
6484
|
managedSocket.events.didConnect.subscribe(onDidConnect);
|
|
6403
6485
|
managedSocket.events.didDisconnect.subscribe(onDidDisconnect);
|
|
6404
|
-
managedSocket.events.
|
|
6405
|
-
|
|
6406
|
-
|
|
6407
|
-
|
|
6408
|
-
|
|
6486
|
+
managedSocket.events.onConnectionError.subscribe(({ message, code }) => {
|
|
6487
|
+
const type = "ROOM_CONNECTION_ERROR";
|
|
6488
|
+
const err = new LiveblocksError(message, { type, code, roomId });
|
|
6489
|
+
const didNotify = config.errorEventSource.notify(err);
|
|
6490
|
+
if (!didNotify) {
|
|
6491
|
+
if (process.env.NODE_ENV !== "production") {
|
|
6492
|
+
error2(
|
|
6493
|
+
`Connection to websocket server closed. Reason: ${message} (code: ${code}).`
|
|
6494
|
+
);
|
|
6495
|
+
}
|
|
6409
6496
|
}
|
|
6410
|
-
eventHub.error.notify(err);
|
|
6411
6497
|
});
|
|
6412
6498
|
const pool = {
|
|
6413
6499
|
roomId: config.roomId,
|
|
@@ -6470,7 +6556,6 @@ function createRoom(options, config) {
|
|
|
6470
6556
|
self: makeEventSource(),
|
|
6471
6557
|
myPresence: makeEventSource(),
|
|
6472
6558
|
others: makeEventSource(),
|
|
6473
|
-
error: makeEventSource(),
|
|
6474
6559
|
storageBatch: makeEventSource(),
|
|
6475
6560
|
history: makeEventSource(),
|
|
6476
6561
|
storageDidLoad: makeEventSource(),
|
|
@@ -7071,11 +7156,12 @@ ${Array.from(traces).join("\n\n")}`
|
|
|
7071
7156
|
}
|
|
7072
7157
|
return messages;
|
|
7073
7158
|
}
|
|
7074
|
-
function updateYDoc(update, guid) {
|
|
7159
|
+
function updateYDoc(update, guid, isV2) {
|
|
7075
7160
|
const clientMsg = {
|
|
7076
7161
|
type: 301 /* UPDATE_YDOC */,
|
|
7077
7162
|
update,
|
|
7078
|
-
guid
|
|
7163
|
+
guid,
|
|
7164
|
+
v2: isV2
|
|
7079
7165
|
};
|
|
7080
7166
|
context.buffer.messages.push(clientMsg);
|
|
7081
7167
|
eventHub.ydoc.notify(clientMsg);
|
|
@@ -7156,14 +7242,15 @@ ${Array.from(traces).join("\n\n")}`
|
|
|
7156
7242
|
root: nn(context.root)
|
|
7157
7243
|
};
|
|
7158
7244
|
}
|
|
7159
|
-
function fetchYDoc(vector, guid) {
|
|
7245
|
+
function fetchYDoc(vector, guid, isV2) {
|
|
7160
7246
|
if (!context.buffer.messages.find((m) => {
|
|
7161
|
-
return m.type === 300 /* FETCH_YDOC */ && m.vector === vector && m.guid === guid;
|
|
7247
|
+
return m.type === 300 /* FETCH_YDOC */ && m.vector === vector && m.guid === guid && m.v2 === isV2;
|
|
7162
7248
|
})) {
|
|
7163
7249
|
context.buffer.messages.push({
|
|
7164
7250
|
type: 300 /* FETCH_YDOC */,
|
|
7165
7251
|
vector,
|
|
7166
|
-
guid
|
|
7252
|
+
guid,
|
|
7253
|
+
v2: isV2
|
|
7167
7254
|
});
|
|
7168
7255
|
}
|
|
7169
7256
|
flushNowOrSoon();
|
|
@@ -7308,7 +7395,6 @@ ${Array.from(traces).join("\n\n")}`
|
|
|
7308
7395
|
others: eventHub.others.observable,
|
|
7309
7396
|
self: eventHub.self.observable,
|
|
7310
7397
|
myPresence: eventHub.myPresence.observable,
|
|
7311
|
-
error: eventHub.error.observable,
|
|
7312
7398
|
/** @deprecated */
|
|
7313
7399
|
storage: eventHub.storageBatch.observable,
|
|
7314
7400
|
storageBatch: eventHub.storageBatch.observable,
|
|
@@ -7499,7 +7585,11 @@ ${Array.from(traces).join("\n\n")}`
|
|
|
7499
7585
|
attachmentUrlsStore: httpClient.getOrCreateAttachmentUrlsStore(roomId)
|
|
7500
7586
|
},
|
|
7501
7587
|
id: config.roomId,
|
|
7502
|
-
subscribe: makeClassicSubscribeFn(
|
|
7588
|
+
subscribe: makeClassicSubscribeFn(
|
|
7589
|
+
config.roomId,
|
|
7590
|
+
events,
|
|
7591
|
+
config.errorEventSource
|
|
7592
|
+
),
|
|
7503
7593
|
connect: () => managedSocket.connect(),
|
|
7504
7594
|
reconnect: () => managedSocket.reconnect(),
|
|
7505
7595
|
disconnect: () => managedSocket.disconnect(),
|
|
@@ -7568,7 +7658,7 @@ ${Array.from(traces).join("\n\n")}`
|
|
|
7568
7658
|
{ enumerable: false }
|
|
7569
7659
|
);
|
|
7570
7660
|
}
|
|
7571
|
-
function makeClassicSubscribeFn(events) {
|
|
7661
|
+
function makeClassicSubscribeFn(roomId, events, errorEvents) {
|
|
7572
7662
|
function subscribeToLiveStructureDeeply(node, callback) {
|
|
7573
7663
|
return events.storageBatch.subscribe((updates) => {
|
|
7574
7664
|
const relatedUpdates = updates.filter(
|
|
@@ -7608,8 +7698,13 @@ function makeClassicSubscribeFn(events) {
|
|
|
7608
7698
|
return cb(others, internalEvent);
|
|
7609
7699
|
});
|
|
7610
7700
|
}
|
|
7611
|
-
case "error":
|
|
7612
|
-
return
|
|
7701
|
+
case "error": {
|
|
7702
|
+
return errorEvents.subscribe((err) => {
|
|
7703
|
+
if (err.roomId === roomId) {
|
|
7704
|
+
return callback(err);
|
|
7705
|
+
}
|
|
7706
|
+
});
|
|
7707
|
+
}
|
|
7613
7708
|
case "status":
|
|
7614
7709
|
return events.status.subscribe(callback);
|
|
7615
7710
|
case "lost-connection":
|
|
@@ -7781,6 +7876,7 @@ function createClient(options) {
|
|
|
7781
7876
|
},
|
|
7782
7877
|
enableDebugLogging: clientOptions.enableDebugLogging,
|
|
7783
7878
|
baseUrl,
|
|
7879
|
+
errorEventSource: liveblocksErrorSource,
|
|
7784
7880
|
unstable_fallbackToHTTP: !!clientOptions.unstable_fallbackToHTTP,
|
|
7785
7881
|
unstable_streamData: !!clientOptions.unstable_streamData,
|
|
7786
7882
|
roomHttpClient: httpClient,
|
|
@@ -7863,6 +7959,7 @@ function createClient(options) {
|
|
|
7863
7959
|
}
|
|
7864
7960
|
const syncStatusSources = [];
|
|
7865
7961
|
const syncStatusSignal = new Signal("synchronized");
|
|
7962
|
+
const liveblocksErrorSource = makeEventSource();
|
|
7866
7963
|
function getSyncStatus() {
|
|
7867
7964
|
const status = syncStatusSignal.get();
|
|
7868
7965
|
return status === "synchronizing" ? status : "synchronized";
|
|
@@ -7922,6 +8019,7 @@ function createClient(options) {
|
|
|
7922
8019
|
},
|
|
7923
8020
|
getSyncStatus,
|
|
7924
8021
|
events: {
|
|
8022
|
+
error: liveblocksErrorSource,
|
|
7925
8023
|
syncStatus: syncStatusSignal
|
|
7926
8024
|
},
|
|
7927
8025
|
// Internal
|
|
@@ -7937,7 +8035,14 @@ function createClient(options) {
|
|
|
7937
8035
|
httpClient,
|
|
7938
8036
|
// Type-level helper only, it's effectively only an identity-function at runtime
|
|
7939
8037
|
as: () => client,
|
|
7940
|
-
createSyncSource
|
|
8038
|
+
createSyncSource,
|
|
8039
|
+
emitError: (context, cause) => {
|
|
8040
|
+
const error3 = LiveblocksError.from(context, cause);
|
|
8041
|
+
const didNotify = liveblocksErrorSource.notify(error3);
|
|
8042
|
+
if (!didNotify) {
|
|
8043
|
+
error2(error3.message);
|
|
8044
|
+
}
|
|
8045
|
+
}
|
|
7941
8046
|
}
|
|
7942
8047
|
},
|
|
7943
8048
|
kInternal,
|
|
@@ -8773,6 +8878,7 @@ function makePoller(callback, intervalMs, options) {
|
|
|
8773
8878
|
}
|
|
8774
8879
|
doc?.addEventListener("visibilitychange", onVisibilityChange);
|
|
8775
8880
|
win?.addEventListener("online", onVisibilityChange);
|
|
8881
|
+
win?.addEventListener("focus", pollNowIfStale);
|
|
8776
8882
|
fsm.start();
|
|
8777
8883
|
return {
|
|
8778
8884
|
inc,
|
|
@@ -8915,6 +9021,7 @@ export {
|
|
|
8915
9021
|
LiveList,
|
|
8916
9022
|
LiveMap,
|
|
8917
9023
|
LiveObject,
|
|
9024
|
+
LiveblocksError,
|
|
8918
9025
|
MutableSignal,
|
|
8919
9026
|
NotificationsApiError,
|
|
8920
9027
|
OpCode,
|
|
@@ -8986,7 +9093,6 @@ export {
|
|
|
8986
9093
|
toAbsoluteUrl,
|
|
8987
9094
|
toPlainLson,
|
|
8988
9095
|
tryParseJson,
|
|
8989
|
-
unstringify,
|
|
8990
9096
|
url,
|
|
8991
9097
|
urljoin,
|
|
8992
9098
|
wait,
|