Skip to content

Commit

Permalink
refactor(client): add error handler to the default websocket-client
Browse files Browse the repository at this point in the history
  • Loading branch information
TimoBechtel committed Jun 2, 2023
1 parent 03f8fdb commit 234aa59
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 10 deletions.
38 changes: 28 additions & 10 deletions packages/client/src/lib/socket-implementation/websocketClient.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,15 @@
import { createEventBroker, type SocketClient } from '@socketdb/core';

type Unsubscriber = () => void;
// This is needed until the SocketClient type is updated. It is not yet as this is a breaking change.
interface DefaultWebsocketClient extends SocketClient {
onConnect: (...args: Parameters<SocketClient['onConnect']>) => Unsubscriber;
onDisconnect: (
...args: Parameters<SocketClient['onDisconnect']>
) => Unsubscriber;
onError: (callback: (error: unknown) => void) => Unsubscriber;
}

export const createWebsocketClient = ({
url,
protocols,
Expand All @@ -8,7 +18,7 @@ export const createWebsocketClient = ({
url: string;
protocols?: string[];
reconnectTimeout?: number;
}): SocketClient => {
}): DefaultWebsocketClient => {
if (typeof WebSocket === 'undefined') {
console.error(
'Error: You tried to use the default WebsocketClient in a non-browser environment.',
Expand All @@ -20,8 +30,12 @@ export const createWebsocketClient = ({
}

const messageEvents = createEventBroker();
const connectionClosedListener: (() => void)[] = [];
const connectionOpenedListener: (() => void)[] = [];
const socketEvents = createEventBroker<{
'connection-closed': void;
'connection-opened': void;
'connection-error': unknown;
}>();

let manuallyClosed = false;

let socket: Promise<WebSocket>;
Expand All @@ -47,21 +61,22 @@ export const createWebsocketClient = ({
}

function onOpen() {
connectionOpenedListener.forEach((callback) => callback());
socketEvents.notify('connection-opened', undefined);
}

function onMessage({ data: packet }: MessageEvent) {
const { event, data } = JSON.parse(packet);
messageEvents.notify(event, data);
}

async function onError(error: Event) {
console.error(error);
async function onError(event: Event) {
console.error('Socket error:', event);
socketEvents.notify('connection-error', event);
(await socket).close();
}

function onClose() {
connectionClosedListener.forEach((callback) => callback());
socketEvents.notify('connection-closed', undefined);
if (!manuallyClosed)
setTimeout(() => {
connect();
Expand All @@ -77,14 +92,17 @@ export const createWebsocketClient = ({

return {
onConnect(callback) {
connectionOpenedListener.push(callback);
return socketEvents.addListener('connection-opened', callback);
},
onDisconnect(callback) {
connectionClosedListener.push(callback);
return socketEvents.addListener('connection-closed', callback);
},
onError(callback) {
return socketEvents.addListener('connection-error', callback);
},
on: messageEvents.addListener,
off: messageEvents.removeListener,
send(event: string, data: any) {
send(event, data) {
sendMessage(JSON.stringify({ event, data }));
},
close() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { createIncrementalIdGenerator } from './incrementalIdGenerator';
*/
type CustomizableWSOptions = Omit<ws.ServerOptions, 'noServer' | 'port'>;

// This is needed until the SocketServer type is updated. It is not yet as this is a breaking change.
interface DefaultWebsocketServer extends SocketServer {
onConnection: (
...args: Parameters<SocketServer['onConnection']>
Expand Down

1 comment on commit 234aa59

@vercel
Copy link

@vercel vercel bot commented on 234aa59 Jun 2, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please sign in to comment.