> Какие события жизненного цикла HTML-страницы существуют (JavaScript)
Уровень: senior · Роль: frontend · Категория: Технические вопросы
Компании: Домклик
Стек: JavaScript
> Пример ответа
Короткий ответ
Основные события жизненного цикла HTML-страницы: DOMContentLoaded, load, beforeunload, unload, pageshow и pagehide. Также существуют события, связанные с видимостью страницы: visibilitychange, freeze и resume. Ключевое различие между DOMContentLoaded и load - момент срабатывания относительно загрузки внешних ресурсов: первое происходит после построения DOM-дерева, второе - после полной загрузки всех ресурсов (изображения, стили, скрипты).
Подробное объяснение
Жизненный цикл страницы можно разделить на три фазы: загрузка, активное использование и выгрузка.
Фаза загрузки:
DOMContentLoaded- срабатывает, когда HTML полностью распарсен и DOM-дерево построено. Стили, изображения и iframe могут ещё загружаться. Событие не ждёт async-скрипты, но ждёт defer-скрипты.load- срабатывает после полной загрузки всех ресурсов страницы: изображений, стилей, скриптов, iframe. Это последнее событие фазы загрузки.
Фаза активного использования:
pageshow- срабатывает при первом отображении страницы и при каждом возврате на неё из bfcache (back-forward cache). Свойствоevent.persistedпоказывает, была ли страница восстановлена из bfcache.pagehide- срабатывает при уходе со страницы, включая переход в bfcache. Также имеетevent.persisted.visibilitychange- срабатывает при изменении видимости страницы (переключение вкладок, сворачивание окна).document.visibilityStateпринимает значенияvisible,hidden,prerender.freezeиresume- связаны с заморозкой страницы браузером для экономии ресурсов (например, при скрытии вкладки).freezeсрабатывает послеpagehide,resume- передpageshow.
Фаза выгрузки:
beforeunload- срабатывает перед выгрузкой страницы. Используется для предупреждения пользователя о несохранённых данных. Требуетevent.preventDefault()и установкиreturnValue.unload- срабатывает при фактической выгрузке. Надёжность ограничена: браузеры могут не вызвать его при закрытии вкладки или крахе.
Важный нюанс: unload и beforeunload не срабатывают при восстановлении из bfcache, поэтому для аналитики и сохранения состояния лучше использовать pagehide и visibilitychange.
На практике
Для senior-позиции важно понимать не только порядок событий, но и практические сценарии:
-
Инициализация приложения - вешать обработчики на
DOMContentLoaded, если скрипт подключён в<head>. Если скрипт подключён сdeferили в конце<body>, событие уже не нужно - DOM готов. -
Аналитика - для отправки данных об уходе со страницы использовать
pagehideвместоunload, так какunloadненадёжен при bfcache. При этом использоватьnavigator.sendBeacon()для гарантированной отправки. -
Сохранение состояния -
visibilitychangeсdocument.visibilityState === 'hidden'- лучший момент для автосохранения черновиков, так как срабатывает при переключении вкладок. -
Предупреждение о несохранённых данных -
beforeunloadсрабатывает только при реальном уходе, но не при переключении вкладок. Для полного покрытия комбинировать сvisibilitychange. -
Восстановление из bfcache - если страница использует
pageshowсevent.persisted === true, нужно переинициализировать состояние, так как скрипты не перезапускаются, но DOM может быть изменён.
Пример кода
JAVASCRIPT// Инициализация приложенияdocument.addEventListener('DOMContentLoaded', () => {initApp();});window.addEventListener('load', () => {// Тяжёлая инициализация: графики, карты, аналитикаinitHeavyWidgets();});// Отправка аналитики при уходеwindow.addEventListener('pagehide', (event) => {if (event.persisted) {// Страница уходит в bfcache - данные сохранятсяreturn;}navigator.sendBeacon('/api/analytics', JSON.stringify({duration: performance.now()}));});// Автосохранение при скрытии вкладкиdocument.addEventListener('visibilitychange', () => {if (document.visibilityState === 'hidden') {saveDraft();}});// Восстановление из bfcachewindow.addEventListener('pageshow', (event) => {if (event.persisted) {refreshState();}});// Предупреждение о несохранённых данныхwindow.addEventListener('beforeunload', (event) => {if (hasUnsavedChanges()) {event.preventDefault();event.returnValue = '';}});
Как отвечать на собеседовании
Начните с перечисления основных событий в хронологическом порядке. Затем выделите ключевые различия: DOMContentLoaded vs load, pagehide vs unload. Покажите понимание bfcache - это сильный сигнал для senior. Обязательно упомяните visibilitychange как современную альтернативу для многих сценариев. Приведите пример из реальной практики: почему unload ненадёжен и как вы решали эту проблему. Если спросят про порядок - расскажите полную последовательность для типичной загрузки: DOMContentLoaded → load → (активное использование) → pagehide → freeze → (восстановление) → resume → pageshow.
Что проверяет интервьюер
Интервьюер оценивает:
- понимание разницы между событиями загрузки и выгрузки;
- знание bfcache и его влияния на жизненный цикл;
- умение выбирать правильное событие для конкретной задачи;
- осведомлённость о современных API (
sendBeacon,visibilitychange); - способность объяснить edge cases: что происходит при закрытии вкладки, переключении, восстановлении из кэша.
Типичные ошибки
- Путаница между
DOMContentLoadedиload- утверждение, чтоloadсрабатывает после всех скриптов, но это верно лишь частично:loadждёт все ресурсы, включая изображения. - Использование
unloadдля аналитики - ненадёжно из-за bfcache и ограничений браузера. - Игнорирование
pageshowсevent.persisted- при восстановлении из bfcache скрипты не перезапускаются, но состояние может быть устаревшим. - Утверждение, что
beforeunloadсрабатывает при переключении вкладок - это не так, для этого нуженvisibilitychange. - Забывают про
freezeиresume- эти события важны для мобильных браузеров и экономии ресурсов.
> Похожие задачи по frontend
Как работают call stack, callback queue, event loop, микротаски и макротаски в JavaScript
В чем разница между стрелочной и обычной функцией в контексте this в JavaScript?
Как определить, что элемент находится в viewport в JavaScript
В чем разница XML и JSON
> ГОТОВЫ К СЛЕДУЮЩЕМУ СОБЕСЕДОВАНИЮ?
Запустите тренировочную сессию с ИИ и получите детальную обратную связь, чтобы увереннее проходить реальные интервью