Spec-Zone.ru › Web APIs

API навигации

Экспериментально: Это экспериментальная технология.
Перед использованием в продуктовой среде внимательно изучите таблицу совместимости с браузерами.

API навигации предоставляет возможность инициировать, перехватывать и управлять действиями навигации браузера. Также он позволяет просматривать записи истории приложения. Это преемник предыдущих функций веб-платформы, таких как API истории и window.location, который решает их недостатки и специально разработан для нужд приложений с одностраничным интерфейсом (SPA).

Концепции и использование

В приложениях SPA шаблон страницы, как правило, остается неизменным во время использования, а содержимое динамически переписывается по мере перехода пользователя к различным страницам или функциям. В результате в браузере загружается только одна отдельная страница, что нарушает ожидаемое поведение пользователя при навигации вперёд и назад между различными позициями в истории просмотра. Эту проблему можно частично решить с помощью API истории, но он не предназначен для нужд SPA. API навигации призван восполнить этот пробел.

К API можно получить доступ через свойство Window.navigation, которое возвращает ссылку на глобальный объект Navigation. Каждый объект window имеет свой соответствующий экземпляр navigation.

Обработка навигации

Интерфейс navigation имеет несколько связанных событий, наиболее важным из которых является событие navigate. Оно срабатывает при инициировании любого типа навигации, что означает, что вы можете управлять всей навигацией по страницам из одного центрального места, что идеально подходит для функциональности маршрутизации в рамках SPA-фреймворков. (Это не так с API истории, где иногда трудно определить, как реагировать на все навигации.) Обработчик события navigate получает объект NavigateEvent, содержащий подробную информацию, в том числе данные о пункте назначения навигации, типе, наличии данных формы POST или запроса загрузки, и многое другое.

Объект NavigationEvent также предоставляет два метода:

  • intercept() принимает в качестве аргумента функцию обратного вызова, возвращающую промис. Это позволяет контролировать, что происходит при инициировании навигации. Например, в случае SPA это можно использовать для загрузки соответствующего нового содержимого в пользовательский интерфейс на основе пути URL, к которому осуществляется переход.
  • scroll() позволяет вручную инициировать поведение прокрутки браузера (например, до фрагмента идентификатора в URL), если это имеет смысл для вашего кода, а не ожидать, что браузер обработает это автоматически.

После того, как навигация инициирована, и ваш обработчик intercept() вызван, создаётся экземпляр объекта NavigationTransition (доступный через Navigation.transition), который можно использовать для отслеживания процесса текущей навигации.

Примечание: В данном контексте «переход» относится к переходу между одной записью истории и другой. Он не связан с CSS-переходами.

Примечание: Вы также можете вызвать preventDefault(), чтобы полностью остановить навигацию для большинства типов навигации preventDefault(); отмена навигации по переходам пока не реализована.

Когда промис функции обработчика intercept() выполнится, событие navigatesuccess объекта Navigation сработает, позволяя выполнить код очистки после успешного завершения навигации. Если он отклонится, означая, что навигация не удалась, вместо этого сработает navigateerror, позволяя вам элегантно обработать случай неудачи. Также существует свойство finished объекта NavigationTransition, которое выполняется или отклоняется одновременно с срабатыванием вышеупомянутых событий, предоставляя ещё один способ обработки успешных и неудачных случаев.

Примечание: До появления API навигации для выполнения подобных действий вам пришлось бы прослушивать все события щелчков по ссылкам, выполнять e.preventDefault(), выполнять соответствующий вызов History.pushState(), а затем настраивать отображение страницы на основе нового URL. И это не обрабатывало бы все навигации — только инициированные пользователем щелчки по ссылкам.

Программное обновление и навигация по истории навигации

По мере навигации пользователя по вашему приложению каждый новый посещаемый пункт приводит к созданию записи в истории навигации. Каждая запись истории представлена отдельным экземпляром объекта NavigationHistoryEntry. Они содержат несколько свойств, таких как ключ записи, URL и информация о состоянии. Вы можете получить запись, на которой пользователь находится в данный момент, используя Navigation.currentEntry, и массив всех существующих записей истории с помощью Navigation.entries(). Каждый объект NavigationHistoryEntry имеет событие dispose, которое срабатывает, когда запись больше не является частью истории браузера. Например, если пользователь три раза переходит назад, а затем переходит вперёд куда-то ещё, эти три записи истории будут удалены.

Примечание: API навигации отображает только записи истории, созданные в текущем контексте просмотра, которые имеют тот же источник, что и текущая страница (например, не навигации внутри вложенных <iframe> или навигации между источниками), предоставляя точный список всех предыдущих записей истории только для вашего приложения. Это делает навигацию по истории гораздо менее хрупкой по сравнению со старым API истории.

Объект Navigation содержит все методы, необходимые для обновления и навигации по истории навигации:

navigate() Экспериментально

Переходит по новому URL, создавая новую запись в истории навигации.

reload() Экспериментально

Перезагружает текущую запись истории навигации.

back() Экспериментально

Переходит к предыдущей записи истории навигации, если это возможно.

