Библиотека Workbox предоставляет мощные средства для управления кэшированием ресурсов в приложениях на JavaScript. Одним из важных аспектов оптимизации работы сервис-воркеров является контроль объема кэша и числа хранимых записей. Избыточное накопление кэша может привести к замедлению работы приложения, переполнению памяти устройства и нежелательным побочным эффектам при обновлениях ресурсов. Workbox предлагает встроенные механизмы для ограничения количества записей в кэше, что делает управление кэшированием предсказуемым и безопасным.
В Workbox для ограничения числа элементов в кэше используется объект
ExpirationPlugin из пакета
workbox-expiration. Основная функция этого плагина —
контролировать время хранения записей и максимальное количество
элементов в кэше.
Пример базовой конфигурации:
import { registerRoute } from 'workbox-routing';
import { CacheFirst } from 'workbox-strategies';
import { ExpirationPlugin } from 'workbox-expiration';
registerRoute(
({ request }) => request.destination === 'image',
new CacheFirst({
cacheName: 'images-cache',
plugins: [
new ExpirationPlugin({
maxEntries: 50, // Максимальное количество записей в кэше
maxAgeSeconds: 30 * 24 * 60 * 60, // Время жизни записи в секундах (30 дней)
purgeOnQuotaError: true, // Автоматическая очистка при нехватке места
}),
],
})
);
В этом примере:
maxEntries ограничивает число кэшированных изображений
до 50. Если добавляется новый элемент, а лимит достигнут, Workbox
удаляет наименее недавно использованные записи (LRU —
Least Recently Used).maxAgeSeconds устанавливает срок хранения кэша. После
его истечения запись считается устаревшей и подлежит удалению.purgeOnQuotaError активирует автоматическую очистку
кэша при нехватке дискового пространства, предотвращая ошибки
записи.1. CacheFirst
Стратегия CacheFirst извлекает ресурсы из кэша, если они
там есть, и загружает их с сети только при отсутствии кэшированной
копии. Ограничение количества записей здесь предотвращает бесконтрольный
рост кэша:
new CacheFirst({
cacheName: 'static-resources',
plugins: [
new ExpirationPlugin({ maxEntries: 100 })
],
});
2. NetworkFirst
Стратегия NetworkFirst запрашивает ресурс с сети и
только при её недоступности возвращает кэшированную версию. Даже здесь
ограничение количества записей важно для предотвращения переполнения
кэша:
import { NetworkFirst } from 'workbox-strategies';
registerRoute(
({ request }) => request.destination === 'document',
new NetworkFirst({
cacheName: 'html-cache',
plugins: [
new ExpirationPlugin({ maxEntries: 20 })
],
})
);
3. StaleWhileRevalidate
Стратегия StaleWhileRevalidate отдаёт старую копию кэша
мгновенно, параллельно обновляя её с сети. Плагин
ExpirationPlugin обеспечивает контроль над количеством и
сроком хранения устаревших данных:
import { StaleWhileRevalidate } from 'workbox-strategies';
registerRoute(
({ request }) => request.destination === 'script',
new StaleWhileRevalidate({
cacheName: 'scripts-cache',
plugins: [
new ExpirationPlugin({ maxEntries: 30 })
],
})
);
ExpirationPluginmaxEntries.maxAgeSeconds: можно
одновременно ограничивать количество и возраст записей. Старые элементы
будут удаляться даже при недостатке объема.Иногда требуется не просто ограничить количество, а управлять кэшем программно. Workbox позволяет это делать через API кэширования:
const cacheName = 'dynamic-cache';
const maxEntries = 50;
async function cleanUpCache() {
const cache = await caches.open(cacheName);
const keys = await cache.keys();
if (keys.length > maxEntries) {
const excess = keys.length - maxEntries;
for (let i = 0; i < excess; i++) {
await cache.delete(keys[i]);
}
}
}
Такой подход может использоваться совместно с стратегиями Workbox для тонкой настройки кэширования нестандартных данных.
CacheFirst с maxEntries и
maxAgeSeconds.NetworkFirst и лимит на количество записей.purgeOnQuotaError, особенно для
мобильных устройств, чтобы избежать проблем при переполнении
памяти.Ограничение количества записей в кэше позволяет поддерживать баланс между производительностью приложения и использованием ресурсов устройства, обеспечивая предсказуемое поведение сервис-воркеров.