Selecting Compute Backends (CPU, WebGPU, WebNN) in Transformers.js: A Complete Guide

Transformers.js automatically detects your runtime capabilities and maps device requests to the optimal ONNX execution provider, allowing you to explicitly select 'cpu', 'webgpu', 'webnn', or 'auto' when creating pipelines.

Selecting compute backends for different browsers in Hugging Face Transformers.js requires understanding how the library abstracts hardware acceleration behind a unified device selector. The repository probes the JavaScript runtime to determine whether WebGPU, WebNN, or CPU execution is available, then routes inference requests to the appropriate ONNX execution provider. This mechanism works uniformly across Node.js, desktop browsers, mobile browsers, and Web Workers.

How Runtime Capability Detection Works

In src/env.js, the library probes the global environment (window, navigator, process) to expose boolean flags through the exported apis object. These flags include IS_BROWSER_ENV, IS_WEBGPU_AVAILABLE, IS_WEBNN_AVAILABLE, and IS_SAFARI, which determine what compute backends are accessible in the current context.

Based on these flags, src/backends/onnx.js constructs a supportedDevices array. In Node.js environments, this always includes 'cpu' and conditionally adds 'webgpu' or 'cuda' depending on the installed ONNX Runtime binary. In browsers, the array always contains 'wasm' and conditionally includes 'webgpu' and WebNN variants ('webnn', 'webnn-gpu', 'webnn-npu', 'webnn-cpu').

Mapping Devices to ONNX Execution Providers

The function deviceToExecutionProviders() in src/backends/onnx.js translates symbolic device names into concrete ONNX execution providers. When you specify device: "webgpu", the function maps this to the WebGPU execution provider. If you pass device: "auto", the function supplies the entire supportedDevices list, letting ONNX Runtime select the fastest available provider automatically.

When a pipeline is instantiated, the resolved device is passed to createInferenceSession() in the same file. This function ensures WASM binaries are pre-loaded via ensureWasmLoaded() before creating the session with the mapped provider list.

Resolving User Device Requests

The file src/utils/devices.js exports the canonical DEVICE_TYPES list and implements selectDevice(), which resolves per-model configuration objects or plain strings to concrete device names. The selector defaults to cpu in Node.js environments and wasm in browsers when no device is explicitly specified.

Backend Availability by Browser and Environment

Different JavaScript runtimes expose different capabilities that affect which compute backends are available:

  • Node.js: Defaults to cpu. Supports webgpu experimentally if using a GPU-enabled onnxruntime-node binary. Also supports cuda, dml, and coreml on compatible hardware.
  • Chrome/Edge (Desktop): Defaults to wasm. Supports webgpu on Chrome 113+ without flags. WebNN is not currently available.
  • Safari (macOS/iOS): Defaults to wasm. Supports webgpu (Safari 17+) and full WebNN implementations including webnn-gpu, webnn-npu, and webnn-cpu.
  • Firefox: Defaults to wasm. Requires enabling dom.webgpu.enabled flag for WebGPU support. No WebNN implementation.
  • Android Chromium: Defaults to wasm. WebGPU often requires the enable-unsafe-webgpu flag.

Practical Code Examples

Force CPU Execution (Universal Fallback)

Explicitly setting device: 'cpu' works across all environments, including Node.js and every browser, using the ONNX CPU execution provider.

import { pipeline } from '@huggingface/transformers';

const classifier = await pipeline(
  'sentiment-analysis',
  'distilbert-base-uncased-finetuned-sst-2-english',
  { device: 'cpu' }
);

console.log(await classifier('I love Transformers.js!'));

Enable WebGPU Acceleration

Request the WebGPU backend on supported browsers to leverage GPU compute shaders for faster inference.

import { pipeline } from '@huggingface/transformers';

const embedder = await pipeline(
  'feature-extraction',
  'mixedbread-ai/mxbai-embed-xsmall-v1',
  { device: 'webgpu' }
);

const vectors = await embedder(['Hello world!']);
console.log(vectors.tolist());

Use WebNN on Safari

Apple's WebNN implementation is available in Safari on macOS and iOS, offering hardware-accelerated inference through the Neural Engine or GPU.

import { pipeline } from '@huggingface/transformers';

const recognizer = await pipeline(
  'automatic-speech-recognition',
  'onnx-community/whisper-tiny.en',
  { device: 'webnn' }
);

const result = await recognizer('https://huggingface.co/datasets/Xenova/transformers.js-docs/resolve/main/jfk.wav');
console.log(result.text);

You can also request specific WebNN sub-types such as 'webnn-gpu' or 'webnn-npu' to target specific hardware accelerators.

Automatic Device Selection

Passing device: 'auto' lets the library select the fastest available backend from the supportedDevices list.

import { pipeline } from '@huggingface/transformers';

const classifier = await pipeline(
  'image-classification',
  'onnx-community/mobilenetv4_conv_small.e2400_r224_in1k',
  { device: 'auto' }
);

Summary

  • Transformers.js abstracts compute backends through a device selector implemented in src/utils/devices.js and src/backends/onnx.js.
  • Runtime detection occurs in src/env.js, which exposes flags like IS_WEBGPU_AVAILABLE and IS_WEBNN_AVAILABLE via the apis object.
  • The function deviceToExecutionProviders() maps symbolic names (e.g., 'webgpu') to ONNX execution providers.
  • Default devices: cpu for Node.js, wasm for browsers.
  • WebGPU is available in Chrome 113+, Edge, and Safari 17+.
  • WebNN is currently Safari-only, supporting GPU, NPU, and CPU sub-devices.
  • Use device: 'auto' to let the library automatically select the fastest available backend.

Frequently Asked Questions

What is the default compute backend when I don't specify a device?

When you omit the device option, Transformers.js defaults to cpu in Node.js environments and wasm (WebAssembly) in browser environments. This ensures maximum compatibility across all platforms, though it may not provide the best performance compared to GPU-accelerated options.

How do I check if WebGPU is available in my browser before creating a pipeline?

The library automatically checks availability via the apis.IS_WEBGPU_AVAILABLE flag exposed in src/env.js. You can inspect this flag by importing the env object, though typically you simply pass device: 'webgpu' and let the library fall back to wasm if unavailable, or use device: 'auto' to select the best available option.

Can I use WebNN in browsers other than Safari?

Currently, WebNN is only implemented in Safari on macOS and iOS. Chrome and Firefox have not shipped WebNN support, though you can enable experimental WebGPU flags in Firefox for GPU acceleration. The apis.IS_WEBNN_AVAILABLE flag in src/env.js will be false in non-Safari browsers.

Why does my WebGPU pipeline fail with a "session already started" error?

This error occurs when multiple inference sessions attempt to run simultaneously in WASM or WebGPU contexts. According to src/backends/onnx.js, the library chains inference calls via runInferenceSession() to prevent concurrent execution conflicts. Ensure you are not manually creating multiple overlapping sessions, and allow the library to handle session management automatically.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →