useSearchParams

useSearchParams — это хук Клиентского компонента (Client Component), который позволяет читать строку запроса (query string) текущего URL.

useSearchParams возвращает только для чтения версию интерфейса URLSearchParams.

'use client'

import { useSearchParams } from 'next/navigation'

export default function SearchBar() {
  const searchParams = useSearchParams()

  const search = searchParams.get('search')

  // URL -> `/dashboard?search=my-project`
  // `search` -> 'my-project'
  return <>Search: {search}</>
}
'use client'

import { useSearchParams } from 'next/navigation'

export default function SearchBar() {
  const searchParams = useSearchParams()

  const search = searchParams.get('search')

  // URL -> `/dashboard?search=my-project`
  // `search` -> 'my-project'
  return <>Search: {search}</>
}

Параметры

const searchParams = useSearchParams()

useSearchParams не принимает параметров.

Возвращаемое значение

useSearchParams возвращает только для чтения версию интерфейса URLSearchParams, которая включает вспомогательные методы для чтения строки запроса URL:

  • URLSearchParams.get(): Возвращает первое значение, связанное с параметром поиска. Например:

    URLsearchParams.get("a")
    /dashboard?a=1'1'
    /dashboard?a=''
    /dashboard?b=3null
    /dashboard?a=1&a=2'1' - используйте getAll() для получения всех значений
  • URLSearchParams.has(): Возвращает логическое значение, указывающее на наличие параметра. Например:

    URLsearchParams.has("a")
    /dashboard?a=1true
    /dashboard?b=3false
  • Узнайте больше о других только для чтения методах URLSearchParams, включая getAll(), keys(), values(), entries(), forEach() и toString().

Полезно знать:

Поведение

Статический рендеринг (Static Rendering)

Если маршрут рендерится статически (statically rendered), вызов useSearchParams приведет к рендерингу на стороне клиента дерева Клиентских компонентов до ближайшей границы Suspense.

Это позволяет части маршрута рендериться статически, в то время как динамическая часть, использующая useSearchParams, рендерится на стороне клиента.

Рекомендуется обернуть Клиентский компонент, использующий useSearchParams, в границу <Suspense/>. Это позволит статически отрендерить Клиентские компоненты выше и отправить их как часть начального HTML. Пример.

Например:

'use client'

import { useSearchParams } from 'next/navigation'

export default function SearchBar() {
  const searchParams = useSearchParams()

  const search = searchParams.get('search')

  // Это не будет залогировано на сервере при статическом рендеринге
  console.log(search)

  return <>Search: {search}</>
}
'use client'

import { useSearchParams } from 'next/navigation'

export default function SearchBar() {
  const searchParams = useSearchParams()

  const search = searchParams.get('search')

  // Это не будет залогировано на сервере при статическом рендеринге
  console.log(search)

  return <>Search: {search}</>
}
import { Suspense } from 'react'
import SearchBar from './search-bar'

// Этот компонент, переданный как fallback для границы Suspense,
// будет отрендерен вместо строки поиска в начальном HTML.
// Когда значение станет доступным во время гидратации React,
// fallback будет заменен компонентом `<SearchBar>`.
function SearchBarFallback() {
  return <>placeholder</>
}

export default function Page() {
  return (
    <>
      <nav>
        <Suspense fallback={<SearchBarFallback />}>
          <SearchBar />
        </Suspense>
      </nav>
      <h1>Dashboard</h1>
    </>
  )
}
import { Suspense } from 'react'
import SearchBar from './search-bar'

// Этот компонент, переданный как fallback для границы Suspense,
// будет отрендерен вместо строки поиска в начальном HTML.
// Когда значение станет доступным во время гидратации React,
// fallback будет заменен компонентом `<SearchBar>`.
function SearchBarFallback() {
  return <>placeholder</>
}

export default function Page() {
  return (
    <>
      <nav>
        <Suspense fallback={<SearchBarFallback />}>
          <SearchBar />
        </Suspense>
      </nav>
      <h1>Dashboard</h1>
    </>
  )
}

Динамический рендеринг (Dynamic Rendering)

Если маршрут рендерится динамически (dynamically rendered), useSearchParams будет доступен на сервере во время начального серверного рендеринга Клиентского компонента.

Например:

'use client'

import { useSearchParams } from 'next/navigation'

export default function SearchBar() {
  const searchParams = useSearchParams()

  const search = searchParams.get('search')

  // Это будет залогировано на сервере во время начального рендеринга
  // и на клиенте при последующих навигациях.
  console.log(search)

  return <>Search: {search}</>
}
'use client'

import { useSearchParams } from 'next/navigation'

export default function SearchBar() {
  const searchParams = useSearchParams()

  const search = searchParams.get('search')

  // Это будет залогировано на сервере во время начального рендеринга
  // и на клиенте при последующих навигациях.
  console.log(search)

  return <>Search: {search}</>
}
import SearchBar from './search-bar'

export const dynamic = 'force-dynamic'

export default function Page() {
  return (
    <>
      <nav>
        <SearchBar />
      </nav>
      <h1>Dashboard</h1>
    </>
  )
}
import SearchBar from './search-bar'

export const dynamic = 'force-dynamic'

export default function Page() {
  return (
    <>
      <nav>
        <SearchBar />
      </nav>
      <h1>Dashboard</h1>
    </>
  )
}

Полезно знать: Установка опции dynamic в конфигурации сегмента маршрута в значение force-dynamic может использоваться для принудительного динамического рендеринга.

Серверные компоненты (Server Components)

Страницы (Pages)

Для доступа к параметрам поиска в Страницах (Pages) (Серверных компонентах) используйте пропс searchParams.

Макеты (Layouts)

В отличие от Страниц, Макеты (Layouts) (Серверные компоненты) не получают пропс searchParams. Это связано с тем, что общий макет не перерендеривается во время навигации, что может привести к устаревшим searchParams между переходами. Подробнее в объяснении.

Вместо этого используйте пропс searchParams Страницы или хук useSearchParams в Клиентском компоненте, который перерендеривается на клиенте с актуальными searchParams.

Примеры

Обновление searchParams

Вы можете использовать useRouter или Link для установки новых searchParams. После выполнения навигации текущая page.js получит обновленный пропс searchParams.

'use client'

export default function ExampleClientComponent() {
  const router = useRouter()
  const pathname = usePathname()
  const searchParams = useSearchParams()

  // Получение новой строки searchParams путем объединения текущих
  // searchParams с переданной парой ключ/значение
  const createQueryString = useCallback(
    (name: string, value: string) => {
      const params = new URLSearchParams(searchParams.toString())
      params.set(name, value)

      return params.toString()
    },
    [searchParams]
  )

  return (
    <>
      <p>Sort By</p>

      {/* используя useRouter */}
      <button
        onClick={() => {
          // <pathname>?sort=asc
          router.push(pathname + '?' + createQueryString('sort', 'asc'))
        }}
      >
        ASC
      </button>

      {/* используя <Link> */}
      <Link
        href={
          // <pathname>?sort=desc
          pathname + '?' + createQueryString('sort', 'desc')
        }
      >
        DESC
      </Link>
    </>
  )
}
'use client'

export default function ExampleClientComponent() {
  const router = useRouter()
  const pathname = usePathname()
  const searchParams = useSearchParams()

  // Получение новой строки searchParams путем объединения текущих
  // searchParams с переданной парой ключ/значение
  const createQueryString = useCallback(
    (name, value) => {
      const params = new URLSearchParams(searchParams)
      params.set(name, value)

      return params.toString()
    },
    [searchParams]
  )

  return (
    <>
      <p>Sort By</p>

      {/* используя useRouter */}
      <button
        onClick={() => {
          // <pathname>?sort=asc
          router.push(pathname + '?' + createQueryString('sort', 'asc'))
        }}
      >
        ASC
      </button>

      {/* используя <Link> */}
      <Link
        href={
          // <pathname>?sort=desc
          pathname + '?' + createQueryString('sort', 'desc')
        }
      >
        DESC
      </Link>
    </>
  )
}

История версий

ВерсияИзменения
v13.0.0Добавлен useSearchParams.