diff --git a/README.md b/README.md index 5e5d2f7..836278c 100644 --- a/README.md +++ b/README.md @@ -1,37 +1,141 @@ -# Module Federation Runtime Chunk Merging +# Module Federation For Next.js -This plugin makes module federation work as expected when using -`runtimeChunk:"single"` as an optimization tactic. +This plugin enables Module Federation on Next.js -## Usage +This is a workaround to hard limitations caused by Next.js being synchronous. + +I am working on an update to Webpack Core which will circumvent projects with older architecture (like Next.js). + +This is a stable and viable workaround to leverage Module Federation [until this issue is resolved](https://github.com/webpack/webpack/issues/11811). + +### Supports + +- next ^9.5.6 +- SSG +- SSR + +**Once I PR webpack, this workaround will no longer be required.** + +# Check out our book + +| Practical Module Federation Book | We will be actively updating this book over the next year as we learn more about best practices and what issues people are running into with Module Federation, as well as with every release of Webpack as it moves towards a release candidate and release. So with your one purchase you are buying a whole year of updates. | +| --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | + +#### Demo + +You can see it in action here: https://github.com/module-federation/module-federation-examples/tree/master/nextjs + +## How to use on a fresh nextjs app + +```sh +yarn global add @module-federation/nextjs-mf +``` + +Run this inside of a fresh nextjs install. + +```sh +nextjs-mf upgrade -p 3001 +``` + +## How to use on an existing app + +1. Use `withModuleFederation` in your `next.config.js` ```js -plugins: [ - new ModuleFedSingleRuntimePlugin(), - new ModuleFederationPlugin({ - name: "app2", - filename: "remoteEntry.js", +// next.config.js +const { withModuleFederation } = require("@module-federation/nextjs-mf"); +const path = require("path"); + +module.exports = { + webpack: (config, options) => { + const { buildId, dev, isServer, defaultLoaders, webpack } = options; + const mfConf = { + mergeRuntime: true, //this is experimental, read below + name: "next2", + library: { type: config.output.libraryTarget, name: "next2" }, + filename: "static/runtime/remoteEntry.js", + remotes: { + // For SSR, resolve to disk path (or you can use code streaming if you have access) + next1: isServer + ? path.resolve( + __dirname, + "../next1/.next/server/static/runtime/remoteEntry.js" + ) + : "next1", // for client, treat it as a global + }, exposes: { - "./Button": "./src/Button", + "./nav": "./components/nav", }, - shared: { react: { singleton: true }, "react-dom": { singleton: true } }, - }), - new HtmlWebpackPlugin({ - template: "./public/index.html", - }), - ] + shared: ["lodash"], + }; + // Configures ModuleFederation and other Webpack properties + withModuleFederation(config, options, mfConf); + + return config; + }, +}; ``` -# Example +2. Add the `patchSharing` to `_document.js`. This will solve the react sharing issue. -Can be found in the `/example` directory +```jsx +import Document, { Html, Head, Main, NextScript } from "next/document"; +import { patchSharing } from "@module-federation/nextjs-mf"; +class MyDocument extends Document { + static async getInitialProps(ctx) { + const initialProps = await Document.getInitialProps(ctx); + return { ...initialProps }; + } + render() { + return ( + + {patchSharing()} +