🚰

Ladle で Next.js Pages Router のプロバイダを設定する

に公開

この記事について

コンポーネントカタログ「Ladle」の初期設定をしていて、Next.js(Pages Router)の設定でつまづいたのでメモしておく。

発生した問題

Next.js の設定は公式ドキュメントが参考になるが…

基本的に、Next.jsを使う場合は公式のRecipeを参考に設定していけばOK。

https://ladle.dev/docs/nextjs

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 をグローバルなプロバイダとして適用してくれるので、これを使っている。

https://ladle.dev/docs/providers/

やっていることは Pages Router の RouterContext.Provider をデフォルトプロバイダに追加するというだけ。

あくまでただのモックなので、 router.push, router.pathname などの呼び出されうるプロパティだけ設定して型は雑に any で処理している。各々のプロジェクトで使っているプロパティを設定すればOK。

Discussion