Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/denoland/celld/llms.txt

Use this file to discover all available pages before exploring further.

Celld supports WebAssembly via V8’s own engine. A bundle can import a .wasm file as a compiled WebAssembly.Module — the same as on Cloudflare. No special runtime configuration is required, and V8’s Wasm support is available without restrictions.

Importing Wasm

Add a .wasm file to your Wrangler project. When celld deploy bundles the project, esbuild treats .wasm imports as compiled WebAssembly.Module objects:
import wasmModule from "./my-module.wasm";

export default {
  async fetch(request) {
    const instance = await WebAssembly.instantiate(wasmModule, {});
    const result = instance.exports.add(1, 2);
    return new Response(String(result));
  }
};
The wrangler.jsonc does not need any special key for Wasm imports — just reference the file in your JavaScript:
{
  "name": "my-worker",
  "main": "index.js",
  "compatibility_date": "2026-01-01"
}

Using Wasm in a Durable Object

Import the module at the top of the file and instantiate it inside the Durable Object. Because each cell has its own memory, each instance is isolated:
import wasmModule from "./counter.wasm";

export class Counter {
  constructor(state, env) {
    this.state = state;
  }

  async fetch(request) {
    const instance = await WebAssembly.instantiate(wasmModule, {});
    // Call exported Wasm functions directly.
    const n = instance.exports.increment();
    return new Response(JSON.stringify({ n }));
  }
}

Rust + workers-rs

The examples/wasm project is a complete Durable Object counter written in Rust, compiled to Wasm with workers-rs. The Rust source handles the fetch handler and storage calls — no JavaScript is needed beyond the generated shim.
The Wasm example requires a build step before deploy. Run worker-build --release to compile the Rust crate and generate build/worker/shim.mjs. See the examples/wasm README for the full build instructions.
use worker::*;

#[durable_object(fetch)]
pub struct Counter {
    state: State,
}

impl DurableObject for Counter {
    fn new(state: State, _env: Env) -> Self {
        Self { state }
    }

    async fn fetch(&self, req: Request) -> Result<Response> {
        let n: u64 = self.state.storage().get("n").await.ok().flatten().unwrap_or(0);
        let n = n + 1;
        self.state.storage().put("n", &n).await?;
        let path = req.path();
        let name = path.strip_prefix("/c/").unwrap_or("");
        Response::from_json(&serde_json::json!({ "name": name, "n": n, "lang": "rust" }))
    }
}

#[event(fetch)]
async fn fetch(req: Request, env: Env, _ctx: Context) -> Result<Response> {
    let path = req.path();
    if let Some(name) = path.strip_prefix("/c/").filter(|name| !name.is_empty()) {
        let namespace = env.durable_object("COUNTER")?;
        let stub = namespace.id_from_name(name)?.get_stub()?;
        return stub.fetch_with_request(req).await;
    }
    let status = if path == "/" { 200 } else { 404 };
    Ok(Response::ok("celld rust demo. Try: curl http://localhost:8080/c/hello\n")?.with_status(status))
}
The wrangler.jsonc for the Rust example points at the generated shim:
{
  "name": "counter-demo-rs",
  "main": "build/worker/shim.mjs",
  "compatibility_date": "2026-01-01",
  "durable_objects": { "bindings": [{ "name": "COUNTER", "class_name": "Counter" }] },
  "migrations": [{ "tag": "v1", "new_sqlite_classes": ["Counter"] }]
}
To build and deploy:
rustup target add wasm32-unknown-unknown
cargo install worker-build

worker-build --release
celld deploy . --bucket s3://my-cells-bucket

Supported Wasm features

V8’s WebAssembly support is available in full, without restrictions:
FeatureNotes
WebAssembly.ModuleImport a .wasm file directly — it arrives as a compiled module.
WebAssembly.InstanceInstantiate a module with an imports object.
WebAssembly.MemoryCreate or import linear memory with shared flag support.
Imports / exportsPass JavaScript functions as Wasm imports; call Wasm exports from JavaScript.
SIMDAvailable where V8 supports it.
Threads (shared memory)Available with SharedArrayBuffer and a shared WebAssembly.Memory.
There are no compile-time or runtime flags required to enable Wasm features. If V8 supports it, celld supports it.

Build docs developers (and LLMs) love