This documentation is part of the "Projects with Books" initiative at zenOSmosis.
The source code for this project is available on GitHub.
muxio-wasm-rpc-client: Browser/WASM RPC Client
Loading…
muxio-wasm-rpc-client: Browser/WASM RPC Client
Relevant source files
- extensions/muxio-rpc-service-endpoint/src/error.rs
- extensions/muxio-rpc-service-endpoint/src/lib.rs
- extensions/muxio-rpc-service-endpoint/tests/prebuffered_endpoint_tests.rs
- extensions/muxio-tokio-rpc-client/src/lib.rs
- extensions/muxio-tokio-rpc-server/src/lib.rs
- extensions/muxio-wasm-rpc-client/Cargo.toml
- extensions/muxio-wasm-rpc-client/README.md
- extensions/muxio-wasm-rpc-client/src/lib.rs
- extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs
- extensions/muxio-wasm-rpc-client/src/static_lib.rs
- extensions/muxio-wasm-rpc-client/src/static_lib/README.md
- extensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs
- extensions/muxio-wasm-rpc-client/src/static_lib/static_transport_bridge.rs
The muxio-wasm-rpc-client crate provides a WebAssembly-compatible implementation of the Muxio RPC client. It is designed to run in browser environments or any WASM runtime that provides a JavaScript bridge for network I/O. Unlike the native Tokio client, which manages its own sockets via background tasks, this client relies on external triggers (typically from JavaScript) to drive its internal state and data processing.
RpcWasmClient Architecture
The RpcWasmClient acts as the central coordinator for WASM-based RPC operations. It integrates a RpcDispatcher for managing outgoing calls and an RpcServiceEndpoint for handling incoming requests from the remote peer extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:14-21
Key Components
| Component | Role |
|---|---|
dispatcher | Manages RPC stream allocation, request correlation, and frame encoding/decoding extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs15 |
endpoint | Registry for handlers that process incoming RPC calls from the host/server extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs17 |
emit_callback | A closure used to send serialized binary chunks back to the JavaScript environment for network transmission extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs18 |
is_connected | An AtomicBool tracking the transport state extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs20 |
Entity Mapping: Client Internals
The following diagram shows how the RpcWasmClient struct maps to the core Muxio entities.
graph TD
subgraph "RpcWasmClient [extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs]"
C["RpcWasmClient"] --> D["RpcDispatcher [muxio_core::rpc::RpcDispatcher]"]
C --> E["RpcServiceEndpoint [muxio_rpc_service_endpoint::RpcServiceEndpoint]"]
C --> CB["emit_callback [Arc<dyn Fn(Vec<u8>)>]"]
C --> S["state_change_handler [RpcTransportStateChangeHandler]"]
end
D -.->|encodes frames| CB
E -.->|uses for response| D
“WASM Client Entity Map”
Sources: extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:14-32
Lifecycle and Data Flow
The client’s lifecycle is driven by external events, typically mapped from a JavaScript WebSocket object’s events (onopen, onmessage, onclose).
Connection Lifecycle
handle_connect: Called when the transport is established. It updatesis_connectedtotrueand triggers theRpcTransportState::Connectedevent via the registered handler extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:35-41handle_disconnect: Called when the transport fails or closes. It marks the client as disconnected and invokesfail_all_pending_requestson the dispatcher withFrameDecodeError::ReadAfterCancelto clean up any awaiting RPC futures extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:58-68
The read_bytes Pipeline
The read_bytes method processes incoming binary data from the network. It delegates to the internal RpcServiceEndpoint, which handles the decoding and routing of both prebuffered and streaming RPC messages extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:46-55
“WASM Read Bytes Data Flow”
Sources: extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:46-55 extensions/muxio-rpc-service-endpoint/tests/prebuffered_endpoint_tests.rs:71-75
Static Client Pattern
To simplify integration with JavaScript and avoid complex state management across the WASM boundary, the crate provides a “Static Client” pattern. This allows the WASM module to maintain a single, global RpcWasmClient instance extensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs:9-11
Global Reference
The MUXIO_STATIC_RPC_CLIENT_REF is a thread-local RefCell that holds an Option<Arc<RpcWasmClient>>. It is typically initialized once during the WASM startup phase extensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs10
Key Static Functions
init_static_client(): Idempotent initialization of the global client. It sets up theemit_callbackto point to thestatic_muxio_write_bytesbridge, which communicates back to JS extensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs:25-36with_static_client_async(f): The primary interface for making RPC calls from WASM. It retrieves the static client and executes an async closure, returning a JavaScriptPromiseviawasm_bindgen_futures::future_to_promiseextensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs:54-72
Sources: extensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs:9-82
JavaScript Bridge
The bridge uses wasm-bindgen to export functions to JavaScript and import networking functions from the host environment.
Exported to JS
These functions are decorated with #[wasm_bindgen] and are intended to be called by the JavaScript WebSocket wrapper:
static_muxio_read_bytes_uint8(inbound_data): Entry point for binary data arriving from the network. It converts theUint8Arrayto a RustVec<u8>and passes it to the static client extensions/muxio-wasm-rpc-client/src/static_lib/static_transport_bridge.rs:19-31static_muxio_handle_connect(): Bridges the JSonopenevent to the Rust client’s connection logic extensions/muxio-wasm-rpc-client/src/static_lib/static_transport_bridge.rs:34-43static_muxio_handle_disconnect(): Bridges JSoncloseoronerrorevents to the Rust client’s disconnection logic extensions/muxio-wasm-rpc-client/src/static_lib/static_transport_bridge.rs:46-55
Imported from JS
The WASM module expects the host environment to provide:
static_muxio_write_bytes_uint8(data): An external JS function that takes aUint8Arrayand transmits it via the network (e.g.,socket.send(data)) extensions/muxio-wasm-rpc-client/src/static_lib/static_transport_bridge.rs:8-11
“JS-WASM Bridge Interaction”
Sources: extensions/muxio-wasm-rpc-client/src/static_lib/static_transport_bridge.rs:7-55 extensions/muxio-wasm-rpc-client/src/static_lib/static_client.rs29
RpcServiceCallerInterface Implementation
RpcWasmClient implements the RpcServiceCallerInterface, allowing it to participate in the high-level RPC service ecosystem (e.g., using call_rpc_buffered) extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:89-115
| Method | Implementation |
|---|---|
get_dispatcher() | Returns an Arc<Mutex<RpcDispatcher>> extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:90-92 |
get_emit_fn() | Returns the internal emit_callback extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:94-96 |
is_connected() | Returns the current value of the is_connected atomic extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:98-100 |
set_state_change_handler() | Sets the handler and immediately triggers it if already connected extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:102-114 |
Sources: extensions/muxio-wasm-rpc-client/src/rpc_wasm_client.rs:89-115