/
githubmirror
/
next.js
Обзор
Документация
Войти
/
githubmirror
/
next.js
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
canary
errors/next-prerender-client-hook.mdx
90 строк
3 KB
Josh Story
Specialize client hook prerender abort reasons (#94494)
07 июн 2026, 21:23
Не верифицирован
07 июн 2026, 21:23
2df0562
Код
Авторство
О чём код?
--- title: Client navigation hook requires a Suspense boundary --- ## Why This Error Occurred When [`cacheComponents`](/docs/app/api-reference/config/next-config-js/cacheComponents) is enabled, Next.js prerenders as much of a route as possible before a request arrives. A Client Component used a navigation hook whose value was not available during that prerender, but the component was not inside a [`Suspense`](https://react.dev/reference/react/Suspense) boundary. This can happen with the following hooks: - [`useSearchParams`](/docs/app/api-reference/functions/use-search-params), because the query string comes from the request URL - [`useParams`](/docs/app/api-reference/functions/use-params), [`usePathname`](/docs/app/api-reference/functions/use-pathname), [`useSelectedLayoutSegment`](/docs/app/api-reference/functions/use-selected-layout-segment), or [`useSelectedLayoutSegments`](/docs/app/api-reference/functions/use-selected-layout-segments) when the route contains dynamic params that were not provided by [`generateStaticParams`](/docs/app/api-reference/functions/generate-static-params) These hooks are reactive during client navigation. If their initial value is not known while prerendering, Next.js needs a fallback to include in the static shell until the runtime value is available. ## Possible Ways to Fix It ### Wrap the Client Component in Suspense Wrap the smallest subtree that uses the hook in a `Suspense` boundary. Next.js can then prerender the fallback and replace it with the Client Component when the runtime value is available. Before: ```jsx filename="app/dashboard/page.js" import { Search } from './search' export default function Page() { return ( <main> <h1>Dashboard</h1> <Search /> </main> ) } ``` ```jsx filename="app/dashboard/search.js" 'use client' import { useSearchParams } from 'next/navigation' export function Search() { const searchParams = useSearchParams() return <p>Search: {searchParams.get('q')}</p> } ``` After: ```jsx filename="app/dashboard/page.js" import { Suspense } from 'react' import { Search } from './search' export default function Page() { return ( <main> <h1>Dashboard</h1> <Suspense fallback={<p>Loading search...</p>}> <Search /> </Suspense> </main> ) } ``` The fallback should be synchronous and deterministic. Place the boundary close to the component that uses the hook so the rest of the route can remain in the prerendered shell. ### Prerender Known Dynamic Params For hooks that derive their value from dynamic route params, use `generateStaticParams` when the possible values are known ahead of time: ```jsx filename="app/blog/[slug]/page.js" export function generateStaticParams() { return [{ slug: 'hello-world' }, { slug: 'release-notes' }] } export default function Page() { return <BlogNavigation /> } ``` For the generated paths, `useParams`, `usePathname`, and the selected-layout-segment hooks can resolve during prerendering. Paths not returned by `generateStaticParams` may still require a `Suspense` boundary. `generateStaticParams` does not provide search parameters. Components that use `useSearchParams` should be wrapped in `Suspense` when the route is prerendered. ## Useful Links - [`Suspense`](https://react.dev/reference/react/Suspense) - [`generateStaticParams`](/docs/app/api-reference/functions/generate-static-params) - [Cache Components](/docs/app/api-reference/config/next-config-js/cacheComponents)