React plugin

The React plugin provides support for React, integrating features such as JSX compilation and React Refresh.

Quick start

Install plugin

Install the plugin using this command:

npm
yarn
pnpm
bun
npm add @rsbuild/plugin-react -D

Register plugin

Register the plugin in your rsbuild.config.ts file:

rsbuild.config.ts
import { pluginReact } from '@rsbuild/plugin-react';

export default {
  plugins: [pluginReact()],
};

After registering the plugin, you can develop React directly.

Options

swcReactOptions

Configure the behavior of SWC to transform React code, the same as SWC's jsc.transform.react option.

  • Type:
interface ReactConfig {
  pragma?: string;
  pragmaFrag?: string;
  throwIfNamespace?: boolean;
  development?: boolean;
  refresh?:
    | boolean
    | {
        refreshReg?: string;
        refreshSig?: string;
        emitFullSignatures?: boolean;
      };
  runtime?: 'automatic' | 'classic' | 'preserve';
  importSource?: string;
}
  • Default:
const isDev = process.env.NODE_ENV === 'development';
const defaultOptions = {
  development: isDev,
  refresh: isDev,
  runtime: 'automatic',
};

swcReactOptions.runtime

Decides which runtime to use when transforming JSX.

  • Type: 'automatic' | 'classic' | 'preserve'
  • Default: 'automatic'

automatic

By default, Rsbuild uses runtime: 'automatic' to leverage the new JSX runtime introduced in React 17.

This approach eliminates the need to manually import React in every file that uses JSX.

TIP

React 16.14.0 and later versions support the new JSX runtime.

classic

For React versions prior to 16.14.0, set runtime to 'classic':

pluginReact({
  swcReactOptions: {
    runtime: 'classic',
  },
});

When using the classic JSX runtime, you must manually import React in your code:

App.jsx
import React from 'react';

function App() {
  return <h1>Hello World</h1>;
}

preserve

Use runtime: 'preserve' to leave JSX syntax unchanged without transforming it, this is useful when you are building a library that expects JSX to be left as is.

pluginReact({
  swcReactOptions: {
    runtime: 'preserve',
  },
});

swcReactOptions.importSource

  • Type: string
  • Default: 'react'

With runtime set to 'automatic', you can specify the JSX runtime import path through importSource.

For example, when using Emotion, you can set importSource to '@emotion/react':

pluginReact({
  swcReactOptions: {
    importSource: '@emotion/react',
  },
});

See Customize JSX for more details.

swcReactOptions.refresh

Whether to enable React Fast Refresh.

Most of the time, you should use the plugin's fastRefresh option to enable or disable Fast Refresh.

splitChunks

When chunkSplit.strategy set to split-by-experience, Rsbuild will automatically split react and router related packages into separate chunks by default:

  • lib-react.js: includes react, react-dom, and their sub-dependencies (scheduler).
  • lib-router.js: includes react-router, react-router-dom, and their sub-dependencies (history, @remix-run/router).

This option is used to control this behavior and determine whether the react and router related packages need to be split into separate chunks.

  • Type:
type SplitReactChunkOptions = {
  react?: boolean;
  router?: boolean;
};
  • Default:
const defaultOptions = {
  react: true,
  router: true,
};
  • Example:
pluginReact({
  splitChunks: {
    react: false,
    router: false,
  },
});

enableProfiler

  • Type: boolean
  • Default: false

When set to true, enables the React Profiler for performance analysis in production builds. Use the React DevTools to examine profiling results and identify potential performance optimizations. Profiling adds a slight overhead, so it is disabled by default in production mode.

rsbuild.config.ts
pluginReact({
  // Only enable the profiler when REACT_PROFILER is true,
  // as the option will increase the build time and add some small additional overhead.
  enableProfiler: process.env.REACT_PROFILER === 'true',
});

Set REACT_PROFILER=true when running build script:

package.json
{
  "scripts": {
    "build:profiler": "REACT_PROFILER=true rsbuild build"
  }
}

As Windows does not support the above usage, you can also use cross-env to set environment variables. This ensures compatibility across different systems:

package.json
{
  "scripts": {
    "build:profiler": "cross-env REACT_PROFILER=true rsbuild build"
  },
  "devDependencies": {
    "cross-env": "^7.0.0"
  }
}

See the React docs for details about profiling using the React DevTools.

reactRefreshOptions

  • Type:
type ReactRefreshOptions = {
  // @link https://rspack.rs/config/module#condition
  test?: Rspack.RuleSetCondition;
  include?: Rspack.RuleSetCondition;
  exclude?: Rspack.RuleSetCondition;
  library?: string;
  forceEnable?: boolean;
};
  • Default:
const defaultOptions = {
  test: [/\.(?:js|jsx|mjs|cjs|ts|tsx|mts|cts)$/],
  include: [
    // Same as Rsbuild's `source.include` configuration
  ],
  exclude: [
    // Same as Rsbuild's `source.exclude` configuration
  ],
  resourceQuery: { not: /^\?raw$/ },
};

Set the options for @rspack/plugin-react-refresh. The passed value will be shallowly merged with the default value.

  • Example:
pluginReact({
  reactRefreshOptions: {
    exclude: [/some-module-to-exclude/, /[\\/]node_modules[\\/]/],
  },
});

fastRefresh

  • Type: boolean
  • Default: true

Whether to enable React Fast Refresh in development mode.

If fastRefresh is set to true, @rsbuild/plugin-react will automatically register the @rspack/plugin-react-refresh plugin.

To disable Fast Refresh, set it to false:

pluginReact({
  fastRefresh: false,
});