Describe the bug
For SSR builds with ssr.target: 'webworker', Vite still defaults build.rolldownOptions.platform to 'node' for every server build. This causes Rolldown to emit createRequire(import.meta.url) for CJS interop, which crashes on Cloudflare Workers / workerd because import.meta.url is undefined in bundled worker modules.
The worker fails during module initialization before any request is handled:
TypeError: The argument 'path' must be a file URL object, a file URL string,
or an absolute path string. Received 'undefined'
at createRequire (node:module:34:15)
at null.<anonymous> (jsx-runtime.mjs:34:33)
Vite already treats ssr.target === 'webworker' as a special case elsewhere — ssr.resolve.conditions defaults to webworker/browser-style conditions, resolveEnvironmentOptions() threads isSsrTargetWebworkerEnvironment into resolve + keepProcessEnv, and resolveRolldownOptions() special-cases SSR webworker output defaults. But resolveBuildEnvironmentOptions() still hard-defaults all server builds to platform: 'node'.
We intend to submit a PR for this — see #21963 (currently draft).
Reproduction
This does not require Nitro / TanStack / a framework. A plain Vite SSR repro:
vite.config.js
import { defineConfig, defaultClientConditions } from 'vite'
export default defineConfig({
build: { minify: false },
ssr: {
target: 'webworker',
noExternal: true,
external: ['node:assert'],
resolve: {
conditions: [...defaultClientConditions, 'worker'],
},
},
})
dep-cjs-node-assert/package.json
{ "name": "dep-cjs-node-assert", "private": true, "main": "index.cjs" }
dep-cjs-node-assert/index.cjs
const { ok } = require('node:assert')
ok(true)
module.exports = 'cjs-ok'
src/entry-worker.js
import msg from 'dep-cjs-node-assert'
addEventListener('fetch', (event) => {
event.respondWith(new Response(msg))
})
Steps to reproduce
- Set up the files above (or use the existing
playground/ssr-webworker with a CJS fixture added)
- Run
vite build
- Inspect the output:
grep "createRequire" dist/entry-worker.js — it contains createRequire(import.meta.url)
- Run under a worker runtime:
npx wrangler dev dist/entry-worker.js — crashes at startup
System Info
System:
OS: macOS 15.5 (Darwin 24.6.0)
CPU: Apple M3 Max
Memory: 36 GB
Binaries:
Node: 22.14.0
pnpm: 10.32.1
bun: 1.3.2
npmPackages:
vite: npm:rolldown-vite@^7.3.1 => 7.3.1
rolldown: 1.0.0-rc.10
Used Package Manager
pnpm
Logs
Click to expand!
# Build output contains createRequire:
$ grep "createRequire" .output/server/_chunks/jsx-runtime.mjs
import { createRequire } from "node:module";
var __require = /* @__PURE__ */ createRequire(import.meta.url);
# Worker crashes at startup:
$ wrangler dev .output/server/index.mjs
TypeError: The argument 'path' must be a file URL object, a file URL string,
or an absolute path string. Received 'undefined'
at createRequire (node:module:34:15)
at null.<anonymous> (jsx-runtime.mjs:34:33)
Validations
Describe the bug
For SSR builds with
ssr.target: 'webworker', Vite still defaultsbuild.rolldownOptions.platformto'node'for every server build. This causes Rolldown to emitcreateRequire(import.meta.url)for CJS interop, which crashes on Cloudflare Workers /workerdbecauseimport.meta.urlisundefinedin bundled worker modules.The worker fails during module initialization before any request is handled:
Vite already treats
ssr.target === 'webworker'as a special case elsewhere —ssr.resolve.conditionsdefaults to webworker/browser-style conditions,resolveEnvironmentOptions()threadsisSsrTargetWebworkerEnvironmentinto resolve +keepProcessEnv, andresolveRolldownOptions()special-cases SSR webworker output defaults. ButresolveBuildEnvironmentOptions()still hard-defaults all server builds toplatform: 'node'.We intend to submit a PR for this — see #21963 (currently draft).
Reproduction
This does not require Nitro / TanStack / a framework. A plain Vite SSR repro:
vite.config.js
dep-cjs-node-assert/package.json
{ "name": "dep-cjs-node-assert", "private": true, "main": "index.cjs" }dep-cjs-node-assert/index.cjs
src/entry-worker.js
Steps to reproduce
playground/ssr-webworkerwith a CJS fixture added)vite buildgrep "createRequire" dist/entry-worker.js— it containscreateRequire(import.meta.url)npx wrangler dev dist/entry-worker.js— crashes at startupSystem Info
System: OS: macOS 15.5 (Darwin 24.6.0) CPU: Apple M3 Max Memory: 36 GB Binaries: Node: 22.14.0 pnpm: 10.32.1 bun: 1.3.2 npmPackages: vite: npm:rolldown-vite@^7.3.1 => 7.3.1 rolldown: 1.0.0-rc.10Used Package Manager
pnpm
Logs
Click to expand!
Validations