Сервисные работники и модель оболочки приложения

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

Схема оболочки приложения. Это снимок экрана веб-страницы с заголовком вверху и областью содержимого внизу. Заголовок помечен как «Оболочка приложения», а нижний — как «Содержимое».

Оболочка приложения играет важную роль в воспринимаемой производительности веб-приложения. Это первое, что загружается, и, следовательно, это также первое, что видят пользователи, пока они ждут, пока контент заполнит пользовательский интерфейс.

Хотя оболочка приложения загружается быстро (при условии, что сеть доступна и хотя бы немного быстрее), сервис-воркер, который пр��дварительно кэширует оболочку приложения и связанные с ней ресурсы, дает модели оболочки приложения следующие дополнительные преимущества:

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

Когда следует использовать модель оболочки приложения

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

Если это описывает ваш проект и вы хотите добавить сервисного работника для повышения его надежности и производительности, оболочка приложения должна:

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

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

Создание оболочки приложения

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

Правильный баланс зависит от вашего приложения. Оболочка приложения Trained To Thrill Джейка Арчибальда включает заголовок с кнопкой обновления для получения нового контента с Flickr.

Снимок экрана веб-приложения Trained to Thrill в двух разных состояниях. Слева видна только оболочка кэшированного приложения без заполнения содержимого. Справа контент (несколько изображений некоторых поездов) динамически загружается в область содержимого оболочки приложения.

Разметка оболочки приложения будет варьироваться от проекта к проекту, но вот один пример файла index.html , который предоставляет шаблон приложения:

​​<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>
      Application Shell Example
    </title>
    <link rel="manifest" href="/manifest.json">
    <meta name="viewport" content="width=device-width,initial-scale=1.0">
    <link rel="stylesheet" type="text/css" href="styles/global.css">
  </head>
  <body>
    <header class="header">
      <!-- Application header -->
      <h1 class="header__title">Application Shell Example</h1>
    </header>

    <nav class="nav">
      <!-- Navigation items -->
    </nav>

    <main id="app">
      <!-- Where the application content populates -->
    </main>

    <div class="loader">
      <!-- Spinner/content placeholders -->
    </div>

    <!-- Critical application shell logic -->
    <script src="app.js"></script>

    <!-- Service worker registration script -->
    <script>
      if ('serviceWorker' in navigator) {
        // Register a service worker after the load event
        window.addEventListener('load', () => {
          navigator.serviceWorker.register('/sw.js');
        });
      }
    </script>
  </body>
</html>

Как бы вы ни создавали оболочку приложения для своего проекта, она должна иметь следующие характеристики:

  • HTML должен иметь четко изолированные области для отдельных элементов пользовательского интерфейса. В приведенном выше примере это включает заголовок приложения, навигацию, область основного содержимого и место для «спиннера» загрузки, который появляется только при загрузке содержимого.
  • Исходный код JavaScript и CSS, загружаемый для оболочки приложения, должен быть минимальным и относиться только к функциональности самой оболочки приложения, а не к содержимому. Это гарантирует, что приложение отображает свою оболочку как можно быстрее и сводит к минимуму работу основного потока до тех пор, пока не появится содержимое.
  • Встроенный скрипт, который регистрирует сервисного работника.

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

Кэширование оболочки приложения

Оболочка приложения и ее необходимые ресурсы — это то, что сервисный работник должен предварительно кэшировать сразу во время установки. Предположим, что оболочка приложения подобна приведенному выше примеру, давайте посмотрим, как это можно сделать в базовом примере Workbox с помощью workbox-build :

// build-sw.js
import {generateSW} from 'workbox-build';

// Where the generated service worker will be written to:
const swDest = './dist/sw.js';

generateSW({
  swDest,
  globDirectory: './dist',
  globPatterns: [
    // The necessary CSS and JS for the app shell
    '**/*.js',
    '**/*.css',
    // The app shell itself
    'shell.html'
  ],
  // All navigations for URLs not precached will use this HTML
  navigateFallback: 'shell.html'
}).then(({count, size}) => {
  console.log(`Generated ${swDest}, which precaches ${count} assets totaling ${size} bytes.`);
});

Эта конфигурация, хранящаяся в build-sw.js импортирует CSS и JavaScript приложения, включая файл разметки оболочки приложения, содержащийся в shell.html . Скрипт выполняется с помощью Node следующим образом:

node build-sw.js

Созданный сервис-воркер записывается в ./dist/sw.js и по завершении записывает следующее сообщение:

Generated ./dist/sw.js, which precaches 5 assets totaling 44375 bytes.

Когда страница загружается, сервис-воркер предварительно кэширует разметку оболочки приложения и ее зависимости:

Снимок экрана сетевой панели в Chrome DevTools, показывающий список ресурсов, загруженных из сети. Ресурсы, предварительно кэшированные сервисным работником, отличаются от других активов шестеренкой слева в строке. Некоторые файлы JavaScript и CSS предварительно кэшируются сервисным работником во время установки.
Service Worker предварительно кэширует зависимости оболочки приложения во время установки. Запросы предварительного кэширования — это последние две строки, а значок шестеренки рядом с запросом указывает, что сервисный работник обработал запрос.

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

Заключение

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