Skip to content

Commit

Permalink
refactor mdx plugin docs
Browse files Browse the repository at this point in the history
  • Loading branch information
slorber committed Oct 13, 2023
1 parent dd40aea commit 729b6f8
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 22 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -362,13 +362,22 @@ console.log('hello');

All the official packages (Unified, Remark, Rehype...) in the MDX ecosystem are now [**ES Modules only**](https://gist.github.com/sindresorhus/a39789f98801d908bbc7ff3ecc99d99c) and do not support [CommonJS](https://nodejs.org/api/modules.html#modules-commonjs-modules) anymore.

In practice this means that you can't do `require("remark-plugin")` anymore. Unfortunately the Docusaurus config file only supports CommonJS at the moment, and you can't use `import MyRemarkPlugin from "remark-plugin"`.
In practice this means that you can't do `require("remark-plugin")` anymore.

:::tip How to prepare

Using dynamic imports is a good workaround that enables you to import ES modules inside a CommonJS module. Fortunately, the [Docusaurus config supports the usage of an async function](/docs/configuration#syntax-to-declare-docusaurus-config) to let you do so.
Docusaurus v3 now supports [**ES Modules**](https://flaviocopes.com/es-modules/) configuration files. We recommend that you migrate your config file to ES module, that enables you to import the Remark plugins easily:

You can start refactoring your config to use **async dynamic imports** today. Refer to the [MDX plugin installation documentation](/docs/3.0.0-beta.0/markdown-features/plugins#installing-plugins) for details.
```js title="docusaurus.config.js"
import remarkPlugin from 'remark-plugin';

export default {
title: 'Docusaurus',
/* site config using remark plugins here */
};
```

If you want to keep using CommonJS modules, you can use dynamic imports as a workaround that enables you to import ES modules inside a CommonJS module. Fortunately, the [Docusaurus config supports the usage of an async function](/docs/configuration#syntax-to-declare-docusaurus-config) to let you do so.

```js title="docusaurus.config.js"
module.exports = async function () {
Expand Down
2 changes: 1 addition & 1 deletion website/docs/advanced/architecture.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ This diagram shows how Docusaurus works to build your app. Plugins each collect

Although you (either plugin authors or site creators) are writing JavaScript all the time, bear in mind that the JS is actually run in different environments:

- All plugin lifecycle methods are run in Node. Therefore, until we support ES Modules in our codebase, plugin source code must be provided as CommonJS that can be `require`'d.
- All plugin lifecycle methods are run in Node. Therefore, until we support ES Modules in our codebase, plugin source code must be provided as ES modules that can be imported, or CommonJS that can be `require`'d.
- The theme code is built with Webpack. They can be provided as ESM—following React conventions.

Plugin code and theme code never directly import each other: they only communicate through protocols (in our case, through JSON temp files and calls to `addRoute`). A useful mental model is to imagine that the plugins are not written in JavaScript, but in another language like Rust. The only way to interact with plugins for the user is through `docusaurus.config.js`, which itself is run in Node (hence you can use `require` and pass callbacks as plugin options).
Expand Down
68 changes: 50 additions & 18 deletions website/docs/guides/markdown-features/markdown-features-plugins.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -59,11 +59,41 @@ Next, the `rehype-katex` operates on the Hypertext AST where everything has been

:::warning

Many official Remark/Rehype plugins are using ES Modules, a new JavaScript module system, which Docusaurus doesn't support yet. To work around this issue, we recommend to use dynamic `import()` inside an `async` config creation function.
Many official Remark/Rehype plugins are [**ES Modules only**](https://gist.github.com/sindresorhus/a39789f98801d908bbc7ff3ecc99d99c), a JavaScript module system, which Docusaurus supports. We recommend using an [**ES Modules**](https://flaviocopes.com/es-modules/) config file to make it easier to import such packages.

:::

Next, add them to the plugin options through plugin or preset config in `docusaurus.config.js`, using dynamic `import()`:
Next, import your plugins and add them to the plugin options through plugin or preset config in `docusaurus.config.js`:

```js title="docusaurus.config.js"
// highlight-start
import remarkMath from 'remark-math';
import rehypeKatex from 'rehype-katex';
// highlight-end

// highlight-start
export default {
presets: [
[
'@docusaurus/preset-classic',
{
docs: {
path: 'docs',
// highlight-start
remarkPlugins: [remarkMath],
rehypePlugins: [rehypeKatex],
// highlight-end
},
},
],
],
};
```

<details>
<summary>Using a [**CommonJS**](https://nodejs.org/api/modules.html#modules-commonjs-modules) config file?</summary>

If you decide to use a CommonJS config file, it is possible to load those ES module plugins thanks to dynamic imports and an async config creator function:

```js title="docusaurus.config.js"
// highlight-start
Expand All @@ -88,29 +118,31 @@ export default async function createConfigAsync() {
}
```

</details>

## Configuring plugins {#configuring-plugins}

Some plugins can be configured and accept their own options. In that case, use the `[plugin, pluginOptions]` syntax, like this:

```js title="docusaurus.config.js"
export default async function createConfigAsync() {
return {
presets: [
[
'@docusaurus/preset-classic',
{
docs: {
rehypePlugins: [
// highlight-start
[(await import('rehype-katex')).default, {strict: false}],
// highlight-end
],
},
import rehypeKatex from 'rehype-katex';

export default {
presets: [
[
'@docusaurus/preset-classic',
{
docs: {
rehypePlugins: [
// highlight-start
[rehypeKatex, {strict: false}],
// highlight-end
],
},
],
},
],
};
}
],
};
```

You should check your plugin's documentation for the options it supports.
Expand Down

0 comments on commit 729b6f8

Please sign in to comment.