Обновлять

Вы опубликовали свое PWA: некоторые пользователи используют его из браузера, другие устанавливают на свои устройства. При обновлении приложения важно применять лучшие практики, чтобы избежать ошибок.

Вы можете обновить:

  • Данные приложения.
  • Ресурсы, уже кэшированные на устройствах.
  • Рабочий файл службы или его зависимости.
  • Метаданные манифеста.

Давайте рассмотрим лучшие практики для каждого из этих элементов.

Обновление данных

Чтобы обновить данные, например хранящиеся в IndexedDB, вы можете использовать такие инструменты, как Fetch, WebRTC или WebSockets API. Если ваше приложение поддерживает какие-либо офлайн-функции, не забудьте также обновлять данные, поддерживающие эти функции.

В совместимых браузерах есть возможность синхронизировать данные не только когда пользователь открывает PWA, но и в фоновом режиме. Эти варианты:

  • Фоновая синхронизация : сохраняет неудачные запросы и повторяет их с помощью синхронизации от сервис-воркера.
  • Периодическая фоновая веб-синхронизация : данные периодически синхронизируются в фоновом режиме в определенное время, позволяя приложению предоставлять обновленные данные, даже если пользователь еще не открыл приложение.
  • Фоновая выборка : загружает большие файлы, даже когда PWA закрыт.
  • Web push : отправляет сообщение с сервера, которое пробуждает сервисного работника и уведомляет пользователя. Обычно это называется «push-уведомлением». Для этого API требуется разрешение пользователя.

Все эти API выполняются из контекста сервисного работника. В настоящее время они доступны только в браузерах на базе Chromium, в операционных системах Android и настольных компьютерах. Используя один из этих API, вы можете запускать код в рабочем потоке службы; например, чтобы загрузить данные с вашего сервера и обновить данные IndexedDB.

Обновление ресурсов

Обновление ресурсов включает любые изменения в файлах, которые вы используете для рендеринга интерфейса приложения, таких как HTML, CSS, JavaScript и изображения. Например, изменение логики вашего приложения, изображения, являющегося частью вашего интерфейса, или таблицы стилей CSS.

Обновление шаблонов

Вот несколько распространенных шаблонов обработки обновлений приложений, но вы всегда можете настроить процесс в соответствии со своими потребностями:

  • Полное обновление: каждое изменение, даже незначительное, приводит к замене всего содержимого кэша. Этот шаблон имитирует то, как приложения для конкретных устройств обрабатывают обновления, и он будет потреблять больше полосы пропускания и занимать больше времени.
  • Обновление измененных ресурсов: в кеше заменяются только те ресурсы, которые изменились с момента последнего обновления. Часто это реализуется с помощью такой библиотеки, как Workbox . Он включает в себя создание списка кэшированных файлов, хеш-представления файла и временных меток. Используя эту информацию, сервис-воркер сравнивает этот список с кэшированными активами и решает, какие активы обновить.
  • Обновление отдельных активов: каждый актив обновляется индивидуально при его изменении. Стратегия устаревшей при повторной проверке, описанная в главе «Обслуживание», является примером индивидуального обновления активов.

Когда обновлять

Еще одна хорошая практика — найти подходящее время для проверки наличия обновлений и их применения. Вот несколько вариантов:

  • Когда сервисный работник просыпается. В этот момент нет событий для прослушивания, но браузер выполнит любой код в глобальной области действия сервис-воркера, когда он проснется.
  • В контексте главного окна вашего PWA, после того как браузер загрузил страницу, чтобы избежать замедления загрузки приложения.
  • Когда запускаются фоновые события, например, когда PWA получает push-уведомление или срабатывает фоновая синхронизация. Затем вы можете обновить свой кеш, и ваши пользователи получат новую версию ресурса при следующем открытии приложения.

Живые обновления

Вы также можете выбрать, применять ли обновление, когда приложение открыто (работает) или закрыто. При закрытом подходе приложения, даже если приложение загрузило новые ресурсы, оно не будет вносить никаких изменений и будет использовать новые версии при следующей загрузке.

Оперативное обновление означает, что как только ресурс обновляется в кеше, ваше PWA заменяет ресурс в текущей загрузке. Это сложная задача, не рассматриваемая в данном курсе. Некоторые инструменты, которые помогают реализовать это обновление, — это livereload-js и API обновления ресурсов CSS CSSStyleSheet.replace() .

Обновление сервис-воркера

Браузер запускает алгоритм обновления при изменении вашего сервис-воркера или его зависимостей. Браузер обнаруживает обновления, используя побайтовое сравнение кэшированных файлов и ресурсов, поступающих из сети.

Затем браузер пытается установить новую версию сервис-воркера, и новый сервис-воркер будет находиться в состоянии ожидания , как описано в главе Сервис-воркеры . При новой установке будет запущено событие install для нового сервисного работника. Если вы кэшируете активы в этом обработчике событий, активы также будут повторно кэшированы.

Обнаружение изменений сервис-воркера

