remix-run/react-router · error · Error

React Router Vite plugin not found in Vite config

Error message

React Router Vite plugin not found in Vite config

What it means

React Router's build orchestration (`react-router build`) resolves your Vite config and then verifies that the React Router Vite plugin (name `react-router` or `react-router/rsc`) is present in the resolved plugin list. Without that plugin, the framework cannot discover routes, run the SSR/SSG compilers, or inject the virtual modules the app relies on, so the build aborts immediately. It is a fail-fast guard against running the React Router CLI against a plain Vite project.

Solutions

  1. Add the React Router Vite plugin to vite.config.ts: `import { reactRouter } from '@react-router/dev/vite';` and include `reactRouter()` in the `plugins` array
  2. Verify no conditional logic (env checks, mode checks) removes the plugin from the array used for builds
  3. Confirm the plugin is instantiated exactly once and is not renamed/wrapped by another plugin wrapper
  4. If you intended a plain Vite app, invoke `vite build` instead of `react-router build`

Example fix

// before (vite.config.ts)
import { defineConfig } from 'vite';
export default defineConfig({ plugins: [] });

// after
import { defineConfig } from 'vite';
import { reactRouter } from '@react-router/dev/vite';
export default defineConfig({
  plugins: [reactRouter()],
});
Defensive patterns

Strategy: validation

Validate before calling

// vite.config.ts — assert the plugin is present before building
import { reactRouter } from '@react-router/dev/vite';
const plugins = [reactRouter()];
if (!plugins.some((p) => p && 'name' in p && (p.name === 'react-router' || p.name === 'react-router/rsc'))) {
  throw new Error('reactRouter() plugin missing from config');
}
export default defineConfig({ plugins });

Type guard

const hasReactRouterPlugin = (plugins: unknown[]): boolean =>
  plugins.some(
    (p): p is { name: string } =>
      !!p &&
      typeof p === 'object' &&
      'name' in p &&
      ((p as { name: unknown }).name === 'react-router' ||
       (p as { name: unknown }).name === 'react-router/rsc'),
  );

Try / catch

try {
  await exec('react-router build');
} catch (e) {
  if (e instanceof Error && /not found in Vite config/.test(e.message)) {
    failBuild('vite.config.ts must include reactRouter() from @react-router/dev/vite');
  }
  throw e;
}

Prevention

When it happens

Trigger: Running `react-router build` (or calling the build API in packages/react-router-dev/vite/build.ts) when vite.config.ts does not include `reactRouter()` from `@react-router/dev/vite`; the plugin is added conditionally (e.g. only when an env var is set) so it resolves to absent; the plugin is wrapped/renamed by another wrapper so its `name` is no longer `react-router` or `react-router/rsc`.

Common situations: Migrating a Vite SPA to React Router Framework Mode but forgetting the plugin; mixing up `vite build` vs `react-router build` in a monorepo script; a config factory that skips the plugin for `mode === 'development'`; upgrading templates where the plugin import moved from `@react-router/dev/vite` to a different package.

Related errors


AI-assisted analysis of remix-run/react-router@6beaca3952 (2026-08-18). Data as JSON: /api/errors/5e3d2ce780ac1ff5. Report an issue: GitHub.

Appendix: source

Thrown at packages/react-router-dev/vite/build.ts:74

              },
            };
          }
          if (sourcemapServer && name !== "client") {
            return {
              build: {
                sourcemap: sourcemapServer,
              },
            };
          }
        },
        configResolved(config) {
          let hasReactRouterPlugin = config.plugins.find(
            (plugin) =>
              plugin.name === "react-router" ||
              plugin.name === "react-router/rsc",
          );
          if (!hasReactRouterPlugin) {
            throw new Error(
              "React Router Vite plugin not found in Vite config",
            );
          }
        },
      },
    ],
  });
  await builder.buildApp();
}

View on GitHub (pinned to 6beaca3952)