Skip to content

Prerender fails with nitro vercel preset - runtime.node undefined in srvx #6562

@LeonardoTrapani

Description

@LeonardoTrapani

Which project does this relate to?

Start

Describe the bug

When using TanStack Start with nitro's vercel preset and prerender enabled, the build fails during the prerender phase. The preview server starts successfully via srvx, but when attempting to fetch pages for prerendering, srvx throws a TypeError because this.runtime.node is undefined.

This happens because nitro's vercel preset generates serverless function output designed for Vercel's runtime environment. The prerender step uses srvx to start a local Node.js preview server, but srvx's Node adapter expects this.runtime.node to exist - which it doesn't when running Vercel-formatted functions locally.

Your Example Website or App

Minimal vite.config.ts to reproduce:

import { defineConfig } from 'vite'
import { tanstackStart } from '@tanstack/react-start/plugin/vite'
import { nitro } from 'nitro/vite'
import react from '@vitejs/plugin-react'

export default defineConfig({
  plugins: [
    tanstackStart({
      prerender: {
        enabled: true,
      },
    }),
    nitro({ preset: 'vercel' }),
    react(),
  ],
})

Steps to Reproduce the Bug or Issue

  1. Create a TanStack Start project
  2. Install nitro nightly: npm add nitro@npm:nitro-nightly@latest
  3. Configure vite.config.ts with:
    • nitro({ preset: 'vercel' })
    • tanstackStart({ prerender: { enabled: true } })
  4. Run vite build

Expected behavior

Build should complete successfully, either by:

  • Prerendering pages correctly, or
  • Detecting serverless preset and skipping prerender with a warning

Actual behavior

Build fails during prerender with:

ℹ Spawning preview server...
ℹ npx srvx --static ../../static ./functions/__server.func/index.mjs

➜ Listening on: http://localhost:36889/ (all interfaces)
[prerender] Concurrency: 14
[prerender] Crawling: /
TypeError: Cannot destructure property 'req' of 'this.runtime.node' as it is undefined.
    at get _abortController (file:///project/node_modules/srvx/dist/adapters/node.mjs:210:13)
    at get signal (file:///project/node_modules/srvx/dist/adapters/node.mjs:225:55)
    at renderRouterToStream (file:///project/.vercel/output/functions/__server.func/_chunks/_libs/@tanstack/react-router.mjs:506:23)
    ...

[prerender] Prerendered 0 pages:
Error: Failed to fetch /: Internal Server Error
    at file:///project/node_modules/@tanstack/start-plugin-core/dist/esm/prerender.js:137:19

Screenshots or Videos

N/A

Platform

  • TanStack Start Version: 1.157.18
  • nitro Version: 3.0.1-20260131-134752-eea737f2 (nightly)
  • OS: Linux
  • Node: v25.0.0
  • Bundler: vite 7.3.1

Additional context

Root cause analysis:

The nitro vercel preset outputs to .vercel/output/functions/__server.func/ which is designed for Vercel's serverless runtime. When prerender starts a preview server via srvx (npx srvx --static ../../static .vercel/output/functions/__server.func/index.mjs), the srvx Node adapter tries to access this.runtime.node.req for the abort controller, but the runtime context doesn't exist because the function wasn't invoked through Vercel's runtime.

The key issue is that srvx assumes a Node.js runtime context, but Vercel-preset output expects Vercel's serverless runtime context.

Workaround:

Disable prerender when using the vercel preset:

tanstackStart({
  prerender: {
    enabled: false,
  },
}),
nitro({ preset: 'vercel' }),

Vercel handles SSR dynamically at request time, so prerender isn't strictly necessary.

Possible solutions:

  1. Detect vercel/cloudflare/serverless presets and automatically skip prerender (or warn)
  2. Use a node-compatible build for prerender, then switch to vercel preset for final output
  3. Document that prerender is incompatible with serverless presets

Related issues:

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions