Overview
Browser events arrive on the JS side. Each crossing into WASM may
copy linear-memory buffers or convert strings. A naive “serialize
whole document to Rust on every input” design will
bottleneck before your diff algorithm matters.
Copy cost & encoding
- UTF-16 vs UTF-8: JS exposes strings as UTF-16
code units; Rust
Stringindices differ. Pass byte offsets or scalar offsets explicitly across the boundary, or normalize in one place. - Large strings: Full HTML serialization from JS to Rust duplicates memory. Prefer incremental patches, hashed snapshots, or shared views where your security model allows.
Batching & op streams
Send small operations (insert/delete/format) when possible instead of shipping the whole doc. For collaboration, binary CRDT updates are often smaller than text snapshots.
Debouncing helps for expensive validation—not for losing IME ordering; never batch in ways that reorder composition relative to commits.
Async vs synchronous host calls
Promises from WASM resolve on microtasks; input handlers may expect synchronous DOM updates. If Rust work is async, guard against selection races: the user may type again before your WASM task finishes.
FFI hygiene
- Prefer stable handles for long-lived documents (e.g. boxed Rust state in WASM linear memory).
- Expose narrow APIs: “apply op” vs “replace entire tree”.
- Measure with browser Performance panel: time in WASM vs glue.
Wasm guides
Editing approaches
contenteditable + WASM: source of truth, event order, DOM↔model loop, normalization, and when to call Rust.
IME & composition
composition events, syncing a Rust document model, and why the browser still owns the IME.
Clipboard & input routing
beforeinput, paste, routing decisions in JS vs sanitization in WASM.
Tooling, bundle & workers
wasm-pack, wasm-opt, code splitting, Web Workers, COOP/COEP and threads.
Collaboration & CRDT (WASM)
Yrs/y-crdt, bridging to Yjs, snapshots vs update streams with an editor host.
Selection, Range & offsets
UTF-16 vs UTF-8 indices, Selection/Range in JS, mapping to a Rust model and getTargetRanges.
Undo & redo model
Browser undo stack vs model history, programmatic DOM, and WASM-hosted transactions.
Accessibility (WASM host)
Roles, focus, screen readers when the editable surface is still the browser.
Testing & debugging
E2E, profiling the JS↔WASM boundary, reproducing IME and paste in CI.
Security & deployment
CSP, SRI, module integrity, and hosting WASM next to contenteditable.