mirror of
https://github.com/cpvalente/ontime.git
synced 2026-08-09 09:23:51 +00:00
157 lines
4.1 KiB
TypeScript
157 lines
4.1 KiB
TypeScript
import { Log, RuntimeStore } from 'ontime-types';
|
|
|
|
import { isProduction, RUNTIME, websocketUrl } from '../api/constants';
|
|
import { ontimeQueryClient } from '../queryClient';
|
|
import { socketClientName } from '../stores/connectionName';
|
|
import { addLog } from '../stores/logger';
|
|
import { patchRuntime, runtimeStore } from '../stores/runtime';
|
|
|
|
export let websocket: WebSocket | null = null;
|
|
let reconnectTimeout: NodeJS.Timeout | null = null;
|
|
const reconnectInterval = 1000;
|
|
export let shouldReconnect = true;
|
|
export let hasConnected = false;
|
|
export let reconnectAttempts = 0;
|
|
|
|
export const connectSocket = (preferredClientName?: string) => {
|
|
websocket = new WebSocket(websocketUrl);
|
|
|
|
websocket.onopen = () => {
|
|
clearTimeout(reconnectTimeout as NodeJS.Timeout);
|
|
hasConnected = true;
|
|
reconnectAttempts = 0;
|
|
|
|
if (preferredClientName) {
|
|
socketSendJson('set-client-name', preferredClientName);
|
|
}
|
|
};
|
|
|
|
websocket.onclose = () => {
|
|
console.warn('WebSocket disconnected');
|
|
if (shouldReconnect) {
|
|
reconnectTimeout = setTimeout(() => {
|
|
console.warn('WebSocket: attempting reconnect');
|
|
if (websocket && websocket.readyState === WebSocket.CLOSED) {
|
|
reconnectAttempts += 1;
|
|
connectSocket();
|
|
}
|
|
}, reconnectInterval);
|
|
}
|
|
};
|
|
|
|
websocket.onerror = (error) => {
|
|
console.error('WebSocket error:', error);
|
|
};
|
|
|
|
websocket.onmessage = (event) => {
|
|
try {
|
|
const data = JSON.parse(event.data);
|
|
|
|
const { type, payload } = data;
|
|
|
|
if (!type) {
|
|
return;
|
|
}
|
|
|
|
switch (type) {
|
|
case 'client-name': {
|
|
socketClientName.getState().setName(payload);
|
|
break;
|
|
}
|
|
case 'ontime-log': {
|
|
addLog(payload as Log);
|
|
break;
|
|
}
|
|
case 'ontime': {
|
|
runtimeStore.setState(payload as RuntimeStore);
|
|
if (!isProduction) {
|
|
ontimeQueryClient.setQueryData(RUNTIME, data.payload);
|
|
}
|
|
break;
|
|
}
|
|
case 'ontime-clock': {
|
|
patchRuntime('clock', payload);
|
|
updateDevTools({ clock: payload });
|
|
break;
|
|
}
|
|
case 'ontime-timer': {
|
|
patchRuntime('timer', payload);
|
|
updateDevTools({ timer: payload });
|
|
break;
|
|
}
|
|
case 'ontime-onAir': {
|
|
patchRuntime('onAir', payload);
|
|
updateDevTools({ onAir: payload });
|
|
break;
|
|
}
|
|
case 'ontime-message': {
|
|
patchRuntime('message', payload);
|
|
updateDevTools({ message: payload });
|
|
break;
|
|
}
|
|
case 'ontime-runtime': {
|
|
patchRuntime('runtime', payload);
|
|
updateDevTools({ runtime: payload });
|
|
break;
|
|
}
|
|
case 'ontime-eventNow': {
|
|
patchRuntime('eventNow', payload);
|
|
updateDevTools({ eventNow: payload });
|
|
break;
|
|
}
|
|
case 'ontime-publicEventNow': {
|
|
patchRuntime('publicEventNow', payload);
|
|
updateDevTools({ publicEventNow: payload });
|
|
break;
|
|
}
|
|
case 'ontime-eventNext': {
|
|
patchRuntime('eventNext', payload);
|
|
updateDevTools({ eventNext: payload });
|
|
break;
|
|
}
|
|
case 'ontime-publicEventNext': {
|
|
patchRuntime('publicEventNext', payload);
|
|
updateDevTools({ publicEventNext: payload });
|
|
break;
|
|
}
|
|
case 'ontime-timer1': {
|
|
patchRuntime('timer1', payload);
|
|
updateDevTools({ timer1: payload });
|
|
break;
|
|
}
|
|
}
|
|
} catch (_) {
|
|
// ignore unhandled
|
|
}
|
|
};
|
|
};
|
|
|
|
export const disconnectSocket = () => {
|
|
shouldReconnect = false;
|
|
websocket?.close();
|
|
};
|
|
|
|
export const socketSend = (message: any) => {
|
|
if (websocket && websocket.readyState === WebSocket.OPEN) {
|
|
websocket.send(message);
|
|
}
|
|
};
|
|
|
|
export const socketSendJson = (type: string, payload?: unknown) => {
|
|
socketSend(
|
|
JSON.stringify({
|
|
type,
|
|
payload,
|
|
}),
|
|
);
|
|
};
|
|
|
|
function updateDevTools(newData: Partial<RuntimeStore>) {
|
|
if (!isProduction) {
|
|
ontimeQueryClient.setQueryData(RUNTIME, (oldData: RuntimeStore) => ({
|
|
...oldData,
|
|
...newData,
|
|
}));
|
|
}
|
|
}
|