5
Help us understand the problem. What are the problem?

More than 1 year has passed since last update.

posted at

updated at

Next.js v10 (React v17) でも Storybook を使いたい

Next.js とは

React をベースにした,いい感じにしてくれるフレームワーク.Vercel と連携して API 部分をシュッとサーバレス関数に変換してくれたりする.
https://nextjs.org/

Storybook とは

Vue,React,Angular といったコンポーネント指向のフレームワークで,各コンポーネントのサンプルをストーリとして作っておけるやつ.そのコンポーネント単体をテストベッドに置くイメージで開発できるので便利.
https://storybook.js.org/

Next.js v10 で Storybook を使ったら起きた問題と解決策

Storybook 安定版が React v17 に対応していない問題

09/11/2020 現在, Storybook の安定版である v6.0 はまだ React v17 に対応していないっぽい. --no-dll オプションをつけると起動はできるのだが, Next.js 環境下では React is not defined. というエラーが出た.β版の v6.1 であれば動作したのでこれを使う.

$ yarn add -D @storybook/react@^6.1.0-beta.5

CSS が読み込まれない問題

Next.js (特に create-next-app) は CSS Modules の使用を前提としているが, Storybook はこれを標準でサポートしていない. Webpack の設定をいい感じにしてあげる必要がある.

/.storybook/main.js
const loaders = (options = {}) => [
  { loader: 'style-loader' },
  {
    loader: 'css-loader',
    options: {
      importLoaders: 1,
      ...options,
    },
  },
  { loader: 'postcss-loader' },
];

module.exports = {
  stories: [
    '../stories/**/*.@(tsx|mdx)',
  ],
  webpackFinal: async (config) => ({
    ...config,
    module: {
      ...config.module,
      rules: config.module.rules.reduce(
        (acc, cur) => [
          ...acc,
          ...cur.test.toString() === /\.css$/.toString()
            ? [
              { test: /\.module\.css$/, use: loaders({ modules: true }) },
              { test: /^.*(?<!\.module)\.css$/, use: loaders() },
            ]
            : [cur],
        ],
        [],
      ),
    },
  }),
};

行数削減のために共通部分を出したり reduce したりしているが,やっていることは以下の通り.

  • /\.css$/ に対するルールを 2 つに分割する
    • .module.css で終わるファイルに対して css-loader を CSS Modules 有効で設定する
    • .module.css終わらない かつ .css で終わるファイルに対して css-loader を CSS Modules 無効で設定する
  • それ以外のルールはそのまま通す

なお, stories の値についてはディレクトリ構成に応じて適宜設定してください.

グローバルな CSS が読み込まれない問題

Next.js は既定で /styles/global.css を読みにいくが, Storybook はそんなもの知らないので指定してあげる必要がある.

/.storybook/preview.js
import '../styles/globals.css';

public 内のアセットがサーブされない問題

起動オプションで指定するとサーブしてくれる. npm のスクリプトとかに書いておくと便利.

$ start-storybook -s ./public
/package.json
{
  "scripts": {
    "storybook:start": "start-storybook -s ./public"
  }
}

おわりに

dev.to とかでありがちな記事の構成になってしまった気がする.同じケースで困った方がこの記事にたどり着いてくれたらうれしいです.もっと良い方法があればぜひ教えてください :bow:

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Sign upLogin
5
Help us understand the problem. What are the problem?