@genesislcap/foundation-comms 15.68.0 → 15.69.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.
@@ -1 +1 @@
1
- {"version":3,"file":"reconnectStrategy.d.ts","sourceRoot":"","sources":["../../../src/connect/reconnectStrategy.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,MAAM,CAAC;AAK5C;;;GAGG;AACH,eAAO,MAAM,sBAAsB,KAAK,CAAC;AAEzC;;;GAGG;AACH,oBAAY,uBAAuB;IACjC,MAAM,WAAW;IACjB,WAAW,gBAAgB;CAC5B;AAED;;;GAGG;AACH,MAAM,MAAM,sBAAsB,GAAG;IACnC,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B;;;;;OAKG;IACH,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B;;;OAGG;IACH,iBAAiB,CAAC,EAAE,QAAQ,CAAC,GAAG,CAAC,CAAC;IAClC;;;;;OAKG;IACH,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B;;;OAGG;IACH,iBAAiB,CAAC,EAAE,uBAAuB,CAAC;CAC7C,CAAC;AAEF;;;;;;GAMG;AACH,MAAM,MAAM,wBAAwB,GAAG,CACrC,gBAAgB,EAAE,sBAAsB,EACxC,QAAQ,CAAC,EAAE,MAAM,KACd,MAAM,CAAC;AAEZ;;;;;;GAMG;AACH,eAAO,MAAM,aAAa,GACxB,kBAAkB,sBAAsB,EACxC,WAAW,wBAAwB,uBAoBpC,CAAC;AAEF;;;;;;GAMG;AACH,eAAO,MAAM,oBAAoB,EAAE,wBAWlC,CAAC;AAEF;;;;;GAKG;AACH,eAAO,MAAM,eAAe,EAAE,wBAS7B,CAAC"}
1
+ {"version":3,"file":"reconnectStrategy.d.ts","sourceRoot":"","sources":["../../../src/connect/reconnectStrategy.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,MAAM,CAAC;AAK5C;;;GAGG;AACH,eAAO,MAAM,sBAAsB,KAAK,CAAC;AAEzC;;;GAGG;AACH,oBAAY,uBAAuB;IACjC,MAAM,WAAW;IACjB,WAAW,gBAAgB;CAC5B;AAED;;;GAGG;AACH,MAAM,MAAM,sBAAsB,GAAG;IACnC,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B;;;;;OAKG;IACH,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B;;;OAGG;IACH,iBAAiB,CAAC,EAAE,QAAQ,CAAC,GAAG,CAAC,CAAC;IAClC;;;;;OAKG;IACH,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAC3B;;;OAGG;IACH,iBAAiB,CAAC,EAAE,uBAAuB,CAAC;CAC7C,CAAC;AAEF;;;;;;GAMG;AACH,MAAM,MAAM,wBAAwB,GAAG,CACrC,gBAAgB,EAAE,sBAAsB,EACxC,QAAQ,CAAC,EAAE,MAAM,KACd,MAAM,CAAC;AAEZ;;;;;;GAMG;AACH,eAAO,MAAM,aAAa,GACxB,kBAAkB,sBAAsB,EACxC,WAAW,wBAAwB,uBAuBpC,CAAC;AAEF;;;;;;GAMG;AACH,eAAO,MAAM,oBAAoB,EAAE,wBAWlC,CAAC;AAEF;;;;;GAKG;AACH,eAAO,MAAM,eAAe,EAAE,wBAS7B,CAAC"}
@@ -23,12 +23,16 @@ export declare enum SessionRefreshResult {
23
23
  * trying to reauthenticate simultaneously.
24
24
  *
25
25
  * @public
26
- * @param options - Optional configuration
27
- * @param options.reloadOnFailure - Whether to reload the page if refresh fails (default: true)
26
+ * @param options - `reloadOnFailure` reloads the page if the refresh fails (default: true). `signal` aborts the session
27
+ * check; a refresh that has started is never aborted, because the server revokes the old refresh token as soon as it
28
+ * issues a new one, so the new cookie must be allowed to land.
28
29
  * @returns The result of the refresh attempt
30
+ * @throws If the session check or refresh could not complete (connection error, timeout, aborted check, 408, 429, 5xx,
31
+ * etc.)
29
32
  */
30
33
  export declare function tryRefreshSession(options?: {
31
34
  reloadOnFailure?: boolean;
35
+ signal?: AbortSignal;
32
36
  }): Promise<SessionRefreshResult>;
33
37
  /**
34
38
  * Subscribes to storage events to detect when another tab has finished reauthenticating.
@@ -37,4 +41,15 @@ export declare function tryRefreshSession(options?: {
37
41
  * @returns A function to unsubscribe from the storage events
38
42
  */
39
43
  export declare function onOtherTabReauthComplete(callback: () => void): () => void;
44
+ /**
45
+ * Waits until another tab finishes reauthenticating, or until `signal` aborts.
46
+ *
47
+ * @remarks
48
+ * Relies on `storage` events, which don't fire in the tab that changed the key, so when this tab holds the reauth lock
49
+ * itself only `signal` ends the wait.
50
+ *
51
+ * @public
52
+ * @param signal - Ends the wait when aborted
53
+ */
54
+ export declare function waitForOtherTabReauth(signal: AbortSignal): Promise<void>;
40
55
  //# sourceMappingURL=sessionRefresh.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"sessionRefresh.d.ts","sourceRoot":"","sources":["../../../src/connect/sessionRefresh.ts"],"names":[],"mappings":"AAQA;;;GAGG;AACH,eAAO,MAAM,sBAAsB,QAAS,CAAC;AAE7C;;;GAGG;AACH,oBAAY,oBAAoB;IAC9B,yCAAyC;IACzC,OAAO,YAAY;IACnB,wCAAwC;IACxC,MAAM,WAAW;IACjB,0CAA0C;IAC1C,oBAAoB,yBAAyB;IAC7C,gCAAgC;IAChC,aAAa,kBAAkB;CAChC;AAiED;;;;;;;;;GASG;AACH,wBAAsB,iBAAiB,CACrC,OAAO,GAAE;IAAE,eAAe,CAAC,EAAE,OAAO,CAAA;CAAO,GAC1C,OAAO,CAAC,oBAAoB,CAAC,CA+B/B;AAED;;;;;GAKG;AACH,wBAAgB,wBAAwB,CAAC,QAAQ,EAAE,MAAM,IAAI,GAAG,MAAM,IAAI,CASzE"}
1
+ {"version":3,"file":"sessionRefresh.d.ts","sourceRoot":"","sources":["../../../src/connect/sessionRefresh.ts"],"names":[],"mappings":"AAcA;;;GAGG;AACH,eAAO,MAAM,sBAAsB,QAAS,CAAC;AAE7C;;;GAGG;AACH,oBAAY,oBAAoB;IAC9B,yCAAyC;IACzC,OAAO,YAAY;IACnB,wCAAwC;IACxC,MAAM,WAAW;IACjB,0CAA0C;IAC1C,oBAAoB,yBAAyB;IAC7C,gCAAgC;IAChC,aAAa,kBAAkB;CAChC;AAuFD;;;;;;;;;;;;GAYG;AACH,wBAAsB,iBAAiB,CACrC,OAAO,GAAE;IAAE,eAAe,CAAC,EAAE,OAAO,CAAC;IAAC,MAAM,CAAC,EAAE,WAAW,CAAA;CAAO,GAChE,OAAO,CAAC,oBAAoB,CAAC,CA+B/B;AAED;;;;;GAKG;AACH,wBAAgB,wBAAwB,CAAC,QAAQ,EAAE,MAAM,IAAI,GAAG,MAAM,IAAI,CASzE;AAED;;;;;;;;;GASG;AACH,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,CAcxE"}
@@ -114,6 +114,7 @@ export declare class DefaultSocket implements Socket {
114
114
  protected config: ConnectConfig;
115
115
  private readonly defaultInterval;
116
116
  private readonly secondsMultiplier;
117
+ private readonly sessionCheckTimeout;
117
118
  private websocket;
118
119
  private wsMessages;
119
120
  private wsMessageHandlers;
@@ -153,6 +154,7 @@ export declare class DefaultSocket implements Socket {
153
154
  * more info here https://docs.genesis.global/docs/develop/server-capabilities/access-control/authentication/#sessiontimeoutmins
154
155
  */
155
156
  private handleExpiredSession;
157
+ private get usesCookieAuth();
156
158
  private handleCookieBasedReauth;
157
159
  private updateSessionAndSubscriptions;
158
160
  /**
@@ -163,6 +165,8 @@ export declare class DefaultSocket implements Socket {
163
165
  private applyServerHeartbeatInterval;
164
166
  private prepareHeartbeat;
165
167
  private reconnect;
168
+ private refreshSessionBeforeReconnect;
169
+ private reloadPage;
166
170
  reset(): void;
167
171
  private cleanMessages;
168
172
  send<T>(message: Message<T | any>, needsHandling?: boolean): Promise<Message | any>;
@@ -1 +1 @@
1
- {"version":3,"file":"socket.d.ts","sourceRoot":"","sources":["../../../src/connect/socket.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"socket.d.ts","sourceRoot":"","sources":["../../../src/connect/socket.ts"],"names":[],"mappings":"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"}
@@ -28,6 +28,9 @@ export const retryInterval = (reconnectOptions, scheduler) => {
28
28
  let timeoutId;
29
29
  function recursiveTimeout() {
30
30
  observer.next(count);
31
+ if (observer.closed) {
32
+ return;
33
+ }
31
34
  clearTimeout(timeoutId);
32
35
  timeoutId = setTimeout(recursiveTimeout, scheduler(reconnectOptions, count));
33
36
  count = count + 1;
@@ -1,9 +1,15 @@
1
1
  import { __awaiter } from "tslib";
2
2
  import { LOGIN_DETAILS_URL, LOGIN_URL } from '@genesislcap/foundation-utils';
3
3
  import { DI } from '@genesislcap/web-core';
4
+ import { logger } from '../utils';
4
5
  import { Http } from './http';
5
6
  const REAUTH_ACTION_LOCK_KEY = 'reauthActionLock';
6
7
  const HTTP_STATUS_UNAUTHORIZED = 401;
8
+ const HTTP_CLIENT_ERROR_MIN = 400;
9
+ const HTTP_SERVER_ERROR_MIN = 500;
10
+ const HTTP_STATUS_REQUEST_TIMEOUT = 408;
11
+ const HTTP_STATUS_TOO_MANY_REQUESTS = 429;
12
+ const TRANSIENT_CLIENT_ERRORS = [HTTP_STATUS_REQUEST_TIMEOUT, HTTP_STATUS_TOO_MANY_REQUESTS];
7
13
  /**
8
14
  * How long a reauth lock is honoured before {@link tryRefreshSession} treats it as abandoned and clears it.
9
15
  * @public
@@ -57,9 +63,9 @@ function releaseLock() {
57
63
  * Checks if the user is currently authenticated.
58
64
  * @internal
59
65
  */
60
- function isAuthenticated() {
66
+ function isAuthenticated(signal) {
61
67
  return __awaiter(this, void 0, void 0, function* () {
62
- const loginDetailsFetch = yield fetch(LOGIN_DETAILS_URL, { credentials: 'include' });
68
+ const loginDetailsFetch = yield fetch(LOGIN_DETAILS_URL, { credentials: 'include', signal });
63
69
  // An expired session can answer 401 without a JSON body; that still means "refresh needed".
64
70
  if (loginDetailsFetch.status === HTTP_STATUS_UNAUTHORIZED) {
65
71
  return false;
@@ -68,22 +74,42 @@ function isAuthenticated() {
68
74
  return loginDetails.MESSAGE_TYPE === 'EVENT_LOGIN_DETAILS_ACK';
69
75
  });
70
76
  }
77
+ const isRejectedByServer = (error) => {
78
+ const status = error === null || error === void 0 ? void 0 : error.status;
79
+ return (typeof status === 'number' &&
80
+ status >= HTTP_CLIENT_ERROR_MIN &&
81
+ status < HTTP_SERVER_ERROR_MIN &&
82
+ !TRANSIENT_CLIENT_ERRORS.includes(status));
83
+ };
71
84
  /**
72
85
  * Attempts to refresh the session via EVENT_LOGIN_AUTH.
73
86
  * @internal
74
- * @returns true if refresh was successful (HTTP 2xx response)
75
- * @throws If the network request fails (connection error, timeout, etc.)
87
+ * @returns true if refresh was successful; false if the server rejected it (NACK or 4xx other than 408/429)
88
+ * @throws If the request could not complete (connection error, timeout, 408, 429, 5xx, etc.)
76
89
  */
77
90
  function performRefresh() {
78
91
  return __awaiter(this, void 0, void 0, function* () {
79
92
  const http = DI.getOrCreateDOMContainer().get(Http);
80
- const refreshLoginResponse = yield http.post(LOGIN_URL, {
81
- body: JSON.stringify({
82
- DETAILS: {},
83
- MESSAGE_TYPE: 'EVENT_LOGIN_AUTH',
84
- }),
85
- });
86
- return refreshLoginResponse.MESSAGE_TYPE === 'EVENT_LOGIN_AUTH_ACK';
93
+ try {
94
+ const refreshLoginResponse = yield http.post(LOGIN_URL, {
95
+ body: JSON.stringify({
96
+ DETAILS: {},
97
+ MESSAGE_TYPE: 'EVENT_LOGIN_AUTH',
98
+ }),
99
+ });
100
+ if (refreshLoginResponse.MESSAGE_TYPE === 'EVENT_LOGIN_AUTH_ACK') {
101
+ return true;
102
+ }
103
+ logger.debug('Session refresh rejected: ', refreshLoginResponse.ERROR);
104
+ return false;
105
+ }
106
+ catch (error) {
107
+ if (isRejectedByServer(error)) {
108
+ logger.debug(`Session refresh rejected with HTTP ${error.status}`);
109
+ return false;
110
+ }
111
+ throw error;
112
+ }
87
113
  });
88
114
  }
89
115
  /**
@@ -92,13 +118,16 @@ function performRefresh() {
92
118
  * trying to reauthenticate simultaneously.
93
119
  *
94
120
  * @public
95
- * @param options - Optional configuration
96
- * @param options.reloadOnFailure - Whether to reload the page if refresh fails (default: true)
121
+ * @param options - `reloadOnFailure` reloads the page if the refresh fails (default: true). `signal` aborts the session
122
+ * check; a refresh that has started is never aborted, because the server revokes the old refresh token as soon as it
123
+ * issues a new one, so the new cookie must be allowed to land.
97
124
  * @returns The result of the refresh attempt
125
+ * @throws If the session check or refresh could not complete (connection error, timeout, aborted check, 408, 429, 5xx,
126
+ * etc.)
98
127
  */
99
128
  export function tryRefreshSession() {
100
129
  return __awaiter(this, arguments, void 0, function* (options = {}) {
101
- const { reloadOnFailure = true } = options;
130
+ const { reloadOnFailure = true, signal } = options;
102
131
  // Clear any stale locks from crashed tabs
103
132
  clearStaleLock();
104
133
  if (!tryAcquireLock()) {
@@ -108,7 +137,7 @@ export function tryRefreshSession() {
108
137
  try {
109
138
  // Session might already be extended on another tab, so we first check if user is
110
139
  // authenticated. Cookies are shared between tabs so we can just retry.
111
- if (yield isAuthenticated()) {
140
+ if (yield isAuthenticated(signal)) {
112
141
  return SessionRefreshResult.ALREADY_VALID;
113
142
  }
114
143
  const refreshSuccessful = yield performRefresh();
@@ -141,3 +170,28 @@ export function onOtherTabReauthComplete(callback) {
141
170
  window.addEventListener('storage', handler);
142
171
  return () => window.removeEventListener('storage', handler);
143
172
  }
173
+ /**
174
+ * Waits until another tab finishes reauthenticating, or until `signal` aborts.
175
+ *
176
+ * @remarks
177
+ * Relies on `storage` events, which don't fire in the tab that changed the key, so when this tab holds the reauth lock
178
+ * itself only `signal` ends the wait.
179
+ *
180
+ * @public
181
+ * @param signal - Ends the wait when aborted
182
+ */
183
+ export function waitForOtherTabReauth(signal) {
184
+ return new Promise((resolve) => {
185
+ const done = () => {
186
+ stopListening();
187
+ signal.removeEventListener('abort', done);
188
+ resolve();
189
+ };
190
+ const stopListening = onOtherTabReauthComplete(done);
191
+ if (signal.aborted) {
192
+ done();
193
+ return;
194
+ }
195
+ signal.addEventListener('abort', done);
196
+ });
197
+ }
@@ -3,8 +3,8 @@ import { User } from '@genesislcap/foundation-user';
3
3
  import { GENESIS_SOCKET_URL, JSONSerializer, UUID } from '@genesislcap/foundation-utils';
4
4
  import { DOM, observable } from '@microsoft/fast-element';
5
5
  import { DI } from '@microsoft/fast-foundation';
6
- import { Observable, of, Subject, Subscription, throwError } from 'rxjs';
7
- import { filter, mergeMap, switchMap, takeWhile } from 'rxjs/operators';
6
+ import { from, Observable, of, Subject, Subscription, throwError } from 'rxjs';
7
+ import { exhaustMap, filter, map, switchMap, takeWhile } from 'rxjs/operators';
8
8
  import { WebSocketSubject } from 'rxjs/webSocket';
9
9
  import { Session } from '../session';
10
10
  import { logger } from '../utils';
@@ -13,7 +13,7 @@ import { ConnectConfig } from './connect.types';
13
13
  import { Http } from './http';
14
14
  import { EventMessageType, MessageBuilder, MessageType, } from './message';
15
15
  import { exponentialScheduler, linearScheduler, MAX_RECONNECT_ATTEMPTS, retryInterval, SocketReconnectStrategy, } from './reconnectStrategy';
16
- import { onOtherTabReauthComplete, SessionRefreshResult, tryRefreshSession, } from './sessionRefresh';
16
+ import { onOtherTabReauthComplete, SessionRefreshResult, tryRefreshSession, waitForOtherTabReauth, } from './sessionRefresh';
17
17
  import { SocketStatus } from './socket.status';
18
18
  import { Ticker } from './ticker';
19
19
  /**
@@ -81,6 +81,9 @@ export class SocketMessageHandler {
81
81
  return this._isSubscription;
82
82
  }
83
83
  }
84
+ const whenAborted = (signal) => new Promise((resolve) => {
85
+ signal.addEventListener('abort', () => resolve(undefined), { once: true });
86
+ });
84
87
  /**
85
88
  * Default Socket implementation.
86
89
  * @public
@@ -131,6 +134,7 @@ let DefaultSocket = class DefaultSocket {
131
134
  this.config = config;
132
135
  this.defaultInterval = 10000;
133
136
  this.secondsMultiplier = 1000;
137
+ this.sessionCheckTimeout = 10000;
134
138
  this.heartbeatIsEnabled = true;
135
139
  this.heartbeatInterval = this.defaultInterval;
136
140
  this.socketMessages = () => this.wsMessages;
@@ -268,20 +272,23 @@ let DefaultSocket = class DefaultSocket {
268
272
  */
269
273
  handleExpiredSession() {
270
274
  return __awaiter(this, void 0, void 0, function* () {
271
- // to detect which auth method is used we check if refreshToken is present in session storage
272
- // it would not be available in cookies method as it's securely stored within cookie
273
- // and not accessible from the client
274
- if (this.session.getSessionStorageItem('refreshToken')) {
275
+ if (this.usesCookieAuth) {
276
+ yield this.handleCookieBasedReauth();
277
+ }
278
+ else {
275
279
  const refreshTokenMessage = this.messageBuilder.createRefreshTokenMessage();
276
280
  const refreshTokenResult = yield this.send(refreshTokenMessage);
277
281
  this.session.setAuthResult(refreshTokenResult);
278
282
  this.updateSessionAndSubscriptions(refreshTokenResult);
279
283
  }
280
- else {
281
- yield this.handleCookieBasedReauth();
282
- }
283
284
  });
284
285
  }
286
+ // to detect which auth method is used we check if refreshToken is present in session storage
287
+ // it would not be available in cookies method as it's securely stored within cookie
288
+ // and not accessible from the client
289
+ get usesCookieAuth() {
290
+ return !this.session.getSessionStorageItem('refreshToken');
291
+ }
285
292
  handleCookieBasedReauth() {
286
293
  return __awaiter(this, void 0, void 0, function* () {
287
294
  const result = yield tryRefreshSession();
@@ -368,21 +375,18 @@ let DefaultSocket = class DefaultSocket {
368
375
  ? exponentialScheduler
369
376
  : linearScheduler;
370
377
  const reconnectObservable = this.isConnectedSubject.asObservable().pipe(switchMap((isConnected) => !isConnected
371
- ? retryInterval(this.reconnectOptions, scheduler).pipe(mergeMap((value) => {
378
+ ? retryInterval(this.reconnectOptions, scheduler).pipe(exhaustMap((tick, attempt) => {
372
379
  var _a, _b, _c;
373
- let attemptsAmount;
374
- if ((_a = this.connectOptions) === null || _a === void 0 ? void 0 : _a.alwaysOn) {
375
- attemptsAmount = value + 1;
376
- }
377
- else {
378
- attemptsAmount =
379
- (_c = (_b = this.reconnectOptions) === null || _b === void 0 ? void 0 : _b.reconnectAttempts) !== null && _c !== void 0 ? _c : MAX_RECONNECT_ATTEMPTS;
380
+ const attemptsAmount = ((_a = this.connectOptions) === null || _a === void 0 ? void 0 : _a.alwaysOn)
381
+ ? attempt + 1
382
+ : ((_c = (_b = this.reconnectOptions) === null || _b === void 0 ? void 0 : _b.reconnectAttempts) !== null && _c !== void 0 ? _c : MAX_RECONNECT_ATTEMPTS);
383
+ if (attempt >= attemptsAmount) {
384
+ this.status.reconnectionLimitReached = true;
385
+ return throwError(() => new Error(`Max reconnect attempts ${attemptsAmount} reached.`));
380
386
  }
381
- if (value < attemptsAmount) {
382
- return of(value);
383
- }
384
- this.status.reconnectionLimitReached = true;
385
- return throwError(() => new Error(`Max reconnect attempts ${attemptsAmount} reached.`));
387
+ return tick > 0 && this.user.isAuthenticated && this.usesCookieAuth
388
+ ? from(this.refreshSessionBeforeReconnect()).pipe(map(() => attempt))
389
+ : of(attempt);
386
390
  }))
387
391
  : of(-1)), takeWhile(() => this.websocket && !this.isConnected));
388
392
  reconnectObservable.subscribe((_e = (_d = this.reconnectOptions) === null || _d === void 0 ? void 0 : _d.reconnectObserver) !== null && _e !== void 0 ? _e : {
@@ -408,6 +412,31 @@ let DefaultSocket = class DefaultSocket {
408
412
  },
409
413
  });
410
414
  }
415
+ // The router rejects a handshake carrying a dead session cookie with a 401, which the browser
416
+ // reports as a plain 1006 close, so the session can only be checked over HTTP.
417
+ refreshSessionBeforeReconnect() {
418
+ return __awaiter(this, void 0, void 0, function* () {
419
+ const signal = AbortSignal.timeout(this.sessionCheckTimeout);
420
+ // Stops waiting at the timeout without aborting a refresh in flight, so its new cookie still lands.
421
+ const result = yield Promise.race([
422
+ tryRefreshSession({ reloadOnFailure: false, signal }),
423
+ whenAborted(signal),
424
+ ]).catch((error) => {
425
+ logger.debug('Could not check the session before reconnecting: ', error);
426
+ return undefined;
427
+ });
428
+ if (result === SessionRefreshResult.FAILED) {
429
+ this.reloadPage();
430
+ throw new Error('Session expired and could not be refreshed.');
431
+ }
432
+ if (result === SessionRefreshResult.HANDLED_BY_OTHER_TAB) {
433
+ yield waitForOtherTabReauth(signal);
434
+ }
435
+ });
436
+ }
437
+ reloadPage() {
438
+ window.location.reload();
439
+ }
411
440
  reset() {
412
441
  this.status.isConnected = false;
413
442
  this.status.isConfigured = false;
@@ -37725,7 +37725,7 @@
37725
37725
  {
37726
37726
  "kind": "Function",
37727
37727
  "canonicalReference": "@genesislcap/foundation-comms!tryRefreshSession:function(1)",
37728
- "docComment": "/**\n * Attempts to refresh the session when authentication has expired. Uses a localStorage-based lock mechanism to prevent multiple tabs from trying to reauthenticate simultaneously.\n *\n * @param options - Optional configuration\n *\n * @param - options.reloadOnFailure - Whether to reload the page if refresh fails (default: true)\n *\n * @returns The result of the refresh attempt\n *\n * @public\n */\n",
37728
+ "docComment": "/**\n * Attempts to refresh the session when authentication has expired. Uses a localStorage-based lock mechanism to prevent multiple tabs from trying to reauthenticate simultaneously.\n *\n * @param options - `reloadOnFailure` reloads the page if the refresh fails (default: true). `signal` aborts the session check; a refresh that has started is never aborted, because the server revokes the old refresh token as soon as it issues a new one, so the new cookie must be allowed to land.\n *\n * @returns The result of the refresh attempt\n *\n * @throws\n *\n * If the session check or refresh could not complete (connection error, timeout, aborted check, 408, 429, 5xx, etc.)\n *\n * @public\n */\n",
37729
37729
  "excerptTokens": [
37730
37730
  {
37731
37731
  "kind": "Content",
@@ -37733,7 +37733,16 @@
37733
37733
  },
37734
37734
  {
37735
37735
  "kind": "Content",
37736
- "text": "{\n reloadOnFailure?: boolean;\n}"
37736
+ "text": "{\n reloadOnFailure?: boolean;\n signal?: "
37737
+ },
37738
+ {
37739
+ "kind": "Reference",
37740
+ "text": "AbortSignal",
37741
+ "canonicalReference": "!AbortSignal:interface"
37742
+ },
37743
+ {
37744
+ "kind": "Content",
37745
+ "text": ";\n}"
37737
37746
  },
37738
37747
  {
37739
37748
  "kind": "Content",
@@ -37764,8 +37773,8 @@
37764
37773
  ],
37765
37774
  "fileUrlPath": "src/connect/sessionRefresh.ts",
37766
37775
  "returnTypeTokenRange": {
37767
- "startIndex": 3,
37768
- "endIndex": 7
37776
+ "startIndex": 5,
37777
+ "endIndex": 9
37769
37778
  },
37770
37779
  "releaseTag": "Public",
37771
37780
  "overloadIndex": 1,
@@ -37774,7 +37783,7 @@
37774
37783
  "parameterName": "options",
37775
37784
  "parameterTypeTokenRange": {
37776
37785
  "startIndex": 1,
37777
- "endIndex": 2
37786
+ "endIndex": 4
37778
37787
  },
37779
37788
  "isOptional": true
37780
37789
  }
@@ -37990,6 +37999,57 @@
37990
37999
  "endIndex": 2
37991
38000
  }
37992
38001
  ]
38002
+ },
38003
+ {
38004
+ "kind": "Function",
38005
+ "canonicalReference": "@genesislcap/foundation-comms!waitForOtherTabReauth:function(1)",
38006
+ "docComment": "/**\n * Waits until another tab finishes reauthenticating, or until `signal` aborts.\n *\n * @remarks\n *\n * Relies on `storage` events, which don't fire in the tab that changed the key, so when this tab holds the reauth lock itself only `signal` ends the wait.\n *\n * @param signal - Ends the wait when aborted\n *\n * @public\n */\n",
38007
+ "excerptTokens": [
38008
+ {
38009
+ "kind": "Content",
38010
+ "text": "export declare function waitForOtherTabReauth(signal: "
38011
+ },
38012
+ {
38013
+ "kind": "Reference",
38014
+ "text": "AbortSignal",
38015
+ "canonicalReference": "!AbortSignal:interface"
38016
+ },
38017
+ {
38018
+ "kind": "Content",
38019
+ "text": "): "
38020
+ },
38021
+ {
38022
+ "kind": "Reference",
38023
+ "text": "Promise",
38024
+ "canonicalReference": "!Promise:interface"
38025
+ },
38026
+ {
38027
+ "kind": "Content",
38028
+ "text": "<void>"
38029
+ },
38030
+ {
38031
+ "kind": "Content",
38032
+ "text": ";"
38033
+ }
38034
+ ],
38035
+ "fileUrlPath": "src/connect/sessionRefresh.ts",
38036
+ "returnTypeTokenRange": {
38037
+ "startIndex": 3,
38038
+ "endIndex": 5
38039
+ },
38040
+ "releaseTag": "Public",
38041
+ "overloadIndex": 1,
38042
+ "parameters": [
38043
+ {
38044
+ "parameterName": "signal",
38045
+ "parameterTypeTokenRange": {
38046
+ "startIndex": 1,
38047
+ "endIndex": 2
38048
+ },
38049
+ "isOptional": false
38050
+ }
38051
+ ],
38052
+ "name": "waitForOtherTabReauth"
37993
38053
  }
37994
38054
  ]
37995
38055
  }
@@ -2668,6 +2668,7 @@ export declare class DefaultSocket implements Socket {
2668
2668
  protected config: ConnectConfig;
2669
2669
  private readonly defaultInterval;
2670
2670
  private readonly secondsMultiplier;
2671
+ private readonly sessionCheckTimeout;
2671
2672
  private websocket;
2672
2673
  private wsMessages;
2673
2674
  private wsMessageHandlers;
@@ -2707,6 +2708,7 @@ export declare class DefaultSocket implements Socket {
2707
2708
  * more info here https://docs.genesis.global/docs/develop/server-capabilities/access-control/authentication/#sessiontimeoutmins
2708
2709
  */
2709
2710
  private handleExpiredSession;
2711
+ private get usesCookieAuth();
2710
2712
  private handleCookieBasedReauth;
2711
2713
  private updateSessionAndSubscriptions;
2712
2714
  /**
@@ -2717,6 +2719,8 @@ export declare class DefaultSocket implements Socket {
2717
2719
  private applyServerHeartbeatInterval;
2718
2720
  private prepareHeartbeat;
2719
2721
  private reconnect;
2722
+ private refreshSessionBeforeReconnect;
2723
+ private reloadPage;
2720
2724
  reset(): void;
2721
2725
  private cleanMessages;
2722
2726
  send<T>(message: Message<T | any>, needsHandling?: boolean): Promise<Message | any>;
@@ -5339,12 +5343,16 @@ export declare const toFieldMetadata: (fieldDef: MetadataDetail[]) => FieldMetad
5339
5343
  * trying to reauthenticate simultaneously.
5340
5344
  *
5341
5345
  * @public
5342
- * @param options - Optional configuration
5343
- * @param options.reloadOnFailure - Whether to reload the page if refresh fails (default: true)
5346
+ * @param options - `reloadOnFailure` reloads the page if the refresh fails (default: true). `signal` aborts the session
5347
+ * check; a refresh that has started is never aborted, because the server revokes the old refresh token as soon as it
5348
+ * issues a new one, so the new cookie must be allowed to land.
5344
5349
  * @returns The result of the refresh attempt
5350
+ * @throws If the session check or refresh could not complete (connection error, timeout, aborted check, 408, 429, 5xx,
5351
+ * etc.)
5345
5352
  */
5346
5353
  export declare function tryRefreshSession(options?: {
5347
5354
  reloadOnFailure?: boolean;
5355
+ signal?: AbortSignal;
5348
5356
  }): Promise<SessionRefreshResult>;
5349
5357
 
5350
5358
  /**
@@ -5422,6 +5430,18 @@ export declare type UserPermission = CoreUserPermissions | UnknownUserPermission
5422
5430
  */
5423
5431
  export declare type UserProfile = CoreUserProfiles | UnknownUserProfiles;
5424
5432
 
5433
+ /**
5434
+ * Waits until another tab finishes reauthenticating, or until `signal` aborts.
5435
+ *
5436
+ * @remarks
5437
+ * Relies on `storage` events, which don't fire in the tab that changed the key, so when this tab holds the reauth lock
5438
+ * itself only `signal` ends the wait.
5439
+ *
5440
+ * @public
5441
+ * @param signal - Ends the wait when aborted
5442
+ */
5443
+ export declare function waitForOtherTabReauth(signal: AbortSignal): Promise<void>;
5444
+
5425
5445
  /**
5426
5446
  * The DI token for the Connect interface (WS-only).
5427
5447
  * @internal
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@genesislcap/foundation-comms",
3
3
  "description": "Genesis Foundation UI Comms",
4
- "version": "15.68.0",
4
+ "version": "15.69.0",
5
5
  "sideEffects": false,
6
6
  "license": "SEE LICENSE IN license.txt",
7
7
  "main": "dist/esm/index.js",
@@ -74,23 +74,23 @@
74
74
  }
75
75
  },
76
76
  "devDependencies": {
77
- "@genesislcap/foundation-testing": "15.68.0",
78
- "@genesislcap/genx": "15.68.0",
79
- "@genesislcap/ts-builder": "15.68.0",
80
- "@genesislcap/uvu-playwright-builder": "15.68.0",
81
- "@genesislcap/vite-builder": "15.68.0",
82
- "@genesislcap/webpack-builder": "15.68.0",
77
+ "@genesislcap/foundation-testing": "15.69.0",
78
+ "@genesislcap/genx": "15.69.0",
79
+ "@genesislcap/ts-builder": "15.69.0",
80
+ "@genesislcap/uvu-playwright-builder": "15.69.0",
81
+ "@genesislcap/vite-builder": "15.69.0",
82
+ "@genesislcap/webpack-builder": "15.69.0",
83
83
  "@types/js-cookie": "^3.0.2",
84
84
  "@types/json-schema": "^7.0.11",
85
85
  "@types/webappsec-credential-management": "^0.6.2",
86
86
  "sinon": "^17.0.1"
87
87
  },
88
88
  "dependencies": {
89
- "@genesislcap/foundation-broadcast-channel": "15.68.0",
90
- "@genesislcap/foundation-logger": "15.68.0",
91
- "@genesislcap/foundation-user": "15.68.0",
92
- "@genesislcap/foundation-utils": "15.68.0",
93
- "@genesislcap/web-core": "15.68.0",
89
+ "@genesislcap/foundation-broadcast-channel": "15.69.0",
90
+ "@genesislcap/foundation-logger": "15.69.0",
91
+ "@genesislcap/foundation-user": "15.69.0",
92
+ "@genesislcap/foundation-utils": "15.69.0",
93
+ "@genesislcap/web-core": "15.69.0",
94
94
  "@microsoft/fast-element": "1.14.0",
95
95
  "@microsoft/fast-foundation": "2.50.0",
96
96
  "bowser": "^2.11.0",