Using Cesium.js without wasm on main thread
- Dominant language
- JavaScript
- Stars
- 15.7k
- Forks
- 3.9k
- Avg merge
- 4d 6h
- Merged PRs (30d)
- 34
Description
### Feature Request / Inquiry
Hi,
We're looking into using Cesium in a desktop app, and are debating expanding our CSP to support wasm. As part of the discussion, we'd like to know if it is possible to run Cesium without wasm support - or to at least move all wasm usage to within workers to allow for a less-permissive CSP where `wasm-unsafe-eval` is scoped to worker contexts.
With the help of Claude I've gathered all instances of wasm usage in the library below. As mentioned, one compromise might be to move all wasm usage into workers. Then we could dynamically add headers to worker responses with the CSP only for that response ([CSPs are set from the response for the resource](https://developer.mozilla.org/en-US/docs/Web/HTTP/Reference/Headers/Content-Security-Policy#csp_in_workers) that creates the context for which a particular CSP is valid)
### Main Thread
| Original document-side path | Current status |
| --- | --- |
| `meshoptimizer` for glTF buffer views and 3D Tiles terrain | Moved to workers: [`Workers/decodeMeshopt.js`](https://github.com/ben-polinsky/cesium/blob/bdp/issue-13617-wasm-main-thread/packages/engine/Source/Workers/decodeMeshopt.js) and `Workers/createVerticesFromCesium3DTilesTerrain.js`. The document schedules a task; `MeshoptDecoder.ready` and decoding execute in the worker. |
| `@spz-loader/core` | Moved to [`Workers/decodeSpz.js`](https://github.com/ben-polinsky/cesium/blob/bdp/issue-13617-wasm-main-thread/packages/engine/Source/Workers/decodeSpz.js), via [`SpzDecoder`](https://github.com/ben-polinsky/cesium/blob/bdp/issue-13617-wasm-main-thread/packages/engine/Source/Scene/SpzDecoder.js). The default SPZ decoder still needs `'unsafe-eval'` in that **worker** because of upstream Emscripten glue; it no longer needs an exception in the document. `SpzDecoder.workerModuleUrl` permits a deployment to substitute a strict-compatible worker. |
I also rechecked the original `long` / `protobufjs` row. It is not a document-side Wasm path: Cesium imports `protobufjs/dist/minimal/protobuf.js`, which does not load `long` in its ESM/CommonJS path (the `long` hookup is optional AMD configuration), and the generated Google Earth Enterprise parser contains no `Long` or 64-bit fields.
### Worker-side
Pattern: main thread fetches `.wasm` bytes ([`TaskProcessor.initWebAssemblyModule`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/Core/TaskProcessor.js)), posts to worker, worker compiles under its own header-delivered policy.¹
| Feature | Config site | Worker | Binary |
|---|---|---|---|
| Draco decode | [`Scene/DracoLoader.js`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/Scene/DracoLoader.js) | `Workers/decodeDraco.js` | `ThirdParty/draco_decoder.wasm` |
| KTX2/Basis transcode | [`Core/KTX2Transcoder.js`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/Core/KTX2Transcoder.js) | `Workers/transcodeKTX2.js` | `ThirdParty/basis_transcoder.wasm` |
| I3S decode | [`Scene/I3SDecoder.js`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/Scene/I3SDecoder.js) | `Workers/decodeI3S.js` | `ThirdParty/draco_decoder.wasm` |
| Gaussian splat sort | [`Scene/GaussianSplatSorter.js`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/Scene/GaussianSplatSorter.js) | `Workers/gaussianSplatSorter.js` | `ThirdParty/wasm_splats_bg.wasm` |
| Gaussian splat textures | [`Scene/GaussianSplatTextureGenerator.js`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/Scene/GaussianSplatTextureGenerator.js) | `Workers/gaussianSplatTextureGenerator.js` | `ThirdParty/wasm_splats_bg.wasm` |
| KMZ/zip inflate | [`DataSources/KmlDataSource.js`](https://github.com/CesiumGS/cesium/blob/main/packages/engine/Source/DataSources/KmlDataSource.js) (`configure()` inside `loadKmz()` — lazy *and* worker-routed) | `ThirdParty/Workers/zip-web-worker.js` | `ThirdParty/zip-module.wasm` |
Thanks in advance :)
P.S. only partially used AI for the source-gathering.
### AI acknowledgment
- [x] I used AI to generate this feature request.
- [x] (If the above is checked) I have reviewed the AI-generated content before submitting.
At least tangentially related: https://github.com/CesiumGS/cesium/issues/13412
Contributor guide
Assessment
This issue has not been assessed yet.