この記事について
storybookを導入する時にエラーが出て、なかなか実装が進まなかったため忘備録です。
環境
Next.js: 12.1.0
chakra-ui: 1.8.6
emotion: 11
storybook: 6.4.19
エラー1
chakra-uiで書いたコンポーネントをstorybookに読み込ませたとき、以下のようなエラーが大量に出ていました。
ModuleDependencyError: Can't import the named export 'vh' from non EcmaScript module (only default export is available)
at Compilation.reportDependencyErrorsAndWarnings (/...省略/node_modules/webpack/lib/Compilation.js:1468:21)
エラー2
こちらも同様chakra-uiで書いたコンポーネントをstorybookに読み込ませたとき、エラー自体は出てないもののコンポーネントが表示されないという現象が起きていました。
解決したコード
.storybook/main.js
を以下にすると解決しました。
module.exports = {
"stories": [
"../stories/**/*.stories.mdx",
"../stories/**/*.stories.@(js|jsx|ts|tsx)"
],
"addons": [
"@storybook/addon-links",
"@storybook/addon-essentials",
],
// NOTE: これ消したらコンポーネント出てこなくなる
features: {
emotionAlias: false,
},
typescript: {
reactDocgen: false,
},
webpackFinal: async (config) => {
// NOTE: これ消したらエラーになる
config.module.rules.push({
test: /\.mjs$/,
include: /node_modules/,
type: "javascript/auto",
})
return config
},
};
エラー1の原因
ES Modulesファイルがうまく読み込めなかったことが原因なのかなと推測します。
nextに限らず、色々なフレームワークで似たようなエラーがでることがあるようで、その場合はwebpackのmoduleのruleを上書きすることでみなさん回避されているようでした。
webpack周りが勉強不足で全然分からないので魔法のコード感が否めない・・
- ModuleDependencyError: Can't import the named export 'useRef' from non EcmaScript module (only default export is available)
- react apollo webpack 4 compatibility issue
- Can't import the named export 'Component' from non EcmaScript module (only default export is available)
エラー2の原因
storybookの内部で、emotionのバージョンv11の対応がまだ追いついてなくて表示されてなかったようです。
emotionのバージョンをv10に固定すると表示できるため、固定する機能フラグとしてemotionAlias: false
を設定すると良いとのことでした。
WebがスタイリングのためにEmotion11に移行している今、MUI5やChakraUIなどの人気のあるライブラリはemotion@10のみをサポートするStorybook6.3で壊れています。
残念ながら、semverのメジャーリリースなしでStorybookをEmotion 11にアップグレードすることはできず、その準備ができていません。
そのため、回避策として、Emotionバージョンをv10に固定するという以前の動作をオプトアウトする機能フラグを作成しました。
https://github.com/storybookjs/storybook/blob/next/MIGRATION.md#emotion11-quasi-compatibility
おまけ
- WebpackFinalとは何か
- Storybookのwebpack構成をオーバーライドできる関数
- 以下のコードを実行するとwebpackで設定されている細かい情報を得ることができる
## Development mode
yarn start-storybook --debug-webpack
## Production mode
yarn build-storybook --debug-webpack
-
mjs
とは何か- ES Modulesの拡張子。
- CommonJSは
.cjs
になる。 - ブラウザは拡張子ではなく
<script type=module>
で判断しているため.mjs
ではなくても読み込めるらしい。
参考
- Next.jsプロジェクトにStorybookを導入したときに困ったこと
- storybook Webpack
- storybook Configure Storybook
- webpack Resolve
- webpack Configuration
- chakra-uiのstorybookの設定
- Can't import the named export from non EcmaScript module (only default export is available)
- .mjs とは何か、またはモジュールベース JS とエコシステムの今後
- StorybookでEmotion 11がエラーになる問題の解決方法
- Emotion11 quasi-compatibility
- Storybook 6.1.0-rc.4 & Emotion 11.0 support