Чтобы определить, что новый сервис-воркер готов и установлен, мы используем событие updatefound из регистрации сервис-воркера. Это событие вызывается, когда начинается установка нового сервисного работника. Нам нужно дождаться, пока его состояние изменится на installed с помощью события statechange ; см. следующее:

async function detectSWUpdate() {
  const registration = await navigator.serviceWorker.ready;

  registration.addEventListener("updatefound", event => {
    const newSW = registration.installing;
    newSW.addEventListener("statechange", event => {
      if (newSW.state == "installed") {
         // New service worker is installed, but waiting activation
      }
    });
  })
}

Принудительное переопределение

Новый сервисный работник будет установлен, но по умолчанию ожидает активации. Ожидание не позволяет новому сервисному работнику взять на себя управление старыми клиентами, которые могут быть несовместимы с новой версией.

Несмотря на то, что это не рекомендуется, новый работник службы может пропустить период ожидания и немедленно начать активацию.

self.addEventListener("install", event => {
   // forces a service worker to activate immediately
   self.skipWaiting();
  });

self.addEventListener("activate", event => {
  // when this SW becomes activated, we claim all the opened clients
  // they can be standalone PWA windows or browser tabs
  event.waitUntil(clients.claim());
});

Событие controllerchange возникает, когда изменяется сервисный работник, контролирующий текущую страницу. Например, новый работник пропустил ожидание и стал новым активным работником.

navigator.serviceWorker.addEventListener("controllerchange", event => {
   // The service worker controller has changed
 });

Обновление метаданных

Вы также можете обновить метаданные вашего приложения, которые в основном задаются в манифесте веб-приложения . Например, обновите его значок, имя или начальный URL-адрес или добавьте новую функцию, например ярлыки приложений . Но что произойдет со всеми пользователями, которые уже установили на свои устройства приложение со старой иконкой? Как и когда они получат обновленную версию?

Ответ зависит от платформы. Давайте рассмотрим доступные варианты.

Safari в браузерах iOS, iPadOS и Android

На этих платформах единственный способ получить новые метаданные манифеста — переустановить приложение из браузера.

Google Chrome на Android с WebAPK

Когда пользователь установил ваше PWA на Android с помощью Google Chrome с активированным WebAPK (большинство установок Chrome PWA), обновление будет обнаружено и применено на основе алгоритма. Подробности читайте в этой статье об обновлениях манифеста .

Некоторые дополнительные замечания о процессе:

Если пользователь не откроет ваше PWA, его WebAPK не будет обновлен. Если сервер не отвечает файлом манифеста (возникает ошибка 404), Chrome не будет проверять наличие обновлений в течение минимум 30 дней, даже если пользователь откроет PWA.

Перейдите на страницу about:webapks в Chrome на Android, чтобы увидеть статус флага «требуется обновление» и запросить обновление. В главе «Инструменты и отладка» вы можете узнать больше об этом инструменте отладки.

Интернет Samsung на Android с WebAPK

Процесс аналогичен версии Chrome. В этом случае, если манифест PWA требует обновления, в течение следующих 24 часов WebAPK будет обновлен по Wi-Fi после создания обновленного WebAPK .

Google Chrome и Microsoft Edge на рабочем столе

На настольных устройствах при запуске PWA браузер определяет, когда он в последний раз проверял локальный манифест на наличие изменений. Если манифест не просматривался с момента последнего запуска браузера или не проверялся в течение последних 24 часов, браузер выполнит сетевой запрос манифеста, а затем сравнит его с локальной копией.

Когда выбранные свойства обновляются, это запускает обновление после закрытия всех окон.

Оповещение пользователя

Некоторые стратегии обновления требуют перезагрузки или новой навигации со стороны клиентов. Вы захотите сообщить пользователю, что его ждет обновление, но дать ему возможность обновить страницу, когда ему будет лучше.

Для информирования пользователя есть следующие варианты:

  • Используйте DOM или Canvas API для отображения уведомления на экране.
  • Используйте API веб-уведомлений . Этот API является частью разрешения push-уведомлений для создания уведомления в операционной системе. Для его использования вам потребуется запросить разрешение на использование push-уведомлений, даже если вы не используете протокол push-сообщений со своего сервера. Это единственный вариант, который у нас есть, если PWA не открыт.
  • Используйте API значков , чтобы показать, что обновления доступны в установленном значке PWA.

Уведомление об обновлении, отображаемое в DOM. .

Подробнее об API бейджинга

API значков позволяет пометить значок вашего PWA номером значка или точкой значка в совместимых браузерах. Точка значка — это крошечная отметка внутри установленного значка, которая означает, что внутри приложения что-то ждет.

Пример Twitter с восемью уведомлениями и еще одним приложением со значком типа флага.

Вам нужно вызвать setAppBadge(count) для объекта navigator , чтобы установить номер значка. Вы можете сделать это из контекста окна или сервис-воркера, когда знаете, что есть обновление, чтобы предупредить пользователя.

let unreadCount = 125;
navigator.setAppBadge(unreadCount);

Чтобы очистить значок, вы вызываете clearAppBadge() для того же объекта:

navigator.clearAppBadge();

Ресурсы