Skip to content
On this page

Cloudflare Workers Emscripten WASM

Came across a need to run some Emscripten compiled WASM code (google/draco) inside a Cloudflare Worker without browser rendering support.

The default node_js draco wrapper uses wasm bundled as base64 string, which is not supported in Cloudflare Workers. But we can import .wasm files directly in the worker, manually load them from the import, instead of a url.

For this, we need a wrapper js for the Module and wasm file, which can be generated using emcc with the -s ENVIRONMENT=web -s MODULARIZE=1 flags.

javascript
import DracoEncoderModule from './draco_encoder_wrapper';
import DracoEncoderWasm from './draco_encoder.wasm';

// yeah this is also required
globalThis.__dirname = ''

const draco3dEncoder = await DracoEncoderModule({
    instantiateWasm: (imports, callback) => {
        const instance = new WebAssembly.Instance(DracoEncoderWasm, imports);
        callback(instance);
        return instance.exports;
    }

})

The module can then be used with @gltf-transform/core or any other library that supports Draco encoding.

javascript
import {Transform, WebIO} from '@gltf-transform/core'

// in fetch
const io = new WebIO({credentials: 'include'})
    .registerExtensions(ALL_EXTENSIONS)
    .registerDependencies({
        // 'draco3d.decoder': await draco3d.createDecoderModule(), // Optional.
        'draco3d.encoder': draco3dEncoder, // Optional.
    });

Made with ❤️ using the awesome vitepress