UNPKG

@logux/core

Version:

Logux core components

91 lines (77 loc) 1.84 kB
import { createNanoEvents } from 'nanoevents' export class WsConnection { constructor(url, Class, opts) { this.connected = false this.emitter = createNanoEvents() if (Class) { this.Class = Class } else if (typeof WebSocket !== 'undefined') { this.Class = WebSocket } else { /* c8 ignore next 2 */ throw new Error('No WebSocket support') } this.url = url this.opts = opts } connect() { if (this.ws) return Promise.resolve() this.emitter.emit('connecting') this.init(new this.Class(this.url, undefined, this.opts)) return new Promise(resolve => { this.ws.onopen = () => { this.connected = true this.emitter.emit('connect') resolve() } }) } disconnect() { if (this.ws) { this.ws.onclose = undefined this.ws.close() this.onclose() } } error(message) { let err = new Error('Wrong message format') err.received = message this.emitter.emit('error', err) } init(ws) { ws.onerror = event => { this.emitter.emit('error', event.error || new Error('WS Error')) } ws.onclose = () => { this.onclose() } ws.onmessage = event => { let data try { data = JSON.parse(event.data) } catch { this.error(event.data) return } this.emitter.emit('message', data) } this.ws = ws } on(event, listener) { return this.emitter.on(event, listener) } onclose() { if (this.ws) { this.connected = false this.emitter.emit('disconnect') this.ws = undefined } } send(message) { if (this.ws && this.ws.readyState === this.ws.OPEN) { this.ws.send(JSON.stringify(message)) } else { this.emitter.emit('error', new Error('WS was closed')) } } }