Open talohana opened 2 years ago
Late answer, but maybe it will be helpful for someone else:
Storybook is a client side application, so Node.js modules like fs
do not work. Therefore, mdx-bundler
can not be called from within storybook.
What you can do is doing the bundeling in a separate script:
// bundle-mdx.js
const { bundleMDX } = require('mdx-bundler')
const fs = require('fs-extra')
const { join } = require('path')
;(async function () {
const sourceDir = join(__dirname, 'mdx')
const sourceFiles = await fs.readdir(sourceDir, 'utf-8')
const targetDir = join(__dirname, 'bundled')
await fs.remove(targetDir)
await fs.ensureDir(targetDir)
await Promise.all(
sourceFiles.map(async file => {
const sourceFilePath = join(sourceDir, file)
const source = await fs.readFile(sourceFilePath, 'utf-8')
const bundled = await bundleMDX({ source })
const json = JSON.stringify(
bundled,
undefined,
process.env.NODE_ENV === 'production' ? null : 2
)
const targetFile = join(targetDir, file.replace(/\.mdx$/, '.json'))
await fs.writeFile(targetFile, json)
})
)
})()
And add to your package.json
:
{
"scripts": {
"bundle-story-mdx": "node ./bundle-mdx.js",
"bundle-story-mdx:watch": "nodemon --watch ./mdx -e md,mdx ./bundle-mdx.js",
},
...
}
Create a mdx
folder next to bundle-mdx.js
. When you run npm run bundle-story-mdx
(or yarn bundle-story-mdx
, if you are using yarn), all mdx files within will get bundled by the script.
To automatically run the script whenever you change a mdx file, install nodemon via npm i -D nodemon
, and run npm run bundle-story-mdx:watch
.
In storybook, you can then just import the bundles and use them in your stories:
// MyComponent.stories.ts
import React from 'react'
import { Meta, Story } from '@storybook/react/types-6-0'
import { MyComponent, MyComponentProps } from './MyComponent'
import bundle from './bundled/example.json'
const meta: Meta = {
title: 'MyComponent',
component: MyComponent,
}
export default meta
const Template: Story<MyComponentProps> = args => <MyComponent {...args} />
export const Standard = Template.bind({})
Standard.args = {
// pass bundle down to your components
bundledMdx: bundle.code,
}
You might have to adjust things to make it work with your Next.js page.
mdx-bundler
version: 8.0.1node
version: 14.18.1npm
version: 6.14.15next
version: 12.0.8What you did:
I am building my site with Nextjs and using mdx-bundler for my blog. I was trying to add storybook for my blog page, which loads the posts using mdx-bundler.
The blog loads the posts in a similar way as the reproduction below.
What happened:
Starting storybook I get the following error, followed by more similar errors (which seems to be related to esbuild):
After commenting
getStaticProps
atHome
component, storybook runs as expected.Reproduction repository:
https://codesandbox.io/s/nextjs-storybook-mdx-bundler-2jheo?file=/pages/index.js
Running
yarn dev
in terminal or restarting sandbox will raise the error at the terminal