From 3f62287bc7052d81778a6c8b3a0b5682c18c4f62 Mon Sep 17 00:00:00 2001 From: metamuffin Date: Fri, 8 Sep 2023 00:24:58 +0200 Subject: room watches --- client-web/source/protocol/mod.ts | 32 +++++++++++++++++++------------- 1 file changed, 19 insertions(+), 13 deletions(-) (limited to 'client-web/source/protocol/mod.ts') diff --git a/client-web/source/protocol/mod.ts b/client-web/source/protocol/mod.ts index 83ee8cb..0db1162 100644 --- a/client-web/source/protocol/mod.ts +++ b/client-web/source/protocol/mod.ts @@ -4,23 +4,22 @@ Copyright (C) 2023 metamuffin */ import { ClientboundPacket, RelayMessage, RelayMessageWrapper, ServerboundPacket } from "../../../common/packets.d.ts" +import { EventEmitter } from "../helper.ts"; import { log } from "../logger.ts" import { crypto_encrypt, crypto_seeded_key, crypt_decrypt, crypto_hash } from "./crypto.ts" export class SignalingConnection { - room!: string websocket!: WebSocket - room_hash!: string - key!: CryptoKey + room?: string + room_hash?: string + key?: CryptoKey my_id?: number // needed for outgoing relay messages - control_handler: (_packet: ClientboundPacket) => void = () => { } - relay_handler: (_sender: number, _message: RelayMessage) => void = () => { } + control_handler = new EventEmitter() + relay_handler = new EventEmitter<[number, RelayMessage]>() constructor() { } - async connect(room: string): Promise { - this.key = await crypto_seeded_key(room) - this.room_hash = await crypto_hash(room) + async connect(): Promise { log("ws", "connecting…") const ws_url = new URL(`${window.location.protocol.endsWith("s:") ? "wss" : "ws"}://${window.location.host}/signaling`) this.websocket = new WebSocket(ws_url) @@ -44,21 +43,28 @@ export class SignalingConnection { } on_open() { log("ws", "websocket opened"); - this.send_control({ join: { hash: this.room_hash } }) setInterval(() => this.send_control({ ping: null }), 30000) // stupid workaround for nginx disconnecting inactive connections } + + async join(room: string) { + this.room = room; + this.key = await crypto_seeded_key(room) + this.room_hash = await crypto_hash(room) + this.send_control({ join: { hash: this.room_hash } }) + } + on_error() { log({ scope: "ws", error: true }, "websocket error occurred!") } async on_message(data: string) { const packet: ClientboundPacket = JSON.parse(data) // TODO dont crash if invalid - this.control_handler(packet) + this.control_handler.dispatch(packet) if (packet.init) this.my_id = packet.init.your_id; if (packet.message) { - const plain_json = await crypt_decrypt(this.key, packet.message.message) + const plain_json = await crypt_decrypt(this.key!, packet.message.message) const plain: RelayMessageWrapper = JSON.parse(plain_json) // TODO make sure that protocol spec is met if (plain.sender == packet.message.sender) - this.relay_handler(packet.message.sender, plain.inner) + this.relay_handler.dispatch([packet.message.sender, plain.inner]) else { log({ scope: "crypto", warn: true }, `message dropped: sender inconsistent (${plain.sender} != ${packet.message.sender})`) } @@ -71,7 +77,7 @@ export class SignalingConnection { async send_relay(data: RelayMessage, recipient?: number | null) { recipient ??= undefined // null -> undefined const packet: RelayMessageWrapper = { inner: data, sender: this.my_id! } - const message = await crypto_encrypt(this.key, JSON.stringify(packet)) + const message = await crypto_encrypt(this.key!, JSON.stringify(packet)) this.send_control({ relay: { recipient, message } }) } } -- cgit v1.2.3-70-g09d2