import { pluck, distinctUntilChanged } from "rxjs/operators" import DispatchingStore, { defineDispatchers } from "./DispatchingStore" import { HoppRealtimeLog, HoppRealtimeLogLine, } from "~/helpers/types/HoppRealtimeLog" import { WSConnection } from "~/helpers/realtime/WSConnection" export type HoppWSProtocol = { value: string active: boolean } type HoppWSRequest = { endpoint: string protocols: HoppWSProtocol[] } export type HoppWSSession = { request: HoppWSRequest log: HoppRealtimeLog socket: WSConnection } const defaultWSRequest: HoppWSRequest = { endpoint: "wss://echo-websocket.hoppscotch.io", protocols: [], } const defaultWSSession: HoppWSSession = { request: defaultWSRequest, socket: new WSConnection(), log: [], } const dispatchers = defineDispatchers({ setRequest(_: HoppWSSession, { newRequest }: { newRequest: HoppWSRequest }) { return { request: newRequest, } }, setEndpoint(curr: HoppWSSession, { newEndpoint }: { newEndpoint: string }) { return { request: { protocols: curr.request.protocols, endpoint: newEndpoint, }, } }, setProtocols( curr: HoppWSSession, { protocols }: { protocols: HoppWSProtocol[] } ) { return { request: { protocols, endpoint: curr.request.endpoint, }, } }, addProtocol(curr: HoppWSSession, { protocol }: { protocol: HoppWSProtocol }) { return { request: { endpoint: curr.request.endpoint, protocols: [...curr.request.protocols, protocol], }, } }, deleteProtocol(curr: HoppWSSession, { index }: { index: number }) { return { request: { endpoint: curr.request.endpoint, protocols: curr.request.protocols.filter((_, idx) => index !== idx), }, } }, deleteAllProtocols(curr: HoppWSSession) { return { request: { endpoint: curr.request.endpoint, protocols: [], }, } }, updateProtocol( curr: HoppWSSession, { index, updatedProtocol, }: { index: number; updatedProtocol: HoppWSProtocol } ) { return { request: { endpoint: curr.request.endpoint, protocols: curr.request.protocols.map((proto, idx) => { return index === idx ? updatedProtocol : proto }), }, } }, setSocket(_: HoppWSSession, { socket }: { socket: WSConnection }) { return { socket, } }, setLog(_: HoppWSSession, { log }: { log: HoppRealtimeLog }) { return { log, } }, addLogLine(curr: HoppWSSession, { line }: { line: HoppRealtimeLogLine }) { return { log: [...curr.log, line], } }, }) const WSSessionStore = new DispatchingStore(defaultWSSession, dispatchers) export function setWSRequest(newRequest?: HoppWSRequest) { WSSessionStore.dispatch({ dispatcher: "setRequest", payload: { newRequest: newRequest ?? defaultWSRequest, }, }) } export function setWSEndpoint(newEndpoint: string) { WSSessionStore.dispatch({ dispatcher: "setEndpoint", payload: { newEndpoint, }, }) } export function setWSProtocols(protocols: HoppWSProtocol[]) { WSSessionStore.dispatch({ dispatcher: "setProtocols", payload: { protocols, }, }) } export function addWSProtocol(protocol: HoppWSProtocol) { WSSessionStore.dispatch({ dispatcher: "addProtocol", payload: { protocol, }, }) } export function deleteWSProtocol(index: number) { WSSessionStore.dispatch({ dispatcher: "deleteProtocol", payload: { index, }, }) } export function deleteAllWSProtocols() { WSSessionStore.dispatch({ dispatcher: "deleteAllProtocols", payload: {}, }) } export function updateWSProtocol( index: number, updatedProtocol: HoppWSProtocol ) { WSSessionStore.dispatch({ dispatcher: "updateProtocol", payload: { index, updatedProtocol, }, }) } export function setWSSocket(socket: WSConnection) { WSSessionStore.dispatch({ dispatcher: "setSocket", payload: { socket, }, }) } export function setWSLog(log: HoppRealtimeLog) { WSSessionStore.dispatch({ dispatcher: "setLog", payload: { log, }, }) } export function addWSLogLine(line: HoppRealtimeLogLine) { WSSessionStore.dispatch({ dispatcher: "addLogLine", payload: { line, }, }) } export const WSRequest$ = WSSessionStore.subject$.pipe( pluck("request"), distinctUntilChanged() ) export const WSEndpoint$ = WSSessionStore.subject$.pipe( pluck("request", "endpoint"), distinctUntilChanged() ) export const WSProtocols$ = WSSessionStore.subject$.pipe( pluck("request", "protocols"), distinctUntilChanged() ) export const WSConnectingState$ = WSSessionStore.subject$.pipe( pluck("connectingState"), distinctUntilChanged() ) export const WSConnectionState$ = WSSessionStore.subject$.pipe( pluck("connectionState"), distinctUntilChanged() ) export const WSSocket$ = WSSessionStore.subject$.pipe( pluck("socket"), distinctUntilChanged() ) export const WSLog$ = WSSessionStore.subject$.pipe( pluck("log"), distinctUntilChanged() )