🚰
Ladle で Next.js Pages Router のプロバイダを設定する
この記事について
コンポーネントカタログ「Ladle」の初期設定をしていて、Next.js(Pages Router)の設定でつまづいたのでメモしておく。
発生した問題
Next.js の設定は公式ドキュメントが参考になるが…
基本的に、Next.jsを使う場合は公式のRecipeを参考に設定していけばOK。
Pages Router で発生するエラーへの対応
前述のページは App Router前提の説明となっている。私は Pages Router を使っていたため少しカスタムが必要だった。
Pages Router の Provider を渡していないと、Ladleを開いたブラウザのコンソールに以下のようなエラーが出力される。
Uncaught Error: NextRouter was not mounted. https://nextjs.org/docs/messages/next-router-not-mounted
    at useRouter (next_router.js?v=3df67b26:6147:15)
    ...
設定した内容
前述のページの解説項目に加え、以下のように設定することで無事表示できた。
コード
components.tsx
import React from 'react';
import { GlobalProvider } from '@ladle/react';
import { RouterContext } from 'next/dist/shared/lib/router-context.shared-runtime';
const NextRouterProvider = ({ children }) => {
  return (
    <RouterContext.Provider
      value={
        // 雑に any で型を無視している
        {
          push: () => Promise.resolve(true),
          pathname: '/',
        } as any
      }
    >
      {children}
    </RouterContext.Provider>
  );
};
export const Provider: GlobalProvider = ({ children }) => {
  return (
    <NextRouterProvider>
      {children}
    </NextRouterProvider>
  );
};
解説
Ladle では、 .ladle/components.tsx から export した Provider をグローバルなプロバイダとして適用してくれるので、これを使っている。
やっていることは Pages Router の RouterContext.Provider をデフォルトプロバイダに追加するというだけ。
あくまでただのモックなので、 router.push, router.pathname などの呼び出されうるプロパティだけ設定して型は雑に any で処理している。各々のプロジェクトで使っているプロパティを設定すればOK。
Discussion