WebDNN 2: ONNX neural network inference in the browser, without a Python server
The Fastest DNN Running Framework on Web Browser
At a glance
- What is it?
- WebDNN 2 accepts ONNX models directly in the browser and dispatches inference to WebGPU, WebGL or WebAssembly, removing the Python preprocessing requirement of version 1.x. The WebAssembly backend requires a separate emscripten build that the default npm command does not cover, and the supported ONNX operator set is not documented anywhere in the repository.
- Who is it for?
- WebDNN 2 is the right tool when you need browser-native ONNX inference and can accept an alpha-quality API, a build that requires both Node.js 20 and Python 3, and no built-in WebAssembly fallback unless you configure emscripten. Skip it when you need a stable operator set, a documented ONNX opset compatibility table, or an API that will not shift between versions.
- Can I use it commercially?
- Check first. The repository uses a licence we do not classify automatically, so read its LICENSE file before any commercial use.
- Is it still maintained?
- Yes. The repository last received commits 9 days ago.
- What is it written in?
- Mainly TypeScript, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 11, 2026, and from our analysis. They are not legal advice.
Editorial analysis
The Python graph conversion step that v1.x required is gone in v2
WebDNN 1.x required a Python preprocessing stage to convert a model before it could run in the browser. WebDNN 2.x drops that requirement: an ONNX model can be loaded directly without any Python step beforehand, because the browser now handles the format natively. Offline model optimization remains available as an option, but it is no longer a prerequisite for inference.
This change matters for deployment. A team serving a model from a static host can place the .onnx file alongside the JavaScript bundle and handle inference entirely in the browser, with no Python server in the path. Whether that trade-off suits a given project depends on how much the browser's compilation overhead affects first-load latency, and the README gives no numbers on that.
The project describes itself as "The Fastest DNN Running Framework on Web Browser," but the README supplies no benchmark figures, so that claim cannot be verified from the repository alone.
WebGPU, WebGL and WebAssembly: three backends with very different availability profiles
WebDNN 2 covers hardware from WebGPU-capable GPUs to CPU-only environments through three distinct code paths, and the gap in build effort between them is substantial. WebGPU uses a WGSL-based kernel implementation; it works on modern Chrome and Edge without any flag, and on Safari and Firefox only when WebGPU is explicitly enabled in their settings. WebGL is the automatic fallback, using WebGL2 when available and dropping to WebGL1 otherwise.
The WebAssembly path is the broadest in hardware coverage but the narrowest in who can actually build it. It requires emscripten 3.1 or newer and a procedure documented in docs/emscripten-setup.md, separate from the standard npm build. For a CI pipeline without emscripten installed, that fallback is simply not part of the output. No performance data for any backend appears in the README, so the choice between them must rest on your browser support matrix rather than documented throughput.
What npm run build:all chains, and the Python dependency hidden inside it
Node.js 20 or newer is required (see .nvmrc). Python 3.10 or newer is declared in pyproject.toml as `requires-python = ">=3.10"` and is needed only for model optimization and test fixture generation.
npm install
uv sync # only if you use the Python graph transpiler / optimizer`uv sync` is optional and only applies to the Python side. The main build command is:
npm run build:allThis is not a single compile step. It chains three sub-tasks before the Vite bundle: `shader:webgpu` generates WGSL shaders, `makeShaderList` runs `python3 scripts/make_operator_entries.py` to generate operator entry points, and the JavaScript build follows. That middle step calls `python3` specifically, which means Python must be on the path even for a build that ignores the optimizer entirely.
Outputs land in dist/: `dist/webdnn.js` is a UMD bundle for unoptimized ONNX models; `dist/webdnn-core.js` loads models preprocessed offline by the Python optimizer; `dist/op-*.js` files are operator bundles loaded dynamically at runtime; `dist/types/` holds TypeScript type declarations. The WebAssembly backend is not part of this output: it requires emscripten 3.1 or newer and follows the separate steps in docs/emscripten-setup.md.
Loading an ONNX model and calling runner.run in the browser
Loading dist/webdnn.js via a script tag adds a global `WebDNN` object. For a model stored at `model_directory/model.onnx`, the README shows this example using an input of shape [1, 2]:
const runner = await WebDNN.load("model_directory/");
const inputDataArray = new Float32Array([5.1, -2.3]);
const inputTensor = new WebDNN.CPUTensor([1, 2], "float32", inputDataArray);
const [outputTensor] = await runner.run([inputTensor]);
console.log(outputTensor.data); // Float32Array`WebDNN.load` takes a directory path, not a direct file path. Input tensors use `WebDNN.CPUTensor`, which takes a shape array, a dtype string and a typed array. The result in `outputTensor.data` is a Float32Array, as the comment in the example notes. For a project using npm, the package.json exports map `.` to `dist/webdnn.js` and `./webdnn-core` to `dist/webdnn-core.js`, so either bundle can be imported by its mapped name.
The `example/minimum` directory holds a complete minimal working example for cases where the README snippet alone does not cover the surrounding page setup.
webdnn.js versus webdnn-core.js: which bundle to ship and when
Two bundles serve different deployment strategies. `dist/webdnn.js` loads and compiles an ONNX model at runtime entirely in the browser. `dist/webdnn-core.js` expects a model that has already been processed offline by the Python graph transpiler, which is what the `uv sync` path and optimizer produce.
Offline optimization can reduce the browser-side compilation work before inference begins. The cost is an added Python build step and a different model distribution format alongside the .onnx file. For a first deployment with no existing Python toolchain, `webdnn.js` avoids the Python dependency entirely at inference time. When first-load latency matters and a Python build step is acceptable, `webdnn-core.js` is the path the project provides.
How much faster the optimized path runs in practice is not quantified in the repository. The README does not give numbers for either bundle, so the decision must be made by profiling your own model in your target browser.
Test suite structure: vitest unit tests, uv-driven fixture generation, and Playwright E2E
The testing infrastructure separates GPU-dependent work from GPU-independent work clearly. Unit tests run through vitest with no GPU required:
npm test # unit tests (vitest, no GPU required)
npm run fixtures # generate ONNX test fixtures (uv, Python)
npm run test:e2e # Playwright E2E (CPU / WebGPU / WebGL, automated)
npm run server # static server for the manual browser runner`npm run fixtures` calls `uv run --project test/fixtures python test/fixtures/generate_fixtures.py` to produce the ONNX models and input/output tensors that tests rely on. This is the part of the test pipeline that requires Python and uv.
A legacy script at `test/model_test/make_models.py` depends on PyTorch and remains in the repository, but the README notes it is kept only for large-model generation and is not part of the standard flow. For browser backends that need hardware, `npm run test:e2e` drives Playwright across CPU, WebGPU and WebGL automatically. A manual alternative is also available: after `npm run server`, opening http://localhost:8080/test/model_test/runner/standard.html lets you select a backend and run tests by hand.
Operator coverage gaps, the emscripten constraint, and two files that disagree on a key fact
Three constraints matter before adopting this library. First, neither the README nor any other file in the repository lists which ONNX opsets or operator subsets are supported. Testing your specific model is the only way to determine whether it runs, regardless of which backend you target.
Second, the WebAssembly backend is absent from a default build. Any browser lacking WebGPU and WebGL2 falls outside the deployable surface unless you install emscripten 3.1 or newer and follow docs/emscripten-setup.md. For CI environments without emscripten, that fallback is not available.
Third, and the detail a skim of the repository would miss: the GitHub repository metadata lists the licence as "Other (a custom licence GitHub cannot classify; see the LICENSE file)," while pyproject.toml states `license = { text = "MIT" }` and carries the classifier "License :: OSI Approved :: MIT License." These are contradictory claims from the same codebase; LICENSE.txt at the repository root is the file to read before redistributing or embedding the library. The release titled "v2 alpha" on GitHub also differs from the pyproject.toml classifier "Development Status :: 4 - Beta," so the stability indication the two files give does not match.
Editorial conclusion
WebDNN 2 is the right tool when you need browser-native ONNX inference and can accept an alpha-quality API, a build that requires both Node.js 20 and Python 3, and no built-in WebAssembly fallback unless you configure emscripten. Skip it when you need a stable operator set, a documented ONNX opset compatibility table, or an API that will not shift between versions. Before committing, run npm test to confirm the unit tests pass in your environment, then load your own ONNX model through WebDNN.load in the specific browser you target and verify that your model's operators are covered.
Frequently asked questions
Does WebDNN 2 require Python to run inference in the browser?
No. Python 3.10 or newer is needed only for offline model optimization via the Python graph transpiler and for generating ONNX test fixtures. Running inference in the browser with dist/webdnn.js requires no Python at runtime.
What is the difference between webdnn.js and webdnn-core.js?
webdnn.js loads and compiles an ONNX model at runtime in the browser. webdnn-core.js loads models that were preprocessed offline by the WebDNN Python graph transpiler. For a first deployment without a Python toolchain, webdnn.js is the simpler path.
Which browsers support WebDNN 2?
WebGPU works on modern Chrome and Edge by default, and on Safari and Firefox where WebGPU is enabled. WebGL is the fallback, using WebGL2 when available and WebGL1 otherwise. The WebAssembly backend requires a separate emscripten build and is not included in npm run build:all.
What Node.js version does WebDNN 2 require?
Node.js 20 or newer is required, as specified by .nvmrc in the repository. The Python component requires Python 3.10 or newer, as declared in pyproject.toml under requires-python.
Does WebDNN 2 support all ONNX operators?
The README does not document which ONNX opsets or operator subsets are supported. Whether a specific model runs must be determined by testing it in the target browser and backend.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/mil-tokyo-webdnn)