勇哥

勇哥开发之路

I build things on web.

Next.js の useSearchParams() の落とし穴

❗問題#

最近勇哥が AI 対話アプリケーションを作成する過程で、URL からパラメータを取得するために useSearchParams 方法を使用しました。development モードではすべて正常でしたが、build 時にエラーが発生しました:

 useSearchParams() should be wrapped in a suspense boundary at page "/".

❓原因#

公式の説明は次のとおりです:
Suspense 境界がない状態で useSearchParams () を使用して検索パラメータを読み取ると、ページ全体がクライアントレンダリングに入ります。これにより、クライアントの JavaScript が読み込まれるまでページが空白のままになる可能性があります。

勇哥は静的レンダリングを使用しているため、useSearchParams方法はURLSearchParamsインターフェースの読み取り専用インターフェースを返します。そして、URLSearchParamsはブラウザに依存しているため、window オブジェクトが読み込まれるまで待つ必要があります。

✔解決方法#

公式の推奨解決策は非常に簡単です:useSearchParams () の呼び出しがSuspenseでラップされていることを確認してください。

変更前、勇哥の page.tsx ファイルは次のようになっていました:

'use client';

...
import { useRouter, useSearchParams } from 'next/navigation'
import { SidebarProvider, SidebarInset } from "@/components/ui/sidebar"
...

// メインページコンポーネント
export default function Page() {
  const router = useRouter()
  const urlParams = useSearchParams()
  // ... その他の状態とロジック
  
  return (
    <SidebarProvider>
      <AppSidebar />
      <SidebarInset>
        ...
      </SidebarInset>
    </SidebarProvider>
  );
}

変更後:

'use client';

import { Suspense } from "react"
import { useRouter, useSearchParams } from 'next/navigation'
import { SidebarProvider, SidebarInset } from "@/components/ui/sidebar"

// すべてのクライアントロジックを処理するラッピングコンポーネントを新規作成
function ChatPageContent() {
  // ... 元の状態とロジック
    const router = useRouter()
    const urlParams = useSearchParams()
    // ... その他の状態とロジック
    
    return (
      <SidebarProvider>
        <AppSidebar />
        <SidebarInset>
          ...
        </SidebarInset>
      </SidebarProvider>
    );
  }
}

// メインページコンポーネント
export default function Page() {
  // ラッピングコンポーネントの外側に<Suspense />を追加
  return (
    <Suspense fallback={<div>チャットを読み込んでいます...</div>}>
      <ChatPageContent />
    </Suspense>
  );
}

useSearchParamsを使用するクライアントコンポーネントを<Suspense/>でラップします。この場合、ルーティングの一部は静的にレンダリングされ、useSearchParamsを使用する動的部分はクライアントで window オブジェクトが利用可能になった後にレンダリングされます。

読み込み中...
文章は、創作者によって署名され、ブロックチェーンに安全に保存されています。