Связывание и навигация
Существует четыре способа навигации между маршрутами в Next.js:
- Использование компонента
<Link>Компонент - Использование хука
useRouterхук (Клиентские компоненты) - Использование функции
redirectфункция (Серверные компоненты) - Использование родного API History API
На этой странице будет показано, как использовать каждый из этих вариантов, и более подробно рассмотрен процесс навигации.
<Link> Компонент
<Link> — это встроенный компонент, который расширяет тег HTML <a> для обеспечения предварительной загрузки и навигации на стороне клиента между маршрутами. Это основной и рекомендуемый способ навигации между маршрутами в Next.js.
Вы можете использовать его, импортировав его из next/link, и передав свойство href компоненту:
import Link from 'next/link'
export default function Page() {
return <Link href="/dashboard">Dashboard</Link>
}Существуют и другие необязательные свойства, которые вы можете передать <Link>. Дополнительную информацию см. в справочнике API.
Примеры
Связывание с динамическими сегментами
При связывании с динамическими сегментами вы можете использовать шаблоны строк и интерполяцию для генерации списка ссылок. Например, для генерации списка статей блога:
import Link from 'next/link'
export default function PostList({ posts }) {
return (
<ul>
{posts.map((post) => (
<li key={post.id}>
<Link href={`/blog/${post.slug}`}>{post.title}</Link>
</li>
))}
</ul>
)
}Проверка активных ссылок
Вы можете использовать usePathname() для определения, активна ли ссылка. Например, чтобы добавить класс активной ссылке, вы можете проверить, совпадает ли текущий pathname с href ссылки:
'use client'
import { usePathname } from 'next/navigation'
import Link from 'next/link'
export function Links() {
const pathname = usePathname()
return (
<nav>
<ul>
<li>
<Link className={`link ${pathname === '/' ? 'active' : ''}`} href="/">
Home
</Link>
</li>
<li>
<Link
className={`link ${pathname === '/about' ? 'active' : ''}`}
href="/about"
>
About
</Link>
</li>
</ul>
</nav>
)
}Прокрутка до идентификатора
По умолчанию маршрутизатор приложений Next.js прокручивает страницу к началу нового маршрута или сохраняет позицию прокрутки при навигации назад и вперед.
Если вы хотите прокрутить до определенного id при навигации, вы можете добавить в URL # ссылку с хэшем или просто передать ссылку с хэшем в свойство href . Это возможно, так как <Link> рендерится в элемент <a>.
<Link href="/dashboard#settings">Settings</Link> // Output <a href="/dashboard#settings">Settings</a>
Важно знать:
- Next.js будет прокручивать до страницы, если она не видна в области просмотра после навигации.
Отключение восстановления прокрутки
По умолчанию маршрутизатор приложений Next.js прокручивает страницу к началу нового маршрута или сохраняет позицию прокрутки при навигации назад и вперед. Если вы хотите отключить это поведение, вы можете передать scroll={false} компоненту <Link> или scroll: false к router.push() или router.replace().
// next/link
<Link href="/dashboard" scroll={false}>
Dashboard
</Link>
// useRouter
import { useRouter } from 'next/navigation'
const router = useRouter()
router.push('/dashboard', { scroll: false })
Хук useRouter()
Хук useRouter позволяет программно изменять маршруты из клиентских компонентов.
'use client'
import { useRouter } from 'next/navigation'
export default function Page() {
const router = useRouter()
return (
<button type="button" onClick={() => router.push('/dashboard')}>
Dashboard
</button>
)
}Полный список useRouter методов см. в справочнике API.
Рекомендация: Используйте компонент
<Link>для навигации между маршрутами, если у вас нет конкретной необходимости использоватьuseRouter.
Функция redirect
Для серверных компонентов используйте функцию redirect вместо неё.
import { redirect } from 'next/navigation'
async function fetchTeam(id: string) {
const res = await fetch('https://...')
if (!res.ok) return undefined
return res.json()
}
export default async function Profile({ params }: { params: { id: string } }) {
const team = await fetchTeam(params.id)
if (!team) {
redirect('/login')
}
// ...
}Важно знать:
redirectпо умолчанию возвращает код состояния 307 (Временное перенаправление). При использовании в действии сервера она возвращает 303 (См. другое), что часто используется для перенаправления на страницу успеха в результате запроса POST.redirectвнутри генерирует ошибку, поэтому её следует вызывать вне блоковtry/catch.redirectможет вызываться в клиентских компонентах во время процесса рендеринга, но не в обработчиках событий. Вместо этого вы можете использовать хукuseRouterхук.redirectтакже принимает абсолютные URL-адреса и может использоваться для перенаправления на внешние ссылки.- Если вы хотите перенаправить до процесса рендеринга, используйте
next.config.jsили Средства.
Дополнительную информацию см. в redirect справочнике API.
Использование родного API истории
Next.js позволяет использовать родные методы window.history.pushState и window.history.replaceState для обновления стека истории браузера без перезагрузки страницы.
pushState и replaceState вызовы интегрируются в маршрутизатор Next.js, позволяя синхронизироваться с usePathname и useSearchParams.
window.history.pushState
Используйте его для добавления новой записи в стек истории браузера. Пользователь может вернуться к предыдущему состоянию. Например, для сортировки списка продуктов:
'use client'
import { useSearchParams } from 'next/navigation'
export default function SortProducts() {
const searchParams = useSearchParams()
function updateSorting(sortOrder: string) {
const params = new URLSearchParams(searchParams.toString())
params.set('sort', sortOrder)
window.history.pushState(null, '', `?${params.toString()}`)
}
return (
<>
<button onClick={() => updateSorting('asc')}>Sort Ascending</button>
<button onClick={() => updateSorting('desc')}>Sort Descending</button>
</>
)
}
window.history.replaceState
Используйте его для замены текущей записи в стеке истории браузера. Пользователь не может вернуться к предыдущему состоянию. Например, для изменения языка приложения:
'use client'
import { usePathname } from 'next/navigation'
export function LocaleSwitcher() {
const pathname = usePathname()
function switchLocale(locale: string) {
// e.g. '/en/about' or '/fr/contact'
const newPath = `/${locale}${pathname}`
window.history.replaceState(null, '', newPath)
}
return (
<>
<button onClick={() => switchLocale('en')}>English</button>
<button onClick={() => switchLocale('fr')}>French</button>
</>
)
}
Как работает маршрутизация и навигация
Маршрутизатор приложений использует гибридный подход к маршрутизации и навигации. На сервере код вашего приложения автоматически разделяется по маршрутам. А на клиенте Next.js предварительно загружает и кеширует сегменты маршрута. Это означает, что когда пользователь переходит на новый маршрут, браузер не перезагружает страницу, а перерендериваются только изменившиеся сегменты маршрута — повышая удобство и производительность навигации.
1. Разделение кода
Разделение кода позволяет разделить код вашего приложения на более мелкие пакеты для загрузки и выполнения в браузере. Это уменьшает количество передаваемых данных и время выполнения для каждого запроса, что приводит к повышению производительности.
Серверные компоненты позволяют автоматически разделять код вашего приложения по сегментам маршрутов. Это означает, что при навигации загружается только код, необходимый для текущего маршрута.
2. Предварительная загрузка
Предварительная загрузка — это способ предварительной загрузки маршрута в фоновом режиме перед его посещением пользователем.
Существует два способа предварительной загрузки маршрутов в Next.js:
-
<Link>компонент: Маршруты автоматически предварительно загружаются, когда они становятся видимыми в области просмотра пользователя. Предварительная загрузка происходит при первой загрузке страницы или когда она становится видимой при прокрутке. -
router.prefetch(): ХукuseRouterможет использоваться для программно предварительной загрузки маршрутов.
Поведение предварительной загрузки <Link> по умолчанию (т. е. когда свойство prefetch не указано или установлено в значение null ) отличается в зависимости от вашего использования loading.js. Только общий макет, по дереву компонентов до первого loading.js файла, предварительно загружается и кешируется для 30s. Это снижает затраты на загрузку всего динамического маршрута, и это означает, что вы можете показать состояние мгновенной загрузки для лучшей визуальной обратной связи пользователям.
Вы можете отключить предварительную загрузку, установив свойство prefetch в значение false. Кроме того, вы можете предварительно загрузить полные данные страницы за пределами границ загрузки, установив свойство prefetch в значение true.
Дополнительную информацию см. в <Link> справочнике API.
Важно знать:
- Предварительная загрузка не включена в режиме разработки, только в режиме производства.
3. Кэширование
Next.js имеет кэш на стороне клиента в памяти, называемый кэшем маршрутизатора. По мере навигации пользователей по приложению данные React Server Component из предварительно загруженных сегментов маршрута и посещаемых маршрутов хранятся в кэше.
Это означает, что при навигации кэш используется по мере возможности, а не выполняется новый запрос к серверу, повышая производительность за счет уменьшения количества запросов и передаваемых данных.
Узнайте больше о работе кэша маршрутизатора и о том, как его настроить.
4. Частичное рендеринг
Частичное рендеринг означает, что при навигации перерендериваются только сегменты маршрута, которые изменяются, а общие сегменты сохраняются.
Например, при навигации между двумя соседними маршрутами /dashboard/settings и /dashboard/analytics будут рендериться страницы settings и analytics, а общий макет dashboard сохранится.


Без частичного рендеринга каждый переход по навигации приводил бы к полному перерендерингу страницы на клиенте. Рендеринг только изменённого сегмента уменьшает объём передаваемых данных и время выполнения, что приводит к улучшению производительности.
5. Мягкая навигация
Браузеры выполняют «жёсткую навигацию» при переходе между страницами. Router приложения Next.js позволяет выполнять «мягкую навигацию» между страницами, обеспечивая перерендеринг только тех сегментов маршрута, которые изменились (частичный рендеринг). Это позволяет сохранить состояние React клиента во время навигации.
6. Навигация назад и вперёд
По умолчанию Next.js сохранит позицию прокрутки для навигации назад и вперёд и повторно использует сегменты маршрута в кэше маршрутизатора Кэше маршрутизатора.
7. Маршрутизация между страницами и приложением
При поэтапной миграции из pages/ в app/, маршрутизатор Next.js автоматически обрабатывает жёсткую навигацию между ними. Для определения переходов из pages/ в app/ существует фильтр клиента маршрутизатора, который использует вероятностную проверку маршрутов приложения, что может иногда приводить к ложноположительным результатам. По умолчанию такие случаи должны быть очень редкими, так как мы настраиваем вероятность ложноположительного результата на 0,01 %. Эту вероятность можно настроить с помощью опции experimental.clientRouterFilterAllowedRate в next.config.js. Важно отметить, что снижение уровня ложноположительных результатов увеличит размер сгенерированного фильтра в клиентском пакете.
В качестве альтернативы, если вы предпочитаете полностью отключить эту обработку и вручную управлять маршрутизацией между pages/ и app/, вы можете установить experimental.clientRouterFilter в значение false в next.config.js. Когда эта функция отключена, все динамические маршруты на страницах, которые перекрываются с маршрутами приложения, по умолчанию не будут правильно перенаправляться.
© 2024 Vercel, Inc.
Licensed under the MIT License.
https://nextjs.org/docs/app/building-your-application/routing/linking-and-navigating