vitest-dev/vitest · error · Error
Can't find browser origin URL for project "${this.name}"
Error message
Can't find browser origin URL for project "${this.name}" What it means
After confirming the browser exists, _openBrowserPage (project.ts:472-477) reads browser.vite.resolvedUrls to get the local or network origin. If both local[] and network[] are empty/undefined the test page URL cannot be constructed, so Vitest throws. This means the underlying Vite dev server never resolved its listening URLs.
Source
Thrown at packages/vitest/src/node/project.ts:475
/** @internal */
public _getViteEnvironments(): DevEnvironment[] {
return Object.values(this.vite.environments || {})
}
/** @internal */
public async _openBrowserPage(sessionId: string, pool: {
reject: (error: Error) => void
parallel?: boolean
}): Promise<void> {
if (!this.browser) {
throw new Error(`browser is not initialized`)
}
const resolvedUrls = this.browser.vite.resolvedUrls
const origin = resolvedUrls?.local[0] ?? resolvedUrls?.network[0]
if (!origin) {
throw new Error(
`Can't find browser origin URL for project "${this.name}"`,
)
}
const url = new URL('/__vitest_test__/', origin)
url.searchParams.set('sessionId', sessionId)
const otelCarrier = this.vitest._traces.getContextCarrier()
this.vitest._browserSessions.sessionIds.add(sessionId)
const sessionPromise = this.vitest._browserSessions.createSession(
sessionId,
this,
pool,
{ otelCarrier },
)
const pagePromise = this.browser.provider.openPage(
sessionId,
url.toString(),
{ parallel: pool.parallel ?? false },View on GitHub (pinned to d568f8ce37)
Solutions
- Check the earlier server-start logs for an EADDRINUSE or listen error and free/switch the port (server.port or browser config).
- Ensure the Vite server is not closed/recreated between provider init and the first browser test.
- If using a custom server factory, verify it populates resolvedUrls.local.
- Run vitest with --no-watch and a single worker to rule out a restart race.
Example fix
// before
export default defineConfig({
test: { browser: { enabled: true, provider: 'playwright', instances: [{ browser: 'chromium' }] } },
server: { port: 5173 }, // collides
})
// after
export default defineConfig({
test: { browser: { enabled: true, provider: 'playwright', instances: [{ browser: 'chromium' }] } },
server: { port: 0 }, // let vitest pick a free port
}) Defensive patterns
Strategy: validation
Validate before calling
const urls = project.browser?.vite?.resolvedUrls
const origin = urls?.local?.[0] ?? urls?.network?.[0]
if (!origin) throw new Error('Vite server has no resolved URL; check port availability') Type guard
function hasOrigin(urls: { local?: string[]; network?: string[] } | undefined): urls is { local: string[] } | { network: string[] } {
return !!(urls?.local?.length || urls?.network?.length)
} Prevention
- Use server.port: 0 to avoid port conflicts.
- Don't close/recreate the Vite server between init and browser tests.
- Ensure the environment allows binding a port (CI sandboxing, permissions).
When it happens
Trigger: The Vite dev server failed to bind a port (port in use, permission denied), the server was closed before the browser page opened, or server.resolvedUrls was reset. Also possible when a custom middleware/plugin clears resolvedUrls.
Common situations: Port 5173 (or configured port) already in use by another process; running in a CI sandbox that blocks the listen syscall; race condition closing the server between init and the first browser test; running headless without network permissions.
Related errors
- Cannot take a screenshot without a test path
- Element not found: ${v.element}
- The ${provider.name} provider does not support tracing.
- stopChunkTrace cannot be called outside of the test file.
- The ${context.provider.name} provider does not support traci
AI-assisted analysis of vitest-dev/vitest@d568f8ce37 (2026-08-03).
Data as JSON: /data/errors/7e3aa7aa474873a1.json.
Report an issue: GitHub.