> For AI agents: the complete documentation index is available at /llms.txt, the full documentation bundle is available at /llms-full.txt.

# ModuleFederationPlugin

`ModuleFederationPlugin` enables Module Federation in Rspack.

This plugin implements the Module Federation 1.5 specification. If you want to learn more about the core concepts, usage, and best practices of Module Federation, please refer to the [Module Federation Guide](/guide/advanced/module-federation.md).

## Install dependencies

This plugin depends on the runtime package [@module-federation/runtime-tools](https://www.npmjs.com/package/@module-federation/runtime-tools), which provides runtime support for Module Federation. Please install it first:


```sh [npm]
npm add @module-federation/runtime-tools
```

```sh [yarn]
yarn add @module-federation/runtime-tools
```

```sh [pnpm]
pnpm add @module-federation/runtime-tools
```

```sh [bun]
bun add @module-federation/runtime-tools
```

```sh [deno]
deno add npm:@module-federation/runtime-tools
```

## Examples

```js title="rspack.config.mjs"
import { rspack } from '@rspack/core';

export default {
  output: {
    // set uniqueName explicitly to make HMR works
    uniqueName: 'app',
  },
  plugins: [
    new rspack.container.ModuleFederationPlugin({
      name: 'app',
    }),
  ],
};
```

## Options

### implementation

- Type: `string`

Provide a path as the implementation for Module Federation 1.5 runtime, which defaults to [@module-federation/runtime-tools](https://github.com/module-federation/universe/tree/main/packages/runtime-tools).

### runtimePlugins

- Type:
  ```ts
  type RuntimePlugins =
    string[] | [plugin: string, options: Record<string, unknown>][];
  ```

Provide the plugins required to run Module Federation 1.5, which can extend its behavior and capabilities. Use an array of module paths, or an array of `[modulePath, options]` tuples when a plugin needs options.

### name

- Type: `string`

Define the unique name exposed to other containers in the current build. This name will exist as a global variable for the remote container.

The `name` option must be a non-empty string when exposing modules or enabling `shared.treeShaking`. Otherwise, you can omit `name`; the Module Federation runtime uses [`output.uniqueName`](/config/output.md#outputuniquename) instead.

### filename

- Type: `string`

Specify the filename of the remote container entry file. Other containers will load the exposed modules through this file.

### runtime

- Type: `string | false`

Define the runtime chunk for remote container entry.

### library

- Type: [`LibraryOptions`](/config/output.md#outputlibrary)

Define the output format of remote container entry. The default libraryType is "var".

### shareScope

- Type: `string | string[]`

Define the namespace for shared dependencies in the current container. By configuring share scopes between different containers, the sharing behavior of modules can be controlled, including determining which modules are shared between different containers. The default share scope is `"default"`.

### shareStrategy

- Type: `'version-first' | 'loaded-first'`

Control the loading strategy of shared dependencies:

- `'version-first'`: Version takes precedence. After setting, all _remotes_ entry files will be automatically loaded and **register** the corresponding shared dependencies to ensure that all shared dependency versions can be obtained. This strategy is recommended when there are strict version requirements.

- `'loaded-first'`: reuse first. After setting, the _remotes_ entry file will not be automatically loaded (it will only be loaded when needed), and registered shared dependencies will be reused first. This strategy is recommended when there are no strict requirements on the version and performance is required.

### remoteType

- Type: [`ExternalsType`](/config/externals.md#externalstype)

Defines how to load remote containers, defaulting to `"script"`, which loads via the `<script />` tag.

### remotes

- Type:
  ```ts
  type Remotes = (RemotesItem | RemotesObject)[] | RemotesObject;
  type RemotesItem = string;
  type RemotesItems = RemotesItem[];
  type ShareScope = string | string[];
  interface RemotesObject {
    [k: string]: RemotesConfig | RemotesItem | RemotesItems;
  }
  interface RemotesConfig {
    external: RemotesItem | RemotesItems;
    shareScope?: ShareScope;
  }
  ```

Definition of the modules and their addresses that will be loaded remotely. The key is the name of the remote container, the value is the global variable name exposed by the remote container and the URL of the remote container entry. You can also specify shareScope to control whether the remote container shares dependencies.

### exposes

- Type:
  ```ts
  type Exposes = (ExposesItem | ExposesObject)[] | ExposesObject;
  type ExposesItem = string;
  type ExposesItems = ExposesItem[];
  interface ExposesObject {
    [k: string]: ExposesConfig | ExposesItem | ExposesItems;
  }
  interface ExposesConfig {
    import: ExposesItem | ExposesItems;
    name?: string;
  }
  ```

Define how local modules can be referenced by remote containers. The key is the name of the module when referenced as a remote module in the remote container, and the value is the module path relative to the current folder. You can provide a name to specify the name of the exposed local module.

### shared

- Type:
  ```ts
  type Shared = (SharedItem | SharedObject)[] | SharedObject;
  type SharedItem = string;
  type ShareScope = string | string[];
  interface TreeShakingConfig {
    usedExports?: string[];
    mode?: 'server-calc' | 'runtime-infer';
    filename?: string;
  }
  interface SharedObject {
    [k: string]: SharedConfig | SharedItem;
  }
  interface SharedConfig {
    import?: false | SharedItem;
    eager?: boolean;
    packageName?: string;
    requiredVersion?: false | string;
    shareKey?: string;
    shareScope?: ShareScope;
    singleton?: boolean;
    strictVersion?: boolean;
    version?: false | string;
    treeShaking?: TreeShakingConfig;
  }
  ```

Specify which dependencies should be shared dependencies. This allows multiple micro-frontends to share the same instance of a dependency library to avoid loading the same code repeatedly. It can be an object dictionary where the keys are the names of the shared modules and the values are configuration or version strings. It can also be an array where the array items are the shared package names or configurations.

The SharedConfig can include the following sub-options:

- import: Module that should be placed in the share scope of the shared module. If the shared module cannot be found in the share scope of the shared module or the version is invalid, this provided module can be used as a fallback module.
- eager: If set to `true`, the shared module will be loaded in the initial chunk instead of being dynamically loaded when used. This means that the shared module will be loaded together with the main entry point regardless of whether it has been used. This can eliminate the delay caused by dynamic loading, but it will increase the size of the initial package. Also, please note that when this configuration is enabled, all provided modules and fallback modules will always be downloaded.
- packageName: Used to determine the package name and required version from `package.json`. Configuration is only necessary when the package name cannot be automatically determined based on the request.
- requiredVersion: Accepts semantic version number. For example, `"^1.2.3"`. Used to set the version range of shared modules. If the module version of the remote container does not meet this range, the module will not be loaded.
- shareKey: Use this key to search for the requested shared module in the share scope of the shared module. The default is the name of the shared module.
- shareScope: Define the share scope of the shared module. This allows different builds to use their own share scope independently without conflict. The default share scope is `"default"`.
- singleton: Ensure that shared modules are only loaded once between different versions, following the singleton pattern. This is necessary for libraries designed to run as singletons, such as React, as it can prevent various issues caused by instantiating multiple library instances.
- strictVersion: Used to strengthen `requiredVersion`. If set to `true`, the shared module must match the version specified in requiredVersion exactly, otherwise an error will be reported and the module will not be loaded. If set to `false`, it can tolerate imprecise matching.
- version: Explicitly set the version of the shared module. By default, the version in `package.json` will be used.
- treeShaking: Configure the treeshaking behavior of shared dependencies. By enabling treeshaking for shared dependencies, the size of shared dependencies can be reduced. Only effective when using Rspack as the build tool.
  - usedExports: Manually **add** export members used by shared dependencies.
  - mode: Configure the loading strategy for treeshaking.
    - `runtime-infer`: Infer based on the consumer's `usedExports`. If the provider's `usedExports` match the consumer's `usedExports`, the provider's `shared` will be used; otherwise, the consumer's own `shared` will be used. If neither condition is met, the full version is used.
    - `server-calc`: Decide whether to load shared dependencies based on the snapshot sent by the server.
  - filename: Customize the filename of the generated shared fallback entry.

### manifest


[Added in v1.6.1](https://github.com/web-infra-dev/rspack/releases/tag/v1.6.1)

- Type:
  ```ts
  type Manifest = boolean | ManifestConfig;
  interface ManifestConfig {
    filePath?: string;
    disableAssetsAnalyze?: boolean;
    fileName?: string;
  }
  ```

Used to control whether to generate a manifest and the corresponding generation configuration.

When enabled, the plugin emits both `mf-manifest.json` and `mf-stats.json` (you can customize the base name through `fileName`) on every build and writes them into the build output so other tooling can read them during the `processAssets` hook or from the final artifacts.

- `mf-stats.json`: Contains full build statistics, including the asset lists for exposes/shared/remotes, `metaData` (plugin version, build info, `remoteEntry`, etc.), and extra asset analysis data, making it suitable for later aggregation or diagnostics.
- `mf-manifest.json`: A runtime manifest distilled from the stats file. The structure stays stable and can be consumed by Module Federation clients when loading remote modules. The exposes/shared/remotes sections describe what is publicly exposed.

`ManifestConfig` provides the following options:

- `filePath`: Target directory for the manifest files. Applies to both manifest and stats outputs.
- `fileName`: Manifest file name. When set, the stats file automatically appends a `-stats` suffix (for example, `fileName: 'mf.json'` produces `mf.json` and `mf-stats.json`). All files are emitted into the directory defined by `filePath` (if provided).
- `disableAssetsAnalyze`: Disables asset analysis. When `true`, the manifest omits the `shared` and `exposes` fields, and the `remotes` entries will not include asset information.

### injectTreeShakingUsedExports


[Added in v2.0.0](https://github.com/web-infra-dev/rspack/releases/tag/v2.0.0)

Whether to inject the exports used by shared into the bundler runtime.

- Type: `boolean`
- Required: No
- Default: `true`

This option is used to control whether to inject the actual used export information of shared modules into the bundler runtime for more precise dependency management and optimization.

If you are using mode as 'server-calc', it is recommended to set this option to `false`.

### treeShakingSharedDir

Directory for outputting tree shaking shared fallback resources.

- Type: `string`
- Required: No
- Default: `'independent-packages'`

When shared dependency tree shaking is enabled, Module Federation splits unused shared module exports. This option specifies the output directory for these fallback resources.

### treeShakingSharedExcludePlugins

Configure additional plugin names to exclude during the shared dependency tree shaking/fallback build process.

- Type: `string[]`
- Required: No
- Default: `[]`

Rspack already excludes its Module Federation and tree-shaking helper plugins, as well as common HTML plugins. Use this option to add more plugin names to that exclusion list.

### treeShakingSharedPlugins

Allows users to explicitly specify which plugins should participate in the second treeshaking process for shared modules.

- Type: `string[]`
- Required: No
- Default: `undefined`

If `shared.treeShaking.mode` is set to 'server-calc', then in the deployment service, the shared dependencies that need tree shaking will be rebuilt. At this time, only shared dependencies are built, and the original project's build configuration will not be loaded.
If your project has special build configurations, such as setting externals, you can integrate these build configurations into an NPM Package, and then fill in the name and version of this plugin in `treeShakingSharedPlugins`, so that it can participate in the treeshaking process of shared modules in the second treeshaking process.

For example, a plugin `my-build-plugin` is provided, which sets `externals`:

```ts title='my-build-plugin'
class MyBuildPlugin {
  apply(compiler) {
    compiler.options.externals = {
      react: 'React',
    };
  }
}
export default MyBuildPlugin;
```

Publish this plugin version as `0.0.2`, then you only need to fill in the plugin name and version in `treeShakingSharedPlugins`:

```ts title='module-federation.config.ts'
export default {
  // ...
  treeShakingSharedPlugins: ['my-build-plugin@0.0.2'],
};
```

## FAQ

- Found non-downgraded syntax in the build output?

  If you need to be compatible with legacy browsers, please add [builtin:swc-loader](/guide/features/builtin-swc-loader.md) for syntax downgrade, and make sure it matches packages under `@module-federation` scope. Here is an example:

  ```js title="rspack.config.mjs"
  export default {
    module: {
      rules: [
        {
          include: [/@module-federation[\\/]/],
          use: {
            loader: 'builtin:swc-loader',
            options: {
              jsc: {
                target: 'es5',
              },
            },
          },
        },
      ],
    },
  };
  ```

- Multiple assets emit different content to the same filename mf-manifest.json

  Upgrade the `@module-federation` scoped npm package to `0.21.0` or above.
