@flighthq/socket 0.5.1-next.1295.2b6bfa3 → 0.5.1-next.1344.b88acc1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -2
- package/dist/contract.d.ts +0 -1
- package/dist/contract.d.ts.map +1 -1
- package/dist/contract.js +0 -1
- package/dist/contract.js.map +1 -1
- package/dist/socket.d.ts +1 -3
- package/dist/socket.d.ts.map +1 -1
- package/dist/socket.js +0 -41
- package/dist/socket.js.map +1 -1
- package/package.json +5 -5
- package/src/socket.test.ts +5 -157
package/README.md
CHANGED
|
@@ -13,5 +13,5 @@ Import the supported application-facing API from `@flighthq/socket`. The `@fligh
|
|
|
13
13
|
This package is part of the locked-version Flight SDK graph. Applications may instead install and import `@flighthq/sdk` when package-level tree shaking is sufficient.
|
|
14
14
|
|
|
15
15
|
- [Flight project](https://github.com/flighthq/flight)
|
|
16
|
-
- [Source for @flighthq/socket@0.5.1-next.
|
|
17
|
-
- [License](https://github.com/flighthq/flight/blob/
|
|
16
|
+
- [Source for @flighthq/socket@0.5.1-next.1344.b88acc1](https://github.com/flighthq/flight/tree/b88acc1d080c49af69bcc979eb38073d63c72ba2/packages/socket)
|
|
17
|
+
- [License](https://github.com/flighthq/flight/blob/b88acc1d080c49af69bcc979eb38073d63c72ba2/LICENSE.md)
|
package/dist/contract.d.ts
CHANGED
package/dist/contract.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"contract.d.ts","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAAA,cAAc,sBAAsB,CAAC;AACrC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,UAAU,CAAC
|
|
1
|
+
{"version":3,"file":"contract.d.ts","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAAA,cAAc,sBAAsB,CAAC;AACrC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,UAAU,CAAC"}
|
package/dist/contract.js
CHANGED
package/dist/contract.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"contract.js","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAAA,cAAc,sBAAsB,CAAC;AACrC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,UAAU,CAAC
|
|
1
|
+
{"version":3,"file":"contract.js","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAAA,cAAc,sBAAsB,CAAC;AACrC,cAAc,4BAA4B,CAAC;AAC3C,cAAc,UAAU,CAAC"}
|
package/dist/socket.d.ts
CHANGED
|
@@ -1,13 +1,11 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { HostSocketProvider, Socket, SocketGuard, SocketOptions, SocketReadyState, SocketSignals, TcpSocketConnection, TcpSocketOptions } from '@flighthq/types/contract';
|
|
2
2
|
export declare function attachSocket(socket: Socket): void;
|
|
3
3
|
export declare function closeSocket(socket: Socket, code?: number, reason?: string): void;
|
|
4
4
|
export declare function createSocket(hostSocket: Readonly<HostSocketProvider>, options: Readonly<SocketOptions>): Socket;
|
|
5
|
-
export declare function createWebSocketBackend(): HostSocketProvider & Entity;
|
|
6
5
|
export declare function detachSocket(socket: Socket): void;
|
|
7
6
|
export declare function disposeSocket(socket: Socket): void;
|
|
8
7
|
export declare function enableSocketSignals(socket: Socket): SocketSignals;
|
|
9
8
|
export declare function getSocketReadyState(socket: Readonly<Socket>): SocketReadyState;
|
|
10
|
-
export declare function initializeWebSocketBackend(out: EntityConstruction<HostSocketProvider & Entity>): void;
|
|
11
9
|
export declare function openTcpSocket(hostSocket: Readonly<HostSocketProvider>, options: Readonly<TcpSocketOptions>): TcpSocketConnection | null;
|
|
12
10
|
export declare function sendSocketMessage(socket: Readonly<Socket>, data: string | ArrayBuffer): boolean;
|
|
13
11
|
export declare function setSocketGuard(guard: SocketGuard | null): void;
|
package/dist/socket.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"socket.d.ts","sourceRoot":"","sources":["../src/socket.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EACV,
|
|
1
|
+
{"version":3,"file":"socket.d.ts","sourceRoot":"","sources":["../src/socket.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EACV,kBAAkB,EAClB,MAAM,EAGN,WAAW,EAEX,aAAa,EACb,gBAAgB,EAEhB,aAAa,EACb,mBAAmB,EACnB,gBAAgB,EACjB,MAAM,0BAA0B,CAAC;AAKlC,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAGjD;AAKD,wBAAgB,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,IAAI,CAShF;AAQD,wBAAgB,YAAY,CAAC,UAAU,EAAE,QAAQ,CAAC,kBAAkB,CAAC,EAAE,OAAO,EAAE,QAAQ,CAAC,aAAa,CAAC,GAAG,MAAM,CAkB/G;AAID,wBAAgB,YAAY,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAEjD;AAKD,wBAAgB,aAAa,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CASlD;AAMD,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,MAAM,GAAG,aAAa,CAcjE;AAGD,wBAAgB,mBAAmB,CAAC,MAAM,EAAE,QAAQ,CAAC,MAAM,CAAC,GAAG,gBAAgB,CAE9E;AAKD,wBAAgB,aAAa,CAC3B,UAAU,EAAE,QAAQ,CAAC,kBAAkB,CAAC,EACxC,OAAO,EAAE,QAAQ,CAAC,gBAAgB,CAAC,GAClC,mBAAmB,GAAG,IAAI,CAE5B;AAKD,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,QAAQ,CAAC,MAAM,CAAC,EAAE,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,OAAO,CAQ/F;AAID,wBAAgB,cAAc,CAAC,KAAK,EAAE,WAAW,GAAG,IAAI,GAAG,IAAI,CAE9D"}
|
package/dist/socket.js
CHANGED
|
@@ -48,11 +48,6 @@ export function createSocket(hostSocket, options) {
|
|
|
48
48
|
_guard?.({ operation: 'createSocket', reason: 'no-connection', socket });
|
|
49
49
|
return socket;
|
|
50
50
|
}
|
|
51
|
-
export function createWebSocketBackend() {
|
|
52
|
-
const out = allocateEntity();
|
|
53
|
-
initializeWebSocketBackend(out);
|
|
54
|
-
return finishEntity(out);
|
|
55
|
-
}
|
|
56
51
|
// Stops delivery of provider events to the socket's signals. The live connection is untouched — use
|
|
57
52
|
// closeSocket to close it. Safe to call repeatedly; resume with attachSocket.
|
|
58
53
|
export function detachSocket(socket) {
|
|
@@ -96,35 +91,6 @@ export function enableSocketSignals(socket) {
|
|
|
96
91
|
export function getSocketReadyState(socket) {
|
|
97
92
|
return socket.runtime.readyState;
|
|
98
93
|
}
|
|
99
|
-
// Builds the Web provider over the DOM WebSocket. Nothing constructs one at import time, so importing
|
|
100
|
-
// the package has no side effect; a host composes this value into its own net group. Returns a
|
|
101
|
-
// null connection when WebSocket is unavailable (non-browser host) rather than throwing; raw TCP/UDP
|
|
102
|
-
// is likewise unsupported here and only reachable through a native provider.
|
|
103
|
-
export function initializeWebSocketBackend(out) {
|
|
104
|
-
out.openSocket = (options, events) => {
|
|
105
|
-
if (typeof WebSocket === 'undefined')
|
|
106
|
-
return null;
|
|
107
|
-
const ws = options.protocols !== undefined
|
|
108
|
-
? new WebSocket(options.url, options.protocols)
|
|
109
|
-
: new WebSocket(options.url);
|
|
110
|
-
ws.binaryType = options.binaryType ?? 'arraybuffer';
|
|
111
|
-
ws.onopen = () => events.handleSocketOpen();
|
|
112
|
-
ws.onmessage = (event) => events.handleSocketMessage(toSocketMessage(event.data));
|
|
113
|
-
ws.onclose = (event) => events.handleSocketClose({ code: event.code, reason: event.reason, wasClean: event.wasClean });
|
|
114
|
-
ws.onerror = () => events.handleSocketError();
|
|
115
|
-
return {
|
|
116
|
-
sendSocketFrame(data) {
|
|
117
|
-
if (ws.readyState !== WebSocket.OPEN)
|
|
118
|
-
return false;
|
|
119
|
-
ws.send(data);
|
|
120
|
-
return true;
|
|
121
|
-
},
|
|
122
|
-
closeSocketConnection(code, reason) {
|
|
123
|
-
ws.close(code, reason);
|
|
124
|
-
},
|
|
125
|
-
};
|
|
126
|
-
};
|
|
127
|
-
}
|
|
128
94
|
// Opens a raw TCP byte stream through the socket provider selected by the caller's host. Browser and
|
|
129
95
|
// other framed-only providers omit openTcpSocket, so unsupported raw TCP returns null without trying
|
|
130
96
|
// openSocket or interpreting the endpoint as a WebSocket URL.
|
|
@@ -183,11 +149,4 @@ function makeSocketEventSink(runtime) {
|
|
|
183
149
|
},
|
|
184
150
|
};
|
|
185
151
|
}
|
|
186
|
-
// Maps a raw WebSocket message payload onto a SocketMessage. A string is a text frame; anything else
|
|
187
|
-
// (with binaryType 'arraybuffer', an ArrayBuffer) is a binary frame.
|
|
188
|
-
function toSocketMessage(data) {
|
|
189
|
-
if (typeof data === 'string')
|
|
190
|
-
return { data, binary: false };
|
|
191
|
-
return { data: data, binary: true };
|
|
192
|
-
}
|
|
193
152
|
//# sourceMappingURL=socket.js.map
|
package/dist/socket.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"socket.js","sourceRoot":"","sources":["../src/socket.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,YAAY,EAAE,MAAM,2BAA2B,CAAC;AACzE,OAAO,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,4BAA4B,CAAC;
|
|
1
|
+
{"version":3,"file":"socket.js","sourceRoot":"","sources":["../src/socket.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@flighthq/socket",
|
|
3
|
-
"version": "0.5.1-next.
|
|
3
|
+
"version": "0.5.1-next.1344.b88acc1",
|
|
4
4
|
"author": "Joshua Granick and other contributors",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|
|
@@ -38,10 +38,10 @@
|
|
|
38
38
|
"clean:dist": "tsx ../../scripts/clean-package-dist.ts"
|
|
39
39
|
},
|
|
40
40
|
"dependencies": {
|
|
41
|
-
"@flighthq/entity": "0.5.1-next.
|
|
42
|
-
"@flighthq/log": "0.5.1-next.
|
|
43
|
-
"@flighthq/signals": "0.5.1-next.
|
|
44
|
-
"@flighthq/types": "0.5.1-next.
|
|
41
|
+
"@flighthq/entity": "0.5.1-next.1344.b88acc1",
|
|
42
|
+
"@flighthq/log": "0.5.1-next.1344.b88acc1",
|
|
43
|
+
"@flighthq/signals": "0.5.1-next.1344.b88acc1",
|
|
44
|
+
"@flighthq/types": "0.5.1-next.1344.b88acc1"
|
|
45
45
|
},
|
|
46
46
|
"devDependencies": {
|
|
47
47
|
"typescript": "^5.3.0"
|
package/src/socket.test.ts
CHANGED
|
@@ -14,12 +14,10 @@ import {
|
|
|
14
14
|
attachSocket,
|
|
15
15
|
closeSocket,
|
|
16
16
|
createSocket,
|
|
17
|
-
createWebSocketBackend,
|
|
18
17
|
detachSocket,
|
|
19
18
|
disposeSocket,
|
|
20
19
|
enableSocketSignals,
|
|
21
20
|
getSocketReadyState,
|
|
22
|
-
initializeWebSocketBackend,
|
|
23
21
|
sendSocketMessage,
|
|
24
22
|
setSocketGuard,
|
|
25
23
|
} from './socket';
|
|
@@ -221,97 +219,6 @@ describe('createSocket', () => {
|
|
|
221
219
|
});
|
|
222
220
|
});
|
|
223
221
|
|
|
224
|
-
describe('createWebSocketBackend', () => {
|
|
225
|
-
it('constructs a WebSocket with url and protocols and sets binaryType', () => {
|
|
226
|
-
const restore = installFakeWebSocket();
|
|
227
|
-
try {
|
|
228
|
-
createWebSocketBackend().openSocket(
|
|
229
|
-
{ url: 'ws://host', protocols: ['chat'], binaryType: 'arraybuffer' },
|
|
230
|
-
noopSink(),
|
|
231
|
-
);
|
|
232
|
-
const ws = FakeWebSocket.last!;
|
|
233
|
-
expect(ws.url).toBe('ws://host');
|
|
234
|
-
expect(ws.protocols).toEqual(['chat']);
|
|
235
|
-
expect(ws.binaryType).toBe('arraybuffer');
|
|
236
|
-
} finally {
|
|
237
|
-
restore();
|
|
238
|
-
}
|
|
239
|
-
});
|
|
240
|
-
|
|
241
|
-
it('translates an incoming string message to binary false', () => {
|
|
242
|
-
const restore = installFakeWebSocket();
|
|
243
|
-
try {
|
|
244
|
-
const received: SocketMessage[] = [];
|
|
245
|
-
createWebSocketBackend().openSocket({ url: 'ws://x' }, sinkCollecting(received));
|
|
246
|
-
FakeWebSocket.last!.onmessage!({ data: 'hello' } as MessageEvent);
|
|
247
|
-
expect(received).toEqual([{ data: 'hello', binary: false }]);
|
|
248
|
-
} finally {
|
|
249
|
-
restore();
|
|
250
|
-
}
|
|
251
|
-
});
|
|
252
|
-
|
|
253
|
-
it('translates an incoming ArrayBuffer message to binary true', () => {
|
|
254
|
-
const restore = installFakeWebSocket();
|
|
255
|
-
try {
|
|
256
|
-
const received: SocketMessage[] = [];
|
|
257
|
-
createWebSocketBackend().openSocket({ url: 'ws://x' }, sinkCollecting(received));
|
|
258
|
-
const buffer = new Uint8Array([9]).buffer;
|
|
259
|
-
FakeWebSocket.last!.onmessage!({ data: buffer } as MessageEvent);
|
|
260
|
-
expect(received[0]).toEqual({ data: buffer, binary: true });
|
|
261
|
-
} finally {
|
|
262
|
-
restore();
|
|
263
|
-
}
|
|
264
|
-
});
|
|
265
|
-
|
|
266
|
-
it('maps close events and open into the sink', () => {
|
|
267
|
-
const restore = installFakeWebSocket();
|
|
268
|
-
try {
|
|
269
|
-
let opened = false;
|
|
270
|
-
const closes: SocketCloseInfo[] = [];
|
|
271
|
-
const sink: SocketEventSink = {
|
|
272
|
-
...noopSink(),
|
|
273
|
-
handleSocketOpen: () => (opened = true),
|
|
274
|
-
handleSocketClose: (i) => closes.push(i),
|
|
275
|
-
};
|
|
276
|
-
createWebSocketBackend().openSocket({ url: 'ws://x' }, sink);
|
|
277
|
-
const ws = FakeWebSocket.last!;
|
|
278
|
-
ws.onopen!(new Event('open'));
|
|
279
|
-
ws.onclose!({ code: 1000, reason: 'done', wasClean: true } as CloseEvent);
|
|
280
|
-
expect(opened).toBe(true);
|
|
281
|
-
expect(closes).toEqual([{ code: 1000, reason: 'done', wasClean: true }]);
|
|
282
|
-
} finally {
|
|
283
|
-
restore();
|
|
284
|
-
}
|
|
285
|
-
});
|
|
286
|
-
|
|
287
|
-
it('sends only when the WebSocket is OPEN and closes with code/reason', () => {
|
|
288
|
-
const restore = installFakeWebSocket();
|
|
289
|
-
try {
|
|
290
|
-
const connection = createWebSocketBackend().openSocket({ url: 'ws://x' }, noopSink())!;
|
|
291
|
-
const ws = FakeWebSocket.last!;
|
|
292
|
-
ws.readyState = FakeWebSocket.CONNECTING;
|
|
293
|
-
expect(connection.sendSocketFrame('x')).toBe(false);
|
|
294
|
-
ws.readyState = FakeWebSocket.OPEN;
|
|
295
|
-
expect(connection.sendSocketFrame('y')).toBe(true);
|
|
296
|
-
expect(ws.sent).toEqual(['y']);
|
|
297
|
-
connection.closeSocketConnection(1001, 'later');
|
|
298
|
-
expect(ws.closed).toEqual({ code: 1001, reason: 'later' });
|
|
299
|
-
} finally {
|
|
300
|
-
restore();
|
|
301
|
-
}
|
|
302
|
-
});
|
|
303
|
-
|
|
304
|
-
it('returns a null connection when WebSocket is unavailable', () => {
|
|
305
|
-
const original = (globalThis as { WebSocket?: unknown }).WebSocket;
|
|
306
|
-
(globalThis as { WebSocket?: unknown }).WebSocket = undefined;
|
|
307
|
-
try {
|
|
308
|
-
expect(createWebSocketBackend().openSocket({ url: 'ws://x' }, noopSink())).toBeNull();
|
|
309
|
-
} finally {
|
|
310
|
-
(globalThis as { WebSocket?: unknown }).WebSocket = original;
|
|
311
|
-
}
|
|
312
|
-
});
|
|
313
|
-
});
|
|
314
|
-
|
|
315
222
|
describe('detachSocket', () => {
|
|
316
223
|
it('stops backend events from reaching the signals', () => {
|
|
317
224
|
const fake = fakeBackend();
|
|
@@ -393,12 +300,6 @@ describe('getSocketReadyState', () => {
|
|
|
393
300
|
});
|
|
394
301
|
});
|
|
395
302
|
|
|
396
|
-
describe('initializeWebSocketBackend', () => {
|
|
397
|
-
it('is the construction initializer of createWebSocketBackend', () => {
|
|
398
|
-
expect(typeof initializeWebSocketBackend).toBe('function');
|
|
399
|
-
});
|
|
400
|
-
});
|
|
401
|
-
|
|
402
303
|
describe('openTcpSocket', () => {
|
|
403
304
|
it('forwards the endpoint unchanged and returns the backend connection by identity', () => {
|
|
404
305
|
const expected = tcpConnection();
|
|
@@ -418,8 +319,11 @@ describe('openTcpSocket', () => {
|
|
|
418
319
|
expect(openTcpSocket(host.net.socket, { host: 'localhost', port: 9000 })).toBeNull();
|
|
419
320
|
});
|
|
420
321
|
|
|
421
|
-
|
|
422
|
-
|
|
322
|
+
// A framed-only provider — the shape every browser transport takes — omits openTcpSocket entirely.
|
|
323
|
+
// Raw TCP must then report absence rather than falling through to openSocket and reinterpreting the
|
|
324
|
+
// endpoint as a WebSocket URL.
|
|
325
|
+
it('returns null for a framed-only backend without attempting framed openSocket', () => {
|
|
326
|
+
const backend: HostSocketProvider = { openSocket: vi.fn(() => null) };
|
|
423
327
|
const openSocket = vi.spyOn(backend, 'openSocket');
|
|
424
328
|
|
|
425
329
|
expect(openTcpSocket(hostOf(backend).net.socket, { host: 'localhost', port: 9000 })).toBeNull();
|
|
@@ -488,62 +392,6 @@ describe('sendSocketMessage', () => {
|
|
|
488
392
|
});
|
|
489
393
|
});
|
|
490
394
|
|
|
491
|
-
function noopSink(): SocketEventSink {
|
|
492
|
-
return {
|
|
493
|
-
handleSocketOpen() {},
|
|
494
|
-
handleSocketMessage() {},
|
|
495
|
-
handleSocketClose() {},
|
|
496
|
-
handleSocketError() {},
|
|
497
|
-
};
|
|
498
|
-
}
|
|
499
|
-
|
|
500
|
-
function sinkCollecting(received: SocketMessage[]): SocketEventSink {
|
|
501
|
-
return { ...noopSink(), handleSocketMessage: (m) => received.push(m) };
|
|
502
|
-
}
|
|
503
|
-
|
|
504
|
-
// A minimal stand-in for the DOM WebSocket, recording constructor args, sends, and close, and
|
|
505
|
-
// exposing dispatchable onopen/onmessage/onclose/onerror handlers.
|
|
506
|
-
class FakeWebSocket {
|
|
507
|
-
static CONNECTING = 0;
|
|
508
|
-
static OPEN = 1;
|
|
509
|
-
static CLOSING = 2;
|
|
510
|
-
static CLOSED = 3;
|
|
511
|
-
static last: FakeWebSocket | null = null;
|
|
512
|
-
|
|
513
|
-
url: string;
|
|
514
|
-
protocols?: readonly string[];
|
|
515
|
-
binaryType = 'blob';
|
|
516
|
-
readyState = FakeWebSocket.CONNECTING;
|
|
517
|
-
sent: (string | ArrayBuffer)[] = [];
|
|
518
|
-
closed: { code?: number; reason?: string } | null = null;
|
|
519
|
-
onopen: ((event: Event) => void) | null = null;
|
|
520
|
-
onmessage: ((event: MessageEvent) => void) | null = null;
|
|
521
|
-
onclose: ((event: CloseEvent) => void) | null = null;
|
|
522
|
-
onerror: ((event: Event) => void) | null = null;
|
|
523
|
-
|
|
524
|
-
constructor(url: string, protocols?: string | string[]) {
|
|
525
|
-
this.url = url;
|
|
526
|
-
if (protocols !== undefined) this.protocols = typeof protocols === 'string' ? [protocols] : protocols;
|
|
527
|
-
FakeWebSocket.last = this;
|
|
528
|
-
}
|
|
529
|
-
|
|
530
|
-
send(data: string | ArrayBuffer): void {
|
|
531
|
-
this.sent.push(data);
|
|
532
|
-
}
|
|
533
|
-
|
|
534
|
-
close(code?: number, reason?: string): void {
|
|
535
|
-
this.closed = { code, reason };
|
|
536
|
-
}
|
|
537
|
-
}
|
|
538
|
-
|
|
539
|
-
function installFakeWebSocket(): () => void {
|
|
540
|
-
const original = (globalThis as { WebSocket?: unknown }).WebSocket;
|
|
541
|
-
FakeWebSocket.last = null;
|
|
542
|
-
(globalThis as { WebSocket?: unknown }).WebSocket = FakeWebSocket;
|
|
543
|
-
return () => {
|
|
544
|
-
(globalThis as { WebSocket?: unknown }).WebSocket = original;
|
|
545
|
-
};
|
|
546
|
-
}
|
|
547
395
|
describe('setSocketGuard', () => {
|
|
548
396
|
it('installs and removes the core notice hook', () => {
|
|
549
397
|
const notices: string[] = [];
|