@vuu-ui/vuu-data-remote 0.13.105 → 0.13.107

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (47) hide show
  1. package/cjs/ConnectionManager.js +23 -24
  2. package/cjs/ConnectionManager.js.map +1 -1
  3. package/cjs/DedicatedWorker.js +1 -6
  4. package/cjs/DedicatedWorker.js.map +1 -1
  5. package/cjs/LostConnectionHandler.js +80 -0
  6. package/cjs/LostConnectionHandler.js.map +1 -0
  7. package/cjs/VuuAuthProvider.js +87 -0
  8. package/cjs/VuuAuthProvider.js.map +1 -0
  9. package/cjs/VuuAuthenticator.js +50 -0
  10. package/cjs/VuuAuthenticator.js.map +1 -0
  11. package/cjs/WebSocketConnection.js +11 -17
  12. package/cjs/WebSocketConnection.js.map +1 -1
  13. package/cjs/authenticate.js +15 -0
  14. package/cjs/authenticate.js.map +1 -1
  15. package/cjs/index.js +9 -0
  16. package/cjs/index.js.map +1 -1
  17. package/cjs/inlined-worker.js +259 -343
  18. package/cjs/inlined-worker.js.map +1 -1
  19. package/esm/ConnectionManager.js +25 -26
  20. package/esm/ConnectionManager.js.map +1 -1
  21. package/esm/DedicatedWorker.js +1 -6
  22. package/esm/DedicatedWorker.js.map +1 -1
  23. package/esm/LostConnectionHandler.js +76 -0
  24. package/esm/LostConnectionHandler.js.map +1 -0
  25. package/esm/VuuAuthProvider.js +85 -0
  26. package/esm/VuuAuthProvider.js.map +1 -0
  27. package/esm/VuuAuthenticator.js +47 -0
  28. package/esm/VuuAuthenticator.js.map +1 -0
  29. package/esm/WebSocketConnection.js +11 -17
  30. package/esm/WebSocketConnection.js.map +1 -1
  31. package/esm/authenticate.js +15 -1
  32. package/esm/authenticate.js.map +1 -1
  33. package/esm/index.js +4 -1
  34. package/esm/index.js.map +1 -1
  35. package/esm/inlined-worker.js +259 -343
  36. package/esm/inlined-worker.js.map +1 -1
  37. package/package.json +7 -7
  38. package/types/ConnectionManager.d.ts +5 -6
  39. package/types/DedicatedWorker.d.ts +1 -2
  40. package/types/LostConnectionHandler.d.ts +28 -0
  41. package/types/VuuAuthProvider.d.ts +38 -0
  42. package/types/VuuAuthenticator.d.ts +21 -0
  43. package/types/WebSocketConnection.d.ts +19 -38
  44. package/types/authenticate.d.ts +4 -0
  45. package/types/index.d.ts +5 -2
  46. package/types/inlined-worker.d.ts +1 -1
  47. package/types/server-proxy/server-proxy.d.ts +2 -2
@@ -405,7 +405,18 @@ var MENU_RPC_TYPES = [
405
405
  "VIEW_PORT_MENU_ROW_RPC",
406
406
  "VIEW_PORT_MENU_CELL_RPC"
407
407
  ];
408
- var isSelectRequest = (message) => "type" in message && (message.type === "SELECT_ROW" || message.type === "DESELECT_ROW" || message.type === "SELECT_ROW_RANGE" || message.type === "SELECT_ALL" || message.type === "DESELECT_ALL");
408
+ var INVALID_SESSION = "Invalid session";
409
+ var SESSION_LIMIT_EXCEEDED = "User session limit exceeded";
410
+ var INVALID_TOKEN = "Invalid token";
411
+ var TOKEN_EXPIRED = "Token has expired";
412
+ var InvalidLoginMessages = [
413
+ INVALID_SESSION,
414
+ SESSION_LIMIT_EXCEEDED,
415
+ INVALID_TOKEN,
416
+ TOKEN_EXPIRED
417
+ ];
418
+ var isLoginErrorMessage = (message) => typeof message === "string" && InvalidLoginMessages.includes(message);
419
+ var isSelectRequest = (message) => message && typeof message === "object" && "type" in message && (message.type === "SELECT_ROW" || message.type === "DESELECT_ROW" || message.type === "SELECT_ROW_RANGE" || message.type === "SELECT_ALL" || message.type === "DESELECT_ALL");
409
420
  var isRpcServiceRequest = (message) => message.type === "RPC_REQUEST";
410
421
  var hasViewPortContext = (message) => message.context.type === "VIEWPORT_CONTEXT";
411
422
  var isVuuMenuRpcRequest = (message) => MENU_RPC_TYPES.includes(message["type"]);
@@ -1437,9 +1448,195 @@ var toClientRowTree = ({ rowIndex, rowKey, sel: isSelected, data, ts }, keys) =>
1437
1448
  ].concat(rest);
1438
1449
  };
1439
1450
 
1451
+ // src/WebSocketConnection.ts
1452
+ var { debug: debug3, debugEnabled: debugEnabled3, info: info2 } = logger("WebSocketConnection");
1453
+ var isLoginRejectedMessage = (message) => message !== null && "type" in message && message.type === "LOGIN_REJECTED";
1454
+ var DEFAULT_CONNECTION_TIMEOUT = 1e4;
1455
+ var parseWebSocketMessage = (message) => {
1456
+ try {
1457
+ return JSON.parse(message);
1458
+ } catch (e) {
1459
+ throw Error(\`Error parsing JSON response from server \${message}\`);
1460
+ }
1461
+ };
1462
+ var _callback, _confirmedOpen, _connectionPhase, _connectionStatus, _connectionTimeout, _deferredOpen, _protocols, _url, _ws;
1463
+ var WebSocketConnection = class extends EventEmitter {
1464
+ constructor({
1465
+ callback,
1466
+ connectionTimeout = DEFAULT_CONNECTION_TIMEOUT,
1467
+ protocols,
1468
+ url
1469
+ }) {
1470
+ super();
1471
+ __privateAdd(this, _callback);
1472
+ /**
1473
+ We are not confirmedOpen until we receive the first message from the
1474
+ server. If we get an unexpected close event before that, we consider
1475
+ the reconnect attempts as still within the connection phase, not true
1476
+ reconnection. This can happen e.g. when connecting to remote host via
1477
+ a proxy.
1478
+ */
1479
+ __privateAdd(this, _confirmedOpen, false);
1480
+ __privateAdd(this, _connectionPhase, "initial-connection");
1481
+ __privateAdd(this, _connectionStatus, "closed");
1482
+ __privateAdd(this, _connectionTimeout);
1483
+ __privateAdd(this, _deferredOpen);
1484
+ __privateAdd(this, _protocols);
1485
+ __privateAdd(this, _url);
1486
+ __privateAdd(this, _ws);
1487
+ __publicField(this, "receive", (evt) => {
1488
+ if (isLoginErrorMessage(evt.data)) {
1489
+ console.log(\`[WebSocketConnection] closed because of login issue\`);
1490
+ if (__privateGet(this, _deferredOpen)) {
1491
+ console.log(\`... and qwe have a deferred connection\`);
1492
+ }
1493
+ __privateGet(this, _callback).call(this, {
1494
+ type: "LOGIN_REJECTED",
1495
+ reason: evt.data
1496
+ });
1497
+ this.close(evt.data);
1498
+ } else {
1499
+ const vuuMessageFromServer = parseWebSocketMessage(evt.data);
1500
+ if (debugEnabled3) {
1501
+ if (vuuMessageFromServer.body.type !== "HB") {
1502
+ debug3(\`\${vuuMessageFromServer.body.type}\`);
1503
+ if (vuuMessageFromServer.body.type === "CHANGE_VP_SUCCESS") {
1504
+ debug3(JSON.stringify(vuuMessageFromServer.body));
1505
+ }
1506
+ }
1507
+ }
1508
+ __privateGet(this, _callback).call(this, vuuMessageFromServer);
1509
+ if (!this.confirmedOpen) {
1510
+ if (vuuMessageFromServer.body.type === "LOGIN_SUCCESS") {
1511
+ this.connectionStatus = __privateGet(this, _connectionPhase) === "initial-connection" ? "connected" : "reconnected";
1512
+ this.confirmedOpen = true;
1513
+ }
1514
+ }
1515
+ }
1516
+ });
1517
+ __publicField(this, "send", (msg) => {
1518
+ var _a;
1519
+ if (msg.body.type === "CHANGE_VP_RANGE") {
1520
+ info2 == null ? void 0 : info2(
1521
+ \`CHANGE_VP_RANGE<#\${msg.requestId}> \${msg.body.from}-\${msg.body.to}\`
1522
+ );
1523
+ }
1524
+ (_a = __privateGet(this, _ws)) == null ? void 0 : _a.send(JSON.stringify(msg));
1525
+ });
1526
+ __privateSet(this, _callback, callback);
1527
+ __privateSet(this, _connectionTimeout, connectionTimeout);
1528
+ __privateSet(this, _url, url);
1529
+ __privateSet(this, _protocols, protocols);
1530
+ }
1531
+ get connectionTimeout() {
1532
+ return __privateGet(this, _connectionTimeout);
1533
+ }
1534
+ get protocols() {
1535
+ return __privateGet(this, _protocols);
1536
+ }
1537
+ get isClosed() {
1538
+ return __privateGet(this, _connectionStatus) === "closed";
1539
+ }
1540
+ get isDisconnected() {
1541
+ return __privateGet(this, _connectionStatus) === "disconnected";
1542
+ }
1543
+ get connectionPhase() {
1544
+ return __privateGet(this, _connectionPhase);
1545
+ }
1546
+ get connectionStatus() {
1547
+ return __privateGet(this, _connectionStatus);
1548
+ }
1549
+ set connectionStatus(connectionStatus) {
1550
+ if (connectionStatus !== "connecting" && connectionStatus !== "reconnecting") {
1551
+ __privateSet(this, _connectionStatus, connectionStatus);
1552
+ this.emit("connection-status", __privateGet(this, _connectionStatus));
1553
+ }
1554
+ }
1555
+ get confirmedOpen() {
1556
+ return __privateGet(this, _confirmedOpen);
1557
+ }
1558
+ /**
1559
+ * We are 'confirmedOpen' when we see the first message transmitted
1560
+ * from the server. This ensures that even if we have one or more
1561
+ * proxies in our route to the endPoint, all connections have been
1562
+ * opened successfully.
1563
+ * First time in here (on our initial successful connection) we switch
1564
+ * from 'connect' phase to 'reconnect' phase. We may have different
1565
+ * retry configurations for these two phases.
1566
+ */
1567
+ set confirmedOpen(confirmedOpen) {
1568
+ __privateSet(this, _confirmedOpen, confirmedOpen);
1569
+ if (confirmedOpen && __privateGet(this, _connectionPhase) === "initial-connection") {
1570
+ __privateSet(this, _connectionPhase, "post-disconnect-reconnection");
1571
+ }
1572
+ }
1573
+ get url() {
1574
+ return __privateGet(this, _url);
1575
+ }
1576
+ async openWebSocket() {
1577
+ var _a;
1578
+ const initialConnect = __privateGet(this, _connectionPhase) === "initial-connection";
1579
+ if (__privateGet(this, _deferredOpen) === void 0) {
1580
+ __privateSet(this, _deferredOpen, new DeferredPromise());
1581
+ }
1582
+ const { connectionTimeout, protocols, url } = this;
1583
+ __privateSet(this, _connectionStatus, initialConnect ? "connecting" : "reconnecting");
1584
+ const timer = setTimeout(() => {
1585
+ throw Error(
1586
+ \`Failed to open WebSocket connection to \${url}, timed out after \${connectionTimeout}ms\`
1587
+ );
1588
+ }, connectionTimeout);
1589
+ const ws = __privateSet(this, _ws, new WebSocket(url, protocols));
1590
+ ws.onopen = () => {
1591
+ this.connectionStatus = "websocket-open";
1592
+ clearTimeout(timer);
1593
+ if (__privateGet(this, _deferredOpen)) {
1594
+ __privateGet(this, _deferredOpen).resolve(void 0);
1595
+ __privateSet(this, _deferredOpen, void 0);
1596
+ }
1597
+ };
1598
+ ws.onerror = () => {
1599
+ clearTimeout(timer);
1600
+ };
1601
+ ws.onclose = () => {
1602
+ if (!this.isClosed) {
1603
+ this.confirmedOpen = false;
1604
+ this.connectionStatus = "disconnected";
1605
+ this.close("failure");
1606
+ }
1607
+ };
1608
+ ws.onmessage = (evt) => {
1609
+ this.receive(evt);
1610
+ };
1611
+ return (_a = __privateGet(this, _deferredOpen)) == null ? void 0 : _a.promise;
1612
+ }
1613
+ close(reason = "shutdown") {
1614
+ var _a;
1615
+ this.connectionStatus = "closed";
1616
+ if (reason === "failure") {
1617
+ if (__privateGet(this, _deferredOpen)) {
1618
+ __privateGet(this, _deferredOpen).reject(Error("connection failed"));
1619
+ __privateSet(this, _deferredOpen, void 0);
1620
+ }
1621
+ } else {
1622
+ (_a = __privateGet(this, _ws)) == null ? void 0 : _a.close();
1623
+ }
1624
+ __privateSet(this, _ws, void 0);
1625
+ }
1626
+ };
1627
+ _callback = new WeakMap();
1628
+ _confirmedOpen = new WeakMap();
1629
+ _connectionPhase = new WeakMap();
1630
+ _connectionStatus = new WeakMap();
1631
+ _connectionTimeout = new WeakMap();
1632
+ _deferredOpen = new WeakMap();
1633
+ _protocols = new WeakMap();
1634
+ _url = new WeakMap();
1635
+ _ws = new WeakMap();
1636
+
1440
1637
  // src/server-proxy/server-proxy.ts
1441
1638
  var _requestId = 1;
1442
- var { debug: debug3, debugEnabled: debugEnabled3, error: error2, info: info2, infoEnabled: infoEnabled2, warn: warn2 } = logger("ServerProxy");
1639
+ var { debug: debug4, debugEnabled: debugEnabled4, error: error2, info: info3, infoEnabled: infoEnabled2, warn: warn2 } = logger("ServerProxy");
1443
1640
  var nextRequestId = () => \`\${_requestId++}\`;
1444
1641
  var DEFAULT_OPTIONS = {};
1445
1642
  var isActiveViewport = (viewPort) => viewPort.disabled !== true && viewPort.suspended !== true;
@@ -1476,13 +1673,15 @@ var ServerProxy = class {
1476
1673
  __publicField(this, "cachedTableMetaRequests", /* @__PURE__ */ new Map());
1477
1674
  __publicField(this, "cachedTableSchemas", /* @__PURE__ */ new Map());
1478
1675
  __publicField(this, "tableList");
1479
- __publicField(this, "connectionStatusChanged", (message) => {
1480
- if (message.connectionStatus === "disconnected") {
1676
+ __publicField(this, "connectionStatusChanged", (status) => {
1677
+ if (status === "disconnected") {
1678
+ this.sessionId = void 0;
1481
1679
  this.clearAllViewports();
1680
+ } else if (status === "reconnected") {
1681
+ this.reconnect();
1482
1682
  }
1483
1683
  });
1484
1684
  __publicField(this, "reconnect", async () => {
1485
- await this.login(this.authToken);
1486
1685
  const [activeViewports, inactiveViewports] = partition(
1487
1686
  Array.from(this.viewports.values()),
1488
1687
  isActiveViewport
@@ -1518,7 +1717,6 @@ var ServerProxy = class {
1518
1717
  this.postMessageToClient = callback;
1519
1718
  this.viewports = /* @__PURE__ */ new Map();
1520
1719
  this.mapClientToServerViewport = /* @__PURE__ */ new Map();
1521
- connection.on("reconnected", this.reconnect);
1522
1720
  connection.on("connection-status", this.connectionStatusChanged);
1523
1721
  }
1524
1722
  async login(authToken) {
@@ -1574,8 +1772,8 @@ var ServerProxy = class {
1574
1772
  );
1575
1773
  if (clientResponse) {
1576
1774
  this.postMessageToClient(clientResponse);
1577
- if (debugEnabled3) {
1578
- debug3(
1775
+ if (debugEnabled4) {
1776
+ debug4(
1579
1777
  \`post DataSourceSubscribedMessage to client: \${JSON.stringify(
1580
1778
  clientResponse
1581
1779
  )}\`
@@ -1649,7 +1847,7 @@ var ServerProxy = class {
1649
1847
  unsubscribe(clientViewportId) {
1650
1848
  const serverViewportId = this.mapClientToServerViewport.get(clientViewportId);
1651
1849
  if (serverViewportId) {
1652
- info2 == null ? void 0 : info2(
1850
+ info3 == null ? void 0 : info3(
1653
1851
  \`Unsubscribe Message (Client to Server):
1654
1852
  \${serverViewportId}\`
1655
1853
  );
@@ -1691,26 +1889,26 @@ var ServerProxy = class {
1691
1889
  /**********************************************************************/
1692
1890
  setViewRange(viewport, message) {
1693
1891
  const requestId = nextRequestId();
1694
- infoEnabled2 && info2(\`setViewRange (\${message.range.from}:\${message.range.to})\`);
1892
+ infoEnabled2 && info3(\`setViewRange (\${message.range.from}:\${message.range.to})\`);
1695
1893
  const [serverRequest, rows, debounceRequest] = viewport.rangeRequest(
1696
1894
  requestId,
1697
1895
  message.range
1698
1896
  );
1699
1897
  if (viewport.status === "subscribed") {
1700
- info2 == null ? void 0 : info2(\`setViewRange \${message.range.from} - \${message.range.to}\`);
1898
+ info3 == null ? void 0 : info3(\`setViewRange \${message.range.from} - \${message.range.to}\`);
1701
1899
  if (serverRequest) {
1702
1900
  if (true) {
1703
- info2 == null ? void 0 : info2(
1901
+ info3 == null ? void 0 : info3(
1704
1902
  \`CHANGE_VP_RANGE (\${message.range.from}-\${message.range.to}) => (\${serverRequest.from}-\${serverRequest.to})\`
1705
1903
  );
1706
1904
  }
1707
- infoEnabled2 && info2(
1905
+ infoEnabled2 && info3(
1708
1906
  \`setViewRange send CHANGE_VP_RANGE<#\${requestId}> (\${serverRequest.from}-\${serverRequest.to})\`
1709
1907
  );
1710
1908
  this.sendMessageToServer(serverRequest, requestId);
1711
1909
  }
1712
1910
  if (rows) {
1713
- info2 == null ? void 0 : info2(\`setViewRange \${rows.length} rows returned from cache\`);
1911
+ info3 == null ? void 0 : info3(\`setViewRange \${rows.length} rows returned from cache\`);
1714
1912
  this.postMessageToClient({
1715
1913
  mode: "update",
1716
1914
  type: "viewport-update",
@@ -1774,19 +1972,19 @@ var ServerProxy = class {
1774
1972
  viewport.suspend();
1775
1973
  if (escalateToDisable) {
1776
1974
  viewport.suspendTimer = setTimeout(() => {
1777
- info2 == null ? void 0 : info2("suspendTimer expired, escalate suspend to disable");
1975
+ info3 == null ? void 0 : info3("suspendTimer expired, escalate suspend to disable");
1778
1976
  this.disableViewport(viewport);
1779
1977
  }, escalateDelay);
1780
1978
  }
1781
1979
  }
1782
1980
  resumeViewport(viewport) {
1783
1981
  if (viewport.suspendTimer) {
1784
- debug3 == null ? void 0 : debug3("clear suspend timer");
1982
+ debug4 == null ? void 0 : debug4("clear suspend timer");
1785
1983
  clearTimeout(viewport.suspendTimer);
1786
1984
  viewport.suspendTimer = null;
1787
1985
  }
1788
1986
  const [size, rows] = viewport.resume();
1789
- debug3 == null ? void 0 : debug3(\`resumeViewport size \${size}, \${rows.length} rows sent to client\`);
1987
+ debug4 == null ? void 0 : debug4(\`resumeViewport size \${size}, \${rows.length} rows sent to client\`);
1790
1988
  this.postMessageToClient({
1791
1989
  clientViewportId: viewport.clientViewportId,
1792
1990
  mode: "update",
@@ -2036,6 +2234,14 @@ var ServerProxy = class {
2036
2234
  }
2037
2235
  handleMessageFromServer(message) {
2038
2236
  var _a, _b;
2237
+ if (isLoginRejectedMessage(message)) {
2238
+ if (this.pendingLogin) {
2239
+ this.pendingLogin.reject(message.reason);
2240
+ this.pendingLogin = void 0;
2241
+ this.authToken = "";
2242
+ }
2243
+ return;
2244
+ }
2039
2245
  const { body, requestId, sessionId } = message;
2040
2246
  const pendingRequest = this.pendingRequests.get(requestId);
2041
2247
  if (pendingRequest) {
@@ -2065,9 +2271,6 @@ var ServerProxy = class {
2065
2271
  throw Error("LOGIN_SUCCESS did not provide sessionId");
2066
2272
  }
2067
2273
  break;
2068
- case "LOGIN_FAIL":
2069
- this.postMessageToClient(body);
2070
- break;
2071
2274
  case "REMOVE_VP_SUCCESS":
2072
2275
  {
2073
2276
  const viewport = viewports.get(body.viewPortId);
@@ -2114,8 +2317,8 @@ var ServerProxy = class {
2114
2317
  const response = viewport.completeOperation(requestId);
2115
2318
  if (response !== void 0) {
2116
2319
  this.postMessageToClient(response);
2117
- if (debugEnabled3) {
2118
- debug3(\`postMessageToClient \${JSON.stringify(response)}\`);
2320
+ if (debugEnabled4) {
2321
+ debug4(\`postMessageToClient \${JSON.stringify(response)}\`);
2119
2322
  }
2120
2323
  }
2121
2324
  }
@@ -2165,28 +2368,28 @@ var ServerProxy = class {
2165
2368
  case "TABLE_ROW":
2166
2369
  {
2167
2370
  const viewportRowMap = groupRowsByViewport(body.rows);
2168
- if (debugEnabled3) {
2371
+ if (debugEnabled4) {
2169
2372
  const [firstRow] = body.rows;
2170
2373
  if (body.rows.length === 0) {
2171
- infoEnabled2 && info2("handleMessageFromServer TABLE_ROW 0 rows");
2374
+ infoEnabled2 && info3("handleMessageFromServer TABLE_ROW 0 rows");
2172
2375
  } else if ((firstRow == null ? void 0 : firstRow.rowIndex) === -1) {
2173
2376
  if (body.rows.length === 1) {
2174
2377
  if (firstRow.updateType === "SIZE") {
2175
- infoEnabled2 && info2(
2378
+ infoEnabled2 && info3(
2176
2379
  \`handleMessageFromServer [\${firstRow.viewPortId}] TABLE_ROW SIZE ONLY \${firstRow.vpSize}\`
2177
2380
  );
2178
2381
  } else {
2179
- infoEnabled2 && info2(
2382
+ infoEnabled2 && info3(
2180
2383
  \`handleMessageFromServer [\${firstRow.viewPortId}] TABLE_ROW SIZE \${firstRow.vpSize} rowIdx \${firstRow.rowIndex}\`
2181
2384
  );
2182
2385
  }
2183
2386
  } else {
2184
- infoEnabled2 && info2(
2387
+ infoEnabled2 && info3(
2185
2388
  \`handleMessageFromServer TABLE_ROW \${body.rows.length} rows, SIZE \${firstRow.vpSize}, [\${body.rows.map((r) => r.rowIndex).join(",")}]\`
2186
2389
  );
2187
2390
  }
2188
2391
  } else {
2189
- infoEnabled2 && info2(
2392
+ infoEnabled2 && info3(
2190
2393
  \`handleMessageFromServer TABLE_ROW \${body.rows.length} rows [\${body.rows.map((r) => r.rowIndex).join(",")}]\`
2191
2394
  );
2192
2395
  }
@@ -2209,7 +2412,7 @@ var ServerProxy = class {
2209
2412
  const viewport = this.viewports.get(body.viewPortId);
2210
2413
  if (viewport) {
2211
2414
  const { from, to } = body;
2212
- infoEnabled2 && info2(\`CHANGE_VP_RANGE_SUCCESS<#\${requestId}> \${from} - \${to}\`);
2415
+ infoEnabled2 && info3(\`CHANGE_VP_RANGE_SUCCESS<#\${requestId}> \${from} - \${to}\`);
2213
2416
  viewport.completeOperation(requestId, from, to);
2214
2417
  }
2215
2418
  }
@@ -2354,7 +2557,7 @@ var ServerProxy = class {
2354
2557
  error2(body.msg);
2355
2558
  break;
2356
2559
  default:
2357
- infoEnabled2 && info2(\`handleMessageFromServer \${body["type"]}.\`);
2560
+ infoEnabled2 && info3(\`handleMessageFromServer \${body["type"]}.\`);
2358
2561
  }
2359
2562
  }
2360
2563
  cacheTableMeta(messageBody) {
@@ -2393,7 +2596,7 @@ var ServerProxy = class {
2393
2596
  const [rows, mode] = result;
2394
2597
  const size = viewport.getNewRowCount();
2395
2598
  if (size !== void 0 || rows && rows.length > 0) {
2396
- debugEnabled3 && debug3(
2599
+ debugEnabled4 && debug4(
2397
2600
  \`postMessageToClient #\${viewport.clientViewportId} viewport-update \${mode}, \${(_a = rows == null ? void 0 : rows.length) != null ? _a : "no"} rows, size \${size}\`
2398
2601
  );
2399
2602
  if (mode) {
@@ -2412,316 +2615,31 @@ var ServerProxy = class {
2412
2615
  }
2413
2616
  };
2414
2617
 
2415
- // src/WebSocketConnection.ts
2416
- var { debug: debug4, debugEnabled: debugEnabled4, info: info3 } = logger("WebSocketConnection");
2417
- var isNotConnecting = (connectionState) => connectionState.connectionStatus !== "connecting" && connectionState.connectionStatus !== "reconnecting";
2418
- var isWebSocketConnectionMessage = (msg) => {
2419
- if ("connectionStatus" in msg) {
2420
- return [
2421
- "connecting",
2422
- "connected",
2423
- "connection-open-awaiting-session",
2424
- "reconnecting",
2425
- "reconnected",
2426
- "disconnected",
2427
- "closed",
2428
- "failed"
2429
- ].includes(msg.connectionStatus);
2430
- } else {
2431
- return false;
2432
- }
2433
- };
2434
- var DEFAULT_RETRY_LIMITS = {
2435
- connect: 5,
2436
- reconnect: 8
2437
- };
2438
- var DEFAULT_CONNECTION_TIMEOUT = 1e4;
2439
- var ConnectingEndState = {
2440
- connecting: "connected",
2441
- reconnecting: "reconnected"
2442
- };
2443
- var parseWebSocketMessage = (message) => {
2444
- try {
2445
- return JSON.parse(message);
2446
- } catch (e) {
2447
- throw Error(\`Error parsing JSON response from server \${message}\`);
2448
- }
2449
- };
2450
- var _callback, _confirmedOpen, _connectionState, _connectionTimeout, _deferredConnection, _protocols, _reconnectAttempts, _requiresLogin, _url, _ws;
2451
- var WebSocketConnection = class extends EventEmitter {
2452
- constructor({
2453
- callback,
2454
- connectionTimeout = DEFAULT_CONNECTION_TIMEOUT,
2455
- protocols,
2456
- retryLimits = DEFAULT_RETRY_LIMITS,
2457
- url
2458
- }) {
2459
- super();
2460
- __privateAdd(this, _callback);
2461
- /**
2462
- We are not confirmedOpen until we receive the first message from the
2463
- server. If we get an unexpected close event before that, we consider
2464
- the reconnect attempts as still within the connection phase, not true
2465
- reconnection. This can happen e.g. when connecting to remote host via
2466
- a proxy.
2467
- */
2468
- __privateAdd(this, _confirmedOpen, false);
2469
- __privateAdd(this, _connectionState);
2470
- __privateAdd(this, _connectionTimeout);
2471
- __privateAdd(this, _deferredConnection);
2472
- __privateAdd(this, _protocols);
2473
- __privateAdd(this, _reconnectAttempts);
2474
- __privateAdd(this, _requiresLogin, true);
2475
- __privateAdd(this, _url);
2476
- __privateAdd(this, _ws);
2477
- __publicField(this, "receive", (evt) => {
2478
- if (evt.data === "Invalid token" || evt.data === "Token has expired") {
2479
- const closeReason = evt.data === "Invalid token" ? "invalid-token" : "token-expired";
2480
- this.close(closeReason);
2481
- } else {
2482
- const vuuMessageFromServer = parseWebSocketMessage(evt.data);
2483
- if (vuuMessageFromServer.body.type === "CHANGE_VP_RANGE_SUCCESS") {
2484
- info3 == null ? void 0 : info3(\`CHANGE_VP_RANGE_SUCCESS<#\${vuuMessageFromServer.requestId}>\`);
2485
- }
2486
- if (debugEnabled4) {
2487
- if (vuuMessageFromServer.body.type !== "HB") {
2488
- debug4(\`\${vuuMessageFromServer.body.type}\`);
2489
- if (vuuMessageFromServer.body.type === "CHANGE_VP_SUCCESS") {
2490
- debug4(JSON.stringify(vuuMessageFromServer.body));
2491
- }
2492
- }
2493
- }
2494
- __privateGet(this, _callback).call(this, vuuMessageFromServer);
2495
- }
2496
- });
2497
- __publicField(this, "send", (msg) => {
2498
- var _a;
2499
- if (msg.body.type === "CHANGE_VP_RANGE") {
2500
- info3 == null ? void 0 : info3(
2501
- \`CHANGE_VP_RANGE<#\${msg.requestId}> \${msg.body.from}-\${msg.body.to}\`
2502
- );
2503
- }
2504
- (_a = __privateGet(this, _ws)) == null ? void 0 : _a.send(JSON.stringify(msg));
2505
- });
2506
- __privateSet(this, _callback, callback);
2507
- __privateSet(this, _connectionTimeout, connectionTimeout);
2508
- __privateSet(this, _url, url);
2509
- __privateSet(this, _protocols, protocols);
2510
- __privateSet(this, _reconnectAttempts, {
2511
- retryAttemptsTotal: retryLimits.reconnect,
2512
- retryAttemptsRemaining: retryLimits.reconnect,
2513
- secondsToNextRetry: 1
2514
- });
2515
- __privateSet(this, _connectionState, {
2516
- connectionPhase: "connecting",
2517
- connectionStatus: "closed",
2518
- retryAttemptsTotal: retryLimits.connect,
2519
- retryAttemptsRemaining: retryLimits.connect,
2520
- secondsToNextRetry: 1
2521
- });
2522
- }
2523
- get connectionTimeout() {
2524
- return __privateGet(this, _connectionTimeout);
2525
- }
2526
- get protocols() {
2527
- return __privateGet(this, _protocols);
2528
- }
2529
- get requiresLogin() {
2530
- return __privateGet(this, _requiresLogin);
2531
- }
2532
- get isClosed() {
2533
- return this.status === "closed";
2534
- }
2535
- get isDisconnected() {
2536
- return this.status === "disconnected";
2537
- }
2538
- get isConnecting() {
2539
- return __privateGet(this, _connectionState).connectionPhase === "connecting";
2540
- }
2541
- get status() {
2542
- return __privateGet(this, _connectionState).connectionStatus;
2543
- }
2544
- set status(connectionStatus) {
2545
- __privateSet(this, _connectionState, {
2546
- ...__privateGet(this, _connectionState),
2547
- connectionStatus
2548
- });
2549
- if (isNotConnecting(__privateGet(this, _connectionState))) {
2550
- this.emit("connection-status", __privateGet(this, _connectionState));
2551
- }
2552
- }
2553
- get connectionState() {
2554
- return __privateGet(this, _connectionState);
2555
- }
2556
- get hasConnectionAttemptsRemaining() {
2557
- return __privateGet(this, _connectionState).retryAttemptsRemaining > 0;
2558
- }
2559
- get confirmedOpen() {
2560
- return __privateGet(this, _confirmedOpen);
2561
- }
2562
- /**
2563
- * We are 'confirmedOpen' when we see the first message transmitted
2564
- * from the server. This ensures that even if we have one or more
2565
- * proxies in our route to the endPoint, all connections have been
2566
- * opened successfully.
2567
- * First time in here (on our initial successful connection) we switch
2568
- * from 'connect' phase to 'reconnect' phase. We may have different
2569
- * retry configurations for these two phases.
2570
- */
2571
- set confirmedOpen(confirmedOpen) {
2572
- __privateSet(this, _confirmedOpen, confirmedOpen);
2573
- if (confirmedOpen && this.isConnecting) {
2574
- __privateSet(this, _connectionState, {
2575
- ...__privateGet(this, _connectionState),
2576
- connectionPhase: "reconnecting",
2577
- ...__privateGet(this, _reconnectAttempts)
2578
- });
2579
- } else if (confirmedOpen) {
2580
- __privateSet(this, _connectionState, {
2581
- ...__privateGet(this, _connectionState),
2582
- ...__privateGet(this, _reconnectAttempts)
2583
- });
2584
- }
2585
- }
2586
- get url() {
2587
- return __privateGet(this, _url);
2588
- }
2589
- async connect(clientCall = true) {
2590
- var _a;
2591
- const state = __privateGet(this, _connectionState);
2592
- if (this.isConnecting && __privateGet(this, _deferredConnection) === void 0) {
2593
- __privateSet(this, _deferredConnection, new DeferredPromise());
2594
- }
2595
- const { connectionTimeout, protocols, url } = this;
2596
- this.status = state.connectionPhase;
2597
- const timer = setTimeout(() => {
2598
- throw Error(
2599
- \`Failed to open WebSocket connection to \${url}, timed out after \${connectionTimeout}ms\`
2600
- );
2601
- }, connectionTimeout);
2602
- const ws2 = __privateSet(this, _ws, new WebSocket(url, protocols));
2603
- ws2.onopen = () => {
2604
- const connectedStatus = ConnectingEndState[state.connectionPhase];
2605
- this.status = connectedStatus;
2606
- clearTimeout(timer);
2607
- if (__privateGet(this, _deferredConnection)) {
2608
- __privateGet(this, _deferredConnection).resolve(void 0);
2609
- __privateSet(this, _deferredConnection, void 0);
2610
- }
2611
- if (this.isConnecting) {
2612
- this.emit("connected");
2613
- } else {
2614
- this.emit("reconnected");
2615
- }
2616
- };
2617
- ws2.onerror = () => {
2618
- clearTimeout(timer);
2619
- };
2620
- ws2.onclose = () => {
2621
- if (!this.isClosed) {
2622
- this.confirmedOpen = false;
2623
- this.status = "disconnected";
2624
- if (this.hasConnectionAttemptsRemaining) {
2625
- this.reconnect();
2626
- } else {
2627
- this.close("failure");
2628
- }
2629
- }
2630
- };
2631
- ws2.onmessage = (evt) => {
2632
- if (!this.confirmedOpen) {
2633
- this.confirmedOpen = true;
2634
- }
2635
- this.receive(evt);
2636
- };
2637
- if (clientCall) {
2638
- return (_a = __privateGet(this, _deferredConnection)) == null ? void 0 : _a.promise;
2639
- }
2640
- }
2641
- reconnect() {
2642
- const { retryAttemptsRemaining, secondsToNextRetry } = __privateGet(this, _connectionState);
2643
- setTimeout(() => {
2644
- __privateSet(this, _connectionState, {
2645
- ...__privateGet(this, _connectionState),
2646
- retryAttemptsRemaining: retryAttemptsRemaining - 1,
2647
- secondsToNextRetry: secondsToNextRetry * 2
2648
- });
2649
- this.connect(false);
2650
- }, secondsToNextRetry * 1e3);
2651
- }
2652
- close(reason = "shutdown") {
2653
- var _a;
2654
- this.status = "closed";
2655
- if (reason === "failure") {
2656
- if (__privateGet(this, _deferredConnection)) {
2657
- __privateGet(this, _deferredConnection).reject(Error("connection failed"));
2658
- __privateSet(this, _deferredConnection, void 0);
2659
- }
2660
- } else {
2661
- (_a = __privateGet(this, _ws)) == null ? void 0 : _a.close();
2662
- }
2663
- this.emit("closed", { type: "websocket-closed", reason });
2664
- __privateSet(this, _ws, void 0);
2665
- }
2666
- };
2667
- _callback = new WeakMap();
2668
- _confirmedOpen = new WeakMap();
2669
- _connectionState = new WeakMap();
2670
- _connectionTimeout = new WeakMap();
2671
- _deferredConnection = new WeakMap();
2672
- _protocols = new WeakMap();
2673
- _reconnectAttempts = new WeakMap();
2674
- _requiresLogin = new WeakMap();
2675
- _url = new WeakMap();
2676
- _ws = new WeakMap();
2677
-
2678
2618
  // src/worker.ts
2679
- var server;
2619
+ var serverProxy;
2620
+ var webSocketConnection;
2680
2621
  var { info: info4, infoEnabled: infoEnabled3 } = logger("worker");
2681
- var getRetryLimits = (retryLimitDisconnect, retryLimitStartup) => {
2682
- if (retryLimitDisconnect !== void 0 && retryLimitStartup !== void 0) {
2683
- return {
2684
- connect: retryLimitStartup,
2685
- reconnect: retryLimitDisconnect
2686
- };
2687
- } else if (retryLimitDisconnect !== void 0) {
2688
- return {
2689
- connect: retryLimitDisconnect,
2690
- reconnect: retryLimitDisconnect
2691
- };
2692
- } else if (retryLimitStartup !== void 0) {
2693
- return {
2694
- connect: retryLimitStartup,
2695
- reconnect: retryLimitStartup
2696
- };
2697
- }
2698
- };
2699
- var ws;
2700
2622
  var sendMessageToClient = (message) => {
2701
2623
  postMessage(message);
2702
2624
  };
2703
- async function connectToServer(url, protocols, token, retryLimitDisconnect, retryLimitStartup) {
2704
- const websocketConnection = ws = new WebSocketConnection({
2705
- callback: (msg) => {
2706
- if (isConnectionQualityMetrics(msg)) {
2707
- postMessage({ type: "connection-metrics", messages: msg });
2708
- } else if (isWebSocketConnectionMessage(msg)) {
2709
- postMessage(msg);
2710
- } else {
2711
- server.handleMessageFromServer(msg);
2712
- }
2713
- },
2714
- protocols,
2715
- retryLimits: getRetryLimits(retryLimitStartup, retryLimitDisconnect),
2716
- url
2717
- });
2718
- websocketConnection.on("connection-status", postMessage);
2719
- websocketConnection.on("closed", postMessage);
2720
- await websocketConnection.connect();
2721
- server = new ServerProxy(websocketConnection, sendMessageToClient);
2722
- if (websocketConnection.requiresLogin) {
2723
- return await server.login(token);
2625
+ async function connectToServer(url, protocols, token) {
2626
+ if (webSocketConnection === void 0 && serverProxy === void 0) {
2627
+ webSocketConnection = new WebSocketConnection({
2628
+ callback: (msg) => {
2629
+ if (isConnectionQualityMetrics(msg)) {
2630
+ postMessage({ type: "connection-metrics", messages: msg });
2631
+ } else {
2632
+ serverProxy.handleMessageFromServer(msg);
2633
+ }
2634
+ },
2635
+ protocols,
2636
+ url
2637
+ });
2638
+ webSocketConnection.on("connection-status", postMessage);
2639
+ serverProxy = new ServerProxy(webSocketConnection, sendMessageToClient);
2724
2640
  }
2641
+ await webSocketConnection.openWebSocket();
2642
+ return serverProxy.login(token);
2725
2643
  }
2726
2644
  var handleMessageFromClient = async ({
2727
2645
  data: message
@@ -2732,9 +2650,7 @@ var handleMessageFromClient = async ({
2732
2650
  const sessionId = await connectToServer(
2733
2651
  message.url,
2734
2652
  message.protocol,
2735
- message.token,
2736
- message.retryLimitDisconnect,
2737
- message.retryLimitStartup
2653
+ message.token
2738
2654
  );
2739
2655
  postMessage({ type: "connected", sessionId });
2740
2656
  } catch (err) {
@@ -2744,20 +2660,20 @@ var handleMessageFromClient = async ({
2744
2660
  // If any of the messages below are received BEFORE we have connected and created
2745
2661
  // the server - handle accordingly
2746
2662
  case "disconnect":
2747
- server.disconnect();
2748
- ws == null ? void 0 : ws.close();
2663
+ serverProxy.disconnect();
2664
+ webSocketConnection == null ? void 0 : webSocketConnection.close();
2749
2665
  break;
2750
2666
  case "subscribe":
2751
2667
  infoEnabled3 && info4(\`client subscribe: \${JSON.stringify(message)}\`);
2752
- server.subscribe(message);
2668
+ serverProxy.subscribe(message);
2753
2669
  break;
2754
2670
  case "unsubscribe":
2755
2671
  infoEnabled3 && info4(\`client unsubscribe: \${JSON.stringify(message)}\`);
2756
- server.unsubscribe(message.viewport);
2672
+ serverProxy.unsubscribe(message.viewport);
2757
2673
  break;
2758
2674
  default:
2759
2675
  infoEnabled3 && info4(\`client message: \${JSON.stringify(message)}\`);
2760
- server.handleMessageFromClient(message);
2676
+ serverProxy.handleMessageFromClient(message);
2761
2677
  }
2762
2678
  };
2763
2679
  self.addEventListener("message", handleMessageFromClient);