vitest-dev/vitest · error · Error
[@vitest/web-worker] Cannot initiate a custom Web Worker. "$
Error message
[@vitest/web-worker] Cannot initiate a custom Web Worker. "${name}" is not supported in this environment. Please, consider using jsdom or happy-dom environment. What it means
defineWebWorkers (packages/web-worker/src/pure.ts:6-24) installs the Worker/SharedWorker constructors only when the current runtime lacks them. Before installing, it calls assertGlobalExists('EventTarget') and assertGlobalExists('MessageEvent') (utils.ts:8-14) because Vitest's worker shim is built on top of those primitives. If the named global is missing from globalThis, the function throws this Error telling the user which environment primitives are unavailable.
Source
Thrown at packages/web-worker/src/utils.ts:10
import type { Debugger } from 'obug'
import type { CloneOption } from './types'
import ponyfillStructuredClone from '@ungap/structured-clone'
import { createDebug } from 'obug'
export const debug: Debugger = createDebug('vitest:web-worker')
export function assertGlobalExists(name: string): void {
if (!(name in globalThis)) {
throw new Error(
`[@vitest/web-worker] Cannot initiate a custom Web Worker. "${name}" is not supported in this environment. Please, consider using jsdom or happy-dom environment.`,
)
}
}
function createClonedMessageEvent(
data: any,
transferOrOptions: StructuredSerializeOptions | Transferable[] | undefined,
clone: CloneOption,
) {
const transfer = Array.isArray(transferOrOptions)
? transferOrOptions
: transferOrOptions?.transfer
debug('clone worker message %o', data)
const origin = typeof location === 'undefined' ? undefined : location.origin
const ports = transfer?.filter((t): t is MessagePort => t instanceof MessagePort)
View on GitHub (pinned to d568f8ce37)
Solutions
- Set the test environment to a DOM-providing one in vitest.config.ts: `test: { environment: 'happy-dom' }` (or 'jsdom').
- Install the missing environment package if not present (`npm i -D jsdom` or `npm i -D @happy-dom/global-registrator`).
- If you intentionally run in node, ensure your setup file polyfills EventTarget and MessageEvent on globalThis before calling defineWebWorkers.
- Confirm the environment name in config is spelled correctly — a typo silently falls back to node and trips this assertion.
Example fix
// before — vitest.config.ts
import { defineConfig } from 'vitest/config'
export default defineConfig({
test: { environment: 'node', setupFiles: ['@vitest/web-worker'] },
})
// after — provide EventTarget + MessageEvent via a DOM environment
import { defineConfig } from 'vitest/config'
export default defineConfig({
test: { environment: 'happy-dom', setupFiles: ['./setup.ts'] },
})
// setup.ts
import { defineWebWorkers } from '@vitest/web-worker'
defineWebWorkers() Defensive patterns
Strategy: validation
Validate before calling
// Verify the environment has the globals defineWebWorkers needs BEFORE
// importing @vitest/web-worker. Mirrors utils.ts assertGlobalExists.
function canDefineWebWorkers() {
return (
typeof globalThis !== 'undefined' &&
'EventTarget' in globalThis &&
'MessageEvent' in globalThis
)
}
if (!canDefineWebWorkers()) {
throw new Error(
'Set test.environment to happy-dom or jsdom before using @vitest/web-worker.',
)
} Prevention
- Always declare `test.environment: 'happy-dom'` (or 'jsdom') in vitest.config when tests use web workers.
- Keep `defineWebWorkers()` in a setup file that loads AFTER the DOM environment is registered.
- Add a CI guard that fails fast if the environment is 'node' while @vitest/web-worker is a dependency.
When it happens
Trigger: Calling `import { defineWebWorkers } from '@vitest/web-worker'` followed by `defineWebWorkers()` (often via the `@vitest/web-worker` browser plugin or setup file) while the test `environment` is set to 'node' or any environment that does not expose EventTarget/MessageEvent on globalThis. The check runs at setup time, so the error surfaces as soon as the web-worker plugin initializes.
Common situations: Forgetting to set `test.environment: 'happy-dom'` or `'jsdom'` in vitest.config when tests use web workers; switching a project's environment from jsdom to node to speed up tests and forgetting the worker setup; running in a minimal custom environment that polyfills fetch but not EventTarget/MessageEvent; version upgrade that moved the defineWebWorkers call earlier in setup.
Related errors
- Not called in the browser
- Vitest mocker was not initialized in this environment. vi.${
- Environment "${name}" is not a valid environment. Path "${pa
- Environment "${name}" is not a valid environment. Path "${pa
- A function to advance timers was called but the timers APIs
AI-assisted analysis of vitest-dev/vitest@d568f8ce37 (2026-08-03).
Data as JSON: /data/errors/1e58dce6ca900be2.json.
Report an issue: GitHub.