forward() Экспериментально

Переходит к следующей записи истории навигации, если это возможно.

traverseTo() Экспериментально

Переходит к конкретной записи истории навигации, определяемой по её значению ключа, которое получено через свойство NavigationHistoryEntry.key соответствующей записи.

Каждый из вышеперечисленных методов возвращает объект, содержащий два промиса — { committed, finished }. Это позволяет вызывающей функции ожидать выполнения дальнейших действий до:

  • committed выполняется, что означает, что видимый URL изменился и был создан новый NavigationHistoryEntry.
  • finished выполняется, что означает, что все промисы, возвращённые вашим обработчиком intercept(), выполнены. Это эквивалентно выполнению промиса NavigationTransition.finished при срабатывании события navigatesuccess, как упоминалось ранее.
  • любой из вышеперечисленных промисов отклоняется, что означает, что навигация не удалась по какой-либо причине.

Состояние

API навигации позволяет хранить состояние в каждой записи истории. Эта информация определяется разработчиком — она может быть любой. Например, вы можете хранить свойство visitCount, которое записывает количество посещений представления, или объект, содержащий несколько свойств, связанных с состоянием пользовательского интерфейса, чтобы состояние можно было восстановить, когда пользователь возвращается к этому представлению.

Чтобы получить состояние NavigationHistoryEntry, вы вызываете его метод getState(). Изначально он undefined, но когда информация о состоянии устанавливается в записи, он вернёт ранее установленное состояние.

Установка состояния немного сложнее. Вы не можете извлечь значение состояния и затем обновить его напрямую — копия, хранящаяся в записи, не изменится. Вместо этого вы обновляете его при выполнении navigate() или reload() — каждый из них необязательно принимает параметр объекта опций, который включает свойство state, содержащее новое состояние для установки в записи истории. Когда эти переходы завершаются, изменение состояния автоматически применяется.

В некоторых случаях изменение состояния будет независимым от навигации или перезагрузки — например, когда страница содержит элемент <details> (развернуть/свернуть). В этом случае вы можете сохранить состояние раскрытия/свертывания в записи истории, чтобы восстановить его, когда пользователь возвращается на страницу или перезапускает браузер. Такие случаи обрабатываются с помощью Navigation.updateCurrentEntry(). currententrychange сработает, когда изменение текущей записи будет завершено.

Ограничения

Существует несколько предполагаемых ограничений API навигации:

  1. Текущая спецификация не вызывает событие navigate при первой загрузке страницы. Это может подойти для сайтов, использующих предварительную рендеризацию на стороне сервера (SSR) — ваш сервер может вернуть правильное начальное состояние, что является самым быстрым способом отображения контента пользователям. Но сайты, использующие клиентский код для создания страниц, могут потребовать дополнительную функцию для инициализации страницы.
  2. API навигации работает только в пределах одного фрейма — главной страницы или одного конкретного <iframe>. Это имеет некоторые интересные последствия, которые документированы в спецификации, но на практике это уменьшит путаницу у разработчиков. Предыдущий API истории History API имеет несколько запутанных особых случаев, таких как поддержка фреймов, которые API навигации обрабатывает заранее.
  3. В настоящее время вы не можете использовать API навигации для программированного изменения или перестановки списка истории. Это может быть полезно для временного состояния, например, перенаправления пользователя на временный модальный диалог, который запрашивает у него информацию, а затем возвращает к предыдущему URL. В этом случае вы захотите удалить запись временного модального диалога в истории навигации, чтобы пользователь не мог нарушить поток приложения, нажав кнопку «вперед» и снова открыв его.

Интерфейсы

NavigateEvent Экспериментальный

Объект события для события navigate, которое срабатывает при инициировании любого типа навигации любого типа навигации. Он предоставляет доступ к информации об этой навигации, и, прежде всего, к intercept(), что позволяет вам контролировать то, что происходит при инициировании навигации.

Navigation Экспериментальный

Позволяет управлять всеми действиями навигации для текущего window в одном централизованном месте, включая инициирование навигации программно, изучение записей истории навигации и управление навигацией во время ее выполнения.

NavigationActivation Экспериментальный

Представляет недавнюю навигацию между документами. Она содержит тип навигации и текущие и целевые записи истории документов.

NavigationCurrentEntryChangeEvent Экспериментальный

Объект события для события currententrychange, которое срабатывает при изменении Navigation.currentEntry. Он предоставляет доступ к типу навигации и предыдущей записи истории, из которой происходила навигация.

NavigationDestination Экспериментальный

Представляет конечную точку, к которой происходит навигация в текущей навигации.

NavigationHistoryEntry Экспериментальный

Представляет отдельную запись истории навигации.

NavigationTransition Экспериментальный

Представляет текущую навигацию.

Расширения других интерфейсов

Window.navigation Только для чтения Экспериментальный

Возвращает текущий объект window связанный объект Navigation. Это точка входа в API навигации.

Примеры

Примечание: Ознакомьтесь с живым демо API навигации Domenic Denicola.

Обработка навигации с помощью intercept()

navigation.addEventListener("navigate", (event) => {
  // Exit early if this navigation shouldn't be intercepted,
  // e.g. if the navigation is cross-origin, or a download request
  if (shouldNotIntercept(event)) {
    return;
  }

  const url = new URL(event.destination.url);

  if (url.pathname.startsWith("/articles/")) {
    event.intercept({
      async handler() {
        // The URL has already changed, so show a placeholder while
        // fetching the new content, such as a spinner or loading page
        renderArticlePagePlaceholder();

        // Fetch the new content and display when ready
        const articleContent = await getArticleContent(url.pathname);
        renderArticlePage(articleContent);
      },
    });
  }
});

Обработка прокрутки с помощью scroll()

В этом примере перехвата навигации функция handler() начинает с извлечения и рендеринга контента статьи, а затем извлекает и отображает дополнительный контент. Логично прокрутить страницу к основному содержанию статьи как можно скорее, как только оно станет доступно, чтобы пользователь мог взаимодействовать с ним, а не ждать, пока будет отрисован и дополнительный контент. Для этого мы добавили вызов scroll() между двумя этапами.

navigation.addEventListener("navigate", (event) => {
  if (shouldNotIntercept(event)) {
    return;
  }
  const url = new URL(event.destination.url);

  if (url.pathname.startsWith("/articles/")) {
    event.intercept({
      async handler() {
        const articleContent = await getArticleContent(url.pathname);
        renderArticlePage(articleContent);

        event.scroll();

        const secondaryContent = await getSecondaryContent(url.pathname);
        addSecondaryContent(secondaryContent);
      },
    });
  }
});

Переход к определённой записи истории

// On JS startup, get the key of the first loaded page
// so the user can always go back there.
const { key } = navigation.currentEntry;
backToHomeButton.onclick = () => navigation.traverseTo(key);

// Navigate away, but the button will always work.
await navigation.navigate("/another_url").finished;

Обновление состояния

navigation.navigate(url, { state: newState });

Или

navigation.reload({ state: newState });

Или, если изменение состояния независимо от навигации или перезагрузки:

navigation.updateCurrentEntry({ state: newState });

Спецификации

Спецификация
HTML
# navigation-api

Совместимость с браузерами

Рабочие столы Мобильные устройства
Chrome Edge Firefox Opera Safari Chrome Android Firefox для Android Opera Android Safari на iOS Samsung Internet WebView Android
Navigation_API 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
finished 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
from 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
navigationType 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
Рабочий стол Мобильный
Chrome Edge Firefox Opera Safari Chrome Android Firefox для Android Opera Android Safari на IOS Samsung Internet WebView Android
Navigation_API 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
dispose_event 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
getState 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
id 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
index 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
key 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
sameDocument 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
url 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
Рабочий стол Мобильный
Chrome Edge Firefox Opera Safari Chrome Android Firefox для Android Opera Android Safari на IOS Samsung Internet WebView Android
Navigation_API 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
getState 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
id 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
index 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
key 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
sameDocument 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
url 102 102 Нет 88 Нет 102 Нет 70 Нет 19.0 102
Настольный компьютер Мобильный
Chrome Edge Firefox Opera Safari Chrome Android Firefox for Android Opera Android Safari на IOS Samsung Internet WebView Android
Navigation_API 102 102 No 88 No 102 No 70 No 19.0 102
activation 123 123 No 109 No 123 No 82 No 27.0 123
back 102 102 No 88 No 102 No 70 No 19.0 102
canGoBack 102 102 No 88 No 102 No 70 No 19.0 102
canGoForward 102 102 No 88 No 102 No 70 No 19.0 102
currentEntry 102 102 No 88 No 102 No 70 No 19.0 102
currententrychange_event 102 102 No 88 No 102 No 70 No 19.0 102
entries 102 102 No 88 No 102 No 70 No 19.0 102
forward 102 102 No 88 No 102 No 70 No 19.0 102
navigate 102 102 No 88 No 102 No 70 No 19.0 102
navigate_event 102 102 No 88 No 102 No 70 No 19.0 102
navigateerror_event 102 102 No 88 No 102 No 70 No 19.0 102
navigatesuccess_event 102 102 No 88 No 102 No 70 No 19.0 102
reload 102 102 No 88 No 102 No 70 No 19.0 102
transition 102 102 No 88 No 102 No 70 No 19.0 102
traverseTo 102 102 No 88 No 102 No 70 No 19.0 102
updateCurrentEntry 102 102 No 88 No 102 No 70 No 19.0 102

api.Navigation

Таблицы BCD загружаются только в браузере

api.NavigationDestination

Таблицы BCD загружаются только в браузере

api.NavigationHistoryEntry

Таблицы BCD загружаются только в браузере

api.NavigationTransition

Таблицы BCD загружаются только в браузере

См. также

  • Современная маршрутизация на стороне клиента: API навигации
  • Пояснение к API навигации

© 2005–2024 MDN contributors.
Licensed under the Creative Commons Attribution-ShareAlike License v2.5 or later.
https://developer.mozilla.org/en-US/docs/Web/API/Navigation_API

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API