Skip to content

Add web-rwkv-wasm crate for npm package distribution#62

Merged
cryscan merged 2 commits into
cryscan:mainfrom
sebastian-zm:feat/wasm-npm-package
Jun 1, 2026
Merged

Add web-rwkv-wasm crate for npm package distribution#62
cryscan merged 2 commits into
cryscan:mainfrom
sebastian-zm:feat/wasm-npm-package

Conversation

@sebastian-zm

Copy link
Copy Markdown

Add web-rwkv-wasm crate for npm package distribution

Closes #60

Summary

Adds a new workspace crate, crates/web-rwkv-wasm, that exposes web-rwkv's
WebGPU RWKV inference to JavaScript via wasm-bindgen, packaged for npm. This
lets a web app run RWKV inference locally in the browser with a plain
pnpm add @cryscan/web-rwkv-wasm instead of setting up a Rust/wasm-pack
toolchain. The binding surface is upstreamed from the official demo
web-rwkv-puzzles — same API,
only the packaging differs (--target web ESM instead of the demo's
--target no-modules global).

What's included

  • New crate crates/web-rwkv-wasm (cdylib + rlib), depending on the
    parent web-rwkv crate with default-features = false, features = ["web"]
    (drops tokio and subgroup-ops, neither of which ports to browser WebGPU):
    • session.rsSession with reader/prefab loading, run/softmax,
      state get/load, and a built-in prefix cache (checkout/cache)
    • loader.rsTensor / TensorReader (implements web-rwkv's Reader)
    • sampler.rsSimpleSampler (argmax) and NucleusSampler
    • cache.rs, ops.rs, visual.rs (state heatmaps as base64 PNGs), and the
      mul_exp.wgsl / mul_w.wgsl shaders
    • README.md (API overview + Web Worker usage), LICENSE,
      build.bash / build.cmd
  • Cargo.toml — introduces a [workspace] section registering
    web-rwkv-derive and web-rwkv-wasm as members.
  • .github/workflows/wasm-npm.yml — builds the ESM package on PRs and on
    pushes to main that touch the crate (this is the CI verification);
    publishes to npm only via a manual workflow_dispatch with publish=true.
    The npm scope is parameterized (defaults to @cryscan/web-rwkv-wasm).

Requirements

  • A WebGPU-capable browser (navigator.gpu). No SharedArrayBuffer / threads,
    so no cross-origin isolation (COOP/COEP) needed.
  • Models are f16 safetensors (RWKV v4/v5/v6/v7) or a CBOR prefab; plus a
    tokenizer vocab JSON.

Verification

  • cargo check -p web-rwkv-wasm --target wasm32-unknown-unknown compiles
    cleanly (no errors/warnings).
  • Workspace metadata resolves all three members.

Notes for reviewers / follow-ups

  • Publishing to npm requires an NPM_TOKEN repo secret and ownership of the
    target npm scope. The CI build job verifies on every PR regardless, so
    merge does not depend on the publish setup.
  • --target web (ESM) is chosen over the demo's --target no-modules so the
    package works with bundlers and module workers; consumers must await init()
    before use.
  • wasm-opt = ['-Os'] is set for the release profile to trim module size;
    inference runs on the GPU, so CPU-side wasm speed is not the bottleneck.

Introduce a new `crates/web-rwkv-wasm` crate exposing the runtime to
JavaScript/WebAssembly, including session, cache, sampler, loader, ops,
and visual bindings, plus build scripts and a GitHub Actions workflow to
publish the npm package.
- cache.rs: add SAFETY comment on the as_token_slice repr(transparent) cast
- session.rs: replace user-input assert_eq! panics in softmax/back/checkout
  with descriptive JsError returns; propagate adapter-request failures as
  errors instead of .expect() panics
- visual.rs: return JsError on head-size mismatch and image-write failure
- add trailing newlines to LICENSE, mul_exp.wgsl, mul_w.wgsl
@cryscan cryscan merged commit 7d917a9 into cryscan:main Jun 1, 2026
2 of 3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Feature Request] NPM package

2 participants