How to Migrate from Docusaurus v2 to v3: Complete Upgrade Guide
Migrating from Docusaurus v2 to v3 requires updating core packages to v3 releases, restructuring docusaurus.config.js to move themeConfig outside the preset array, replacing deprecated plugins like @docusaurus/plugin-google-analytics with @docusaurus/plugin-google-gtag, and running the automated migration CLI to handle MDX 2 compatibility and configuration updates.
Docusaurus v3 introduces breaking changes including MDX 2 support, a new bundler abstraction, and restructured configuration patterns while maintaining the zero-config philosophy. This guide walks through the complete migration process based on the official source code in the facebook/docusaurus repository, covering manual configuration updates and automated tooling.
Upgrade Core Packages to v3
The first step to migrate from Docusaurus v2 to v3 is updating your package.json dependencies to the latest v3 releases. Docusaurus v3 ships with a new bundler abstraction (docusaurus-bundler) that defaults to Webpack 5/Rspack, replacing the legacy Webpack 4 configuration from v2.
Update your core dependencies using your package manager:
yarn add @docusaurus/core@latest @docusaurus/preset-classic@latest
yarn add @docusaurus/plugin-content-docs@latest @docusaurus/plugin-content-blog@latest
The preset-classic package in v3 requires that you restructure how options are passed, while individual content plugins maintain their exported APIs but may have relocated configuration keys. After updating dependencies, delete your node_modules folder and lockfile to ensure no stale v2 packages remain.
Restructure docusaurus.config.js
The most significant configuration change when you migrate from Docusaurus v2 to v3 involves the placement of themeConfig. In v2, themeConfig lived inside the preset options array; in v3, it must be placed at the root level of the configuration object.
Move themeConfig Outside the Preset
In docusaurus.config.js, relocate the themeConfig object from inside the preset configuration to the root level:
v2 Configuration (Deprecated):
presets: [
[
'@docusaurus/preset-classic',
{
docs: { sidebarPath: require.resolve('./sidebars.js') },
theme: { customCss: require.resolve('./src/css/custom.css') },
themeConfig: {
navbar: { /* ... */ },
footer: { /* ... */ }
},
},
],
],
v3 Configuration (Current):
presets: [
[
'@docusaurus/preset-classic',
{
docs: { sidebarPath: require.resolve('./sidebars.js') },
theme: { customCss: require.resolve('./src/css/custom.css') },
},
],
],
themeConfig: {
navbar: { /* ... */ },
footer: { /* ... */ },
},
According to the migration documentation in migration-overview.mdx, this change simplifies how the classic preset merges configuration options with the theme system.
Adjust Sidebar Type Definitions
If your project uses TypeScript for sidebar definitions, update the type import for SidebarsConfig. While the structural shape of sidebars.js or sidebars.ts remains unchanged, you should verify the import source comes from the v3 version of @docusaurus/plugin-content-docs.
// sidebars.ts
import type { SidebarsConfig } from '@docusaurus/plugin-content-docs';
export const sidebars: SidebarsConfig = {
tutorialSidebar: [{ type: 'autogenerated', dirName: '.' }],
};
The sidebar migration details are documented in migration-manual.mdx, which confirms that autogenerated sidebars and explicit sidebar definitions require no structural changes during the upgrade.
Replace Deprecated Plugins and Themes
Several official plugins and themes were deprecated or restructured in v3. You must replace these before building your site.
| v2 Plugin | v3 Replacement | Configuration Changes |
|---|---|---|
@docusaurus/plugin-google-analytics |
@docusaurus/plugin-google-gtag |
Install the gtag plugin and update trackingID to gtagId |
@docusaurus/plugin-ideal-image |
Same package, updated version | Upgrade to latest version; API remains compatible |
@docusaurus/plugin-sitemap |
Still available | Verify config matches new schema; changefreq and priority remain valid |
To install the replacement for Google Analytics:
yarn add @docusaurus/plugin-google-gtag@latest
Then update your themeConfig to use the gtag key instead of the old googleAnalytics configuration.
Adapt Content for MDX 2
Docusaurus v3 upgrades the default MDX processor from v1 to v2, which enforces stricter parsing rules. Most existing content works without changes, but you must verify that React component imports follow MDX 2 syntax standards.
Remove any implicit component imports that relied on v1's magic imports feature. If you previously placed components in a components/ folder for automatic availability, you must now explicitly import them in your MDX files or register them globally via the theme configuration in docusaurus.config.js.
Front matter fields like slug, title, and description remain fully supported. The sidebar_position field is now optional, and you can use sidebar_label directly to control navigation text without additional configuration.
Execute the Automated Migration CLI
Docusaurus provides a dedicated CLI command to automate many mechanical changes when you migrate from Docusaurus v2 to v3. This tool updates package.json dependencies, rewrites configuration structures, and flags content requiring manual review.
Run the migration command from your project root:
npx @docusaurus/migrate@latest v2-to-v3 .
The automated migration performs these actions:
- Bumps all
@docusaurus/*dependencies to their latest v3 releases - Transforms
docusaurus.config.jsto the new preset layout - Adjusts plugin configurations and generates warnings for manual fixes still required
Review the generated changes with git diff before committing. The CLI implementation is documented in migration-automated.mdx.
Verify the Build and Update CI
After applying automated and manual changes, verify your site builds correctly:
yarn install
yarn build
yarn serve
Check the console for deprecation warnings during the build process. Open http://localhost:3000 to verify that documentation pages, blog posts, versioned docs, and internationalized routes render correctly.
Pay special attention to the siteUrl and baseUrl configuration—v3 enforces trailing slash policies that differ from v2 behavior, which may affect your deployment URLs.
Update your CI/CD scripts to accommodate v3 requirements:
- Use
yarn docusaurus buildexplicitly instead of legacy shortcuts - Set
NODE_OPTIONS=--max_old_space_size=4096for large sites to prevent memory exhaustion during the Webpack 5/Rspack bundling process - Verify that deployment scripts reference the correct
build/output directory, which remains unchanged from v2
Summary
- Upgrade packages to v3 releases including
@docusaurus/coreand@docusaurus/preset-classicto access the new Webpack 5/Rspack bundler - Restructure configuration by moving
themeConfigfrom inside the preset array to the root ofdocusaurus.config.js - Update sidebar types to import from the v3 version of
@docusaurus/plugin-content-docsif using TypeScript - Replace deprecated plugins such as swapping
@docusaurus/plugin-google-analyticsfor@docusaurus/plugin-google-gtag - Run the migration CLI using
npx @docusaurus/migrate@latest v2-to-v3 .to automate mechanical updates - Verify builds locally and update CI scripts to set appropriate Node memory limits for the new bundler
Frequently Asked Questions
Can I migrate from Docusaurus v2 to v3 automatically without manual changes?
The automated migration CLI handles dependency updates, configuration restructuring, and basic MDX 2 compatibility fixes. However, you must manually verify custom plugins, CSS modules, and complex React components within documentation pages. Run the CLI first, then review the generated diff to identify sections requiring manual intervention.
What breaking changes in MDX 2 affect existing documentation?
MDX 2 enforces stricter parsing compared to v1, particularly regarding HTML-like syntax inside Markdown and implicit component imports. Curly braces must be escaped when not intended as expressions, and components must be explicitly imported rather than relying on magic directory-based resolution. Most standard Markdown content works without modification.
Why was themeConfig moved outside the preset configuration in v3?
This architectural change in docusaurus.config.js separates theme-specific styling and navigation configuration from the preset's plugin orchestration. By placing themeConfig at the root level, Docusaurus v3 creates a clearer boundary between content processing (handled by presets and plugins) and presentation logic (handled by themes).
How do I handle the Google Analytics plugin deprecation during migration?
Uninstall @docusaurus/plugin-google-analytics and install @docusaurus/plugin-google-gtag@latest as its replacement. Update your themeConfig to use the gtag object with trackingID (now renamed to gtagId in some contexts) and anonymizeIP settings. This aligns with Google's migration from Universal Analytics to Google Analytics 4.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →