Developers
Concepts & security

Concepts & security

Differences from the browser WebSocket

MixWebSocket extends EventTarget and mirrors the standard WebSocket surface where it makes sense. Differences are intentional and follow from the underlying WASM transport:

Browser WebSocketMixWebSocketWhy
Synchronous constructor; readiness via the open eventAsynchronous constructor; readiness via await ws.opened() or the open eventThe mixnet connect, smoltcp socket open, and TLS handshake all happen in the worker.
binaryType: 'blob' | 'arraybuffer' (default Blob)binaryType is fixed to 'arraybuffer'Blob construction in a Web Worker requires a transferable; ArrayBuffer is the lowest common denominator.
bufferedAmountNot exposedWrites queue inside the worker; no main-thread byte counter.
send() returns void synchronouslysend() returns Promise<void>The send hops the worker boundary.
close(code, reason) returns voidclose(code, reason) returns Promise<void>Same reason.
protocols argument supports string or string[]Same(no difference)

The standard open, message, close, and error events fire as you would expect. MessageEvent.data is string for text frames and ArrayBuffer for binary frames.

Security model

mix-websocket follows the shared mixnet exit security model. What that means specifically for WS/WSS:

At the IPR exitWhat's visible
Secure (wss://)Destination IP and port. Frames are TLS ciphertext, terminating at the destination.
Plain (ws://)Destination IP and port, plus every frame in plaintext.
⚠️

TLS terminates inside the WASM bundle (via rustls (opens in a new tab) in smolmix-wasm), not in the browser. Mozilla's CA bundle is compiled into the WASM. Use wss:// for any non-public traffic; ws:// is visible to the IPR in full.