{"version":3,"file":"sw.mjs","sources":["../node_modules/workbox-core/_version.js","../node_modules/workbox-core/models/messages/messageGenerator.js","../node_modules/workbox-core/_private/WorkboxError.js","../node_modules/workbox-core/_private/getFriendlyURL.js","../node_modules/workbox-cacheable-response/_version.js","../node_modules/workbox-cacheable-response/CacheableResponse.js","../node_modules/workbox-cacheable-response/CacheableResponsePlugin.js","../node_modules/workbox-core/_private/dontWaitFor.js","../node_modules/idb/build/wrap-idb-value.js","../node_modules/idb/build/index.js","../node_modules/workbox-expiration/_version.js","../node_modules/workbox-expiration/models/CacheTimestampsModel.js","../node_modules/workbox-expiration/CacheExpiration.js","../node_modules/workbox-core/_private/cacheNames.js","../node_modules/workbox-core/models/quotaErrorCallbacks.js","../node_modules/workbox-core/registerQuotaErrorCallback.js","../node_modules/workbox-expiration/ExpirationPlugin.js","../node_modules/workbox-routing/_version.js","../node_modules/workbox-routing/utils/constants.js","../node_modules/workbox-routing/utils/normalizeHandler.js","../node_modules/workbox-routing/Route.js","../node_modules/workbox-routing/RegExpRoute.js","../node_modules/workbox-routing/Router.js","../node_modules/workbox-routing/utils/getOrCreateDefaultRouter.js","../node_modules/workbox-routing/registerRoute.js","../node_modules/workbox-core/_private/cacheMatchIgnoreParams.js","../node_modules/workbox-core/_private/Deferred.js","../node_modules/workbox-core/_private/executeQuotaErrorCallbacks.js","../node_modules/workbox-core/_private/timeout.js","../node_modules/workbox-strategies/_version.js","../node_modules/workbox-strategies/StrategyHandler.js","../node_modules/workbox-strategies/Strategy.js","../node_modules/workbox-strategies/CacheFirst.js","../node_modules/workbox-strategies/plugins/cacheOkAndOpaquePlugin.js","../node_modules/workbox-strategies/NetworkFirst.js","../node_modules/workbox-strategies/StaleWhileRevalidate.js","../public/sw.js"],"sourcesContent":["\"use strict\";\n// @ts-ignore\ntry {\n    self['workbox:core:7.0.0'] && _();\n}\ncatch (e) { }\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { messages } from './messages.js';\nimport '../../_version.js';\nconst fallback = (code, ...args) => {\n    let msg = code;\n    if (args.length > 0) {\n        msg += ` :: ${JSON.stringify(args)}`;\n    }\n    return msg;\n};\nconst generatorFunction = (code, details = {}) => {\n    const message = messages[code];\n    if (!message) {\n        throw new Error(`Unable to find message for code '${code}'.`);\n    }\n    return message(details);\n};\nexport const messageGenerator = process.env.NODE_ENV === 'production' ? fallback : generatorFunction;\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { messageGenerator } from '../models/messages/messageGenerator.js';\nimport '../_version.js';\n/**\n * Workbox errors should be thrown with this class.\n * This allows use to ensure the type easily in tests,\n * helps developers identify errors from workbox\n * easily and allows use to optimise error\n * messages correctly.\n *\n * @private\n */\nclass WorkboxError extends Error {\n    /**\n     *\n     * @param {string} errorCode The error code that\n     * identifies this particular error.\n     * @param {Object=} details Any relevant arguments\n     * that will help developers identify issues should\n     * be added as a key on the context object.\n     */\n    constructor(errorCode, details) {\n        const message = messageGenerator(errorCode, details);\n        super(message);\n        this.name = errorCode;\n        this.details = details;\n    }\n}\nexport { WorkboxError };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\nconst getFriendlyURL = (url) => {\n    const urlObj = new URL(String(url), location.href);\n    // See https://github.com/GoogleChrome/workbox/issues/2323\n    // We want to include everything, except for the origin if it's same-origin.\n    return urlObj.href.replace(new RegExp(`^${location.origin}`), '');\n};\nexport { getFriendlyURL };\n","\"use strict\";\n// @ts-ignore\ntry {\n    self['workbox:cacheable-response:7.0.0'] && _();\n}\ncatch (e) { }\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { getFriendlyURL } from 'workbox-core/_private/getFriendlyURL.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport './_version.js';\n/**\n * This class allows you to set up rules determining what\n * status codes and/or headers need to be present in order for a\n * [`Response`](https://developer.mozilla.org/en-US/docs/Web/API/Response)\n * to be considered cacheable.\n *\n * @memberof workbox-cacheable-response\n */\nclass CacheableResponse {\n    /**\n     * To construct a new CacheableResponse instance you must provide at least\n     * one of the `config` properties.\n     *\n     * If both `statuses` and `headers` are specified, then both conditions must\n     * be met for the `Response` to be considered cacheable.\n     *\n     * @param {Object} config\n     * @param {Array<number>} [config.statuses] One or more status codes that a\n     * `Response` can have and be considered cacheable.\n     * @param {Object<string,string>} [config.headers] A mapping of header names\n     * and expected values that a `Response` can have and be considered cacheable.\n     * If multiple headers are provided, only one needs to be present.\n     */\n    constructor(config = {}) {\n        if (process.env.NODE_ENV !== 'production') {\n            if (!(config.statuses || config.headers)) {\n                throw new WorkboxError('statuses-or-headers-required', {\n                    moduleName: 'workbox-cacheable-response',\n                    className: 'CacheableResponse',\n                    funcName: 'constructor',\n                });\n            }\n            if (config.statuses) {\n                assert.isArray(config.statuses, {\n                    moduleName: 'workbox-cacheable-response',\n                    className: 'CacheableResponse',\n                    funcName: 'constructor',\n                    paramName: 'config.statuses',\n                });\n            }\n            if (config.headers) {\n                assert.isType(config.headers, 'object', {\n                    moduleName: 'workbox-cacheable-response',\n                    className: 'CacheableResponse',\n                    funcName: 'constructor',\n                    paramName: 'config.headers',\n                });\n            }\n        }\n        this._statuses = config.statuses;\n        this._headers = config.headers;\n    }\n    /**\n     * Checks a response to see whether it's cacheable or not, based on this\n     * object's configuration.\n     *\n     * @param {Response} response The response whose cacheability is being\n     * checked.\n     * @return {boolean} `true` if the `Response` is cacheable, and `false`\n     * otherwise.\n     */\n    isResponseCacheable(response) {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(response, Response, {\n                moduleName: 'workbox-cacheable-response',\n                className: 'CacheableResponse',\n                funcName: 'isResponseCacheable',\n                paramName: 'response',\n            });\n        }\n        let cacheable = true;\n        if (this._statuses) {\n            cacheable = this._statuses.includes(response.status);\n        }\n        if (this._headers && cacheable) {\n            cacheable = Object.keys(this._headers).some((headerName) => {\n                return response.headers.get(headerName) === this._headers[headerName];\n            });\n        }\n        if (process.env.NODE_ENV !== 'production') {\n            if (!cacheable) {\n                logger.groupCollapsed(`The request for ` +\n                    `'${getFriendlyURL(response.url)}' returned a response that does ` +\n                    `not meet the criteria for being cached.`);\n                logger.groupCollapsed(`View cacheability criteria here.`);\n                logger.log(`Cacheable statuses: ` + JSON.stringify(this._statuses));\n                logger.log(`Cacheable headers: ` + JSON.stringify(this._headers, null, 2));\n                logger.groupEnd();\n                const logFriendlyHeaders = {};\n                response.headers.forEach((value, key) => {\n                    logFriendlyHeaders[key] = value;\n                });\n                logger.groupCollapsed(`View response status and headers here.`);\n                logger.log(`Response status: ${response.status}`);\n                logger.log(`Response headers: ` + JSON.stringify(logFriendlyHeaders, null, 2));\n                logger.groupEnd();\n                logger.groupCollapsed(`View full response details here.`);\n                logger.log(response.headers);\n                logger.log(response);\n                logger.groupEnd();\n                logger.groupEnd();\n            }\n        }\n        return cacheable;\n    }\n}\nexport { CacheableResponse };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { CacheableResponse, } from './CacheableResponse.js';\nimport './_version.js';\n/**\n * A class implementing the `cacheWillUpdate` lifecycle callback. This makes it\n * easier to add in cacheability checks to requests made via Workbox's built-in\n * strategies.\n *\n * @memberof workbox-cacheable-response\n */\nclass CacheableResponsePlugin {\n    /**\n     * To construct a new CacheableResponsePlugin instance you must provide at\n     * least one of the `config` properties.\n     *\n     * If both `statuses` and `headers` are specified, then both conditions must\n     * be met for the `Response` to be considered cacheable.\n     *\n     * @param {Object} config\n     * @param {Array<number>} [config.statuses] One or more status codes that a\n     * `Response` can have and be considered cacheable.\n     * @param {Object<string,string>} [config.headers] A mapping of header names\n     * and expected values that a `Response` can have and be considered cacheable.\n     * If multiple headers are provided, only one needs to be present.\n     */\n    constructor(config) {\n        /**\n         * @param {Object} options\n         * @param {Response} options.response\n         * @return {Response|null}\n         * @private\n         */\n        this.cacheWillUpdate = async ({ response }) => {\n            if (this._cacheableResponse.isResponseCacheable(response)) {\n                return response;\n            }\n            return null;\n        };\n        this._cacheableResponse = new CacheableResponse(config);\n    }\n}\nexport { CacheableResponsePlugin };\n","/*\n  Copyright 2019 Google LLC\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\n/**\n * A helper function that prevents a promise from being flagged as unused.\n *\n * @private\n **/\nexport function dontWaitFor(promise) {\n    // Effective no-op.\n    void promise.then(() => { });\n}\n","const instanceOfAny = (object, constructors) => constructors.some((c) => object instanceof c);\n\nlet idbProxyableTypes;\nlet cursorAdvanceMethods;\n// This is a function to prevent it throwing up in node environments.\nfunction getIdbProxyableTypes() {\n    return (idbProxyableTypes ||\n        (idbProxyableTypes = [\n            IDBDatabase,\n            IDBObjectStore,\n            IDBIndex,\n            IDBCursor,\n            IDBTransaction,\n        ]));\n}\n// This is a function to prevent it throwing up in node environments.\nfunction getCursorAdvanceMethods() {\n    return (cursorAdvanceMethods ||\n        (cursorAdvanceMethods = [\n            IDBCursor.prototype.advance,\n            IDBCursor.prototype.continue,\n            IDBCursor.prototype.continuePrimaryKey,\n        ]));\n}\nconst cursorRequestMap = new WeakMap();\nconst transactionDoneMap = new WeakMap();\nconst transactionStoreNamesMap = new WeakMap();\nconst transformCache = new WeakMap();\nconst reverseTransformCache = new WeakMap();\nfunction promisifyRequest(request) {\n    const promise = new Promise((resolve, reject) => {\n        const unlisten = () => {\n            request.removeEventListener('success', success);\n            request.removeEventListener('error', error);\n        };\n        const success = () => {\n            resolve(wrap(request.result));\n            unlisten();\n        };\n        const error = () => {\n            reject(request.error);\n            unlisten();\n        };\n        request.addEventListener('success', success);\n        request.addEventListener('error', error);\n    });\n    promise\n        .then((value) => {\n        // Since cursoring reuses the IDBRequest (*sigh*), we cache it for later retrieval\n        // (see wrapFunction).\n        if (value instanceof IDBCursor) {\n            cursorRequestMap.set(value, request);\n        }\n        // Catching to avoid \"Uncaught Promise exceptions\"\n    })\n        .catch(() => { });\n    // This mapping exists in reverseTransformCache but doesn't doesn't exist in transformCache. This\n    // is because we create many promises from a single IDBRequest.\n    reverseTransformCache.set(promise, request);\n    return promise;\n}\nfunction cacheDonePromiseForTransaction(tx) {\n    // Early bail if we've already created a done promise for this transaction.\n    if (transactionDoneMap.has(tx))\n        return;\n    const done = new Promise((resolve, reject) => {\n        const unlisten = () => {\n            tx.removeEventListener('complete', complete);\n            tx.removeEventListener('error', error);\n            tx.removeEventListener('abort', error);\n        };\n        const complete = () => {\n            resolve();\n            unlisten();\n        };\n        const error = () => {\n            reject(tx.error || new DOMException('AbortError', 'AbortError'));\n            unlisten();\n        };\n        tx.addEventListener('complete', complete);\n        tx.addEventListener('error', error);\n        tx.addEventListener('abort', error);\n    });\n    // Cache it for later retrieval.\n    transactionDoneMap.set(tx, done);\n}\nlet idbProxyTraps = {\n    get(target, prop, receiver) {\n        if (target instanceof IDBTransaction) {\n            // Special handling for transaction.done.\n            if (prop === 'done')\n                return transactionDoneMap.get(target);\n            // Polyfill for objectStoreNames because of Edge.\n            if (prop === 'objectStoreNames') {\n                return target.objectStoreNames || transactionStoreNamesMap.get(target);\n            }\n            // Make tx.store return the only store in the transaction, or undefined if there are many.\n            if (prop === 'store') {\n                return receiver.objectStoreNames[1]\n                    ? undefined\n                    : receiver.objectStore(receiver.objectStoreNames[0]);\n            }\n        }\n        // Else transform whatever we get back.\n        return wrap(target[prop]);\n    },\n    set(target, prop, value) {\n        target[prop] = value;\n        return true;\n    },\n    has(target, prop) {\n        if (target instanceof IDBTransaction &&\n            (prop === 'done' || prop === 'store')) {\n            return true;\n        }\n        return prop in target;\n    },\n};\nfunction replaceTraps(callback) {\n    idbProxyTraps = callback(idbProxyTraps);\n}\nfunction wrapFunction(func) {\n    // Due to expected object equality (which is enforced by the caching in `wrap`), we\n    // only create one new func per func.\n    // Edge doesn't support objectStoreNames (booo), so we polyfill it here.\n    if (func === IDBDatabase.prototype.transaction &&\n        !('objectStoreNames' in IDBTransaction.prototype)) {\n        return function (storeNames, ...args) {\n            const tx = func.call(unwrap(this), storeNames, ...args);\n            transactionStoreNamesMap.set(tx, storeNames.sort ? storeNames.sort() : [storeNames]);\n            return wrap(tx);\n        };\n    }\n    // Cursor methods are special, as the behaviour is a little more different to standard IDB. In\n    // IDB, you advance the cursor and wait for a new 'success' on the IDBRequest that gave you the\n    // cursor. It's kinda like a promise that can resolve with many values. That doesn't make sense\n    // with real promises, so each advance methods returns a new promise for the cursor object, or\n    // undefined if the end of the cursor has been reached.\n    if (getCursorAdvanceMethods().includes(func)) {\n        return function (...args) {\n            // Calling the original function with the proxy as 'this' causes ILLEGAL INVOCATION, so we use\n            // the original object.\n            func.apply(unwrap(this), args);\n            return wrap(cursorRequestMap.get(this));\n        };\n    }\n    return function (...args) {\n        // Calling the original function with the proxy as 'this' causes ILLEGAL INVOCATION, so we use\n        // the original object.\n        return wrap(func.apply(unwrap(this), args));\n    };\n}\nfunction transformCachableValue(value) {\n    if (typeof value === 'function')\n        return wrapFunction(value);\n    // This doesn't return, it just creates a 'done' promise for the transaction,\n    // which is later returned for transaction.done (see idbObjectHandler).\n    if (value instanceof IDBTransaction)\n        cacheDonePromiseForTransaction(value);\n    if (instanceOfAny(value, getIdbProxyableTypes()))\n        return new Proxy(value, idbProxyTraps);\n    // Return the same value back if we're not going to transform it.\n    return value;\n}\nfunction wrap(value) {\n    // We sometimes generate multiple promises from a single IDBRequest (eg when cursoring), because\n    // IDB is weird and a single IDBRequest can yield many responses, so these can't be cached.\n    if (value instanceof IDBRequest)\n        return promisifyRequest(value);\n    // If we've already transformed this value before, reuse the transformed value.\n    // This is faster, but it also provides object equality.\n    if (transformCache.has(value))\n        return transformCache.get(value);\n    const newValue = transformCachableValue(value);\n    // Not all types are transformed.\n    // These may be primitive types, so they can't be WeakMap keys.\n    if (newValue !== value) {\n        transformCache.set(value, newValue);\n        reverseTransformCache.set(newValue, value);\n    }\n    return newValue;\n}\nconst unwrap = (value) => reverseTransformCache.get(value);\n\nexport { reverseTransformCache as a, instanceOfAny as i, replaceTraps as r, unwrap as u, wrap as w };\n","import { w as wrap, r as replaceTraps } from './wrap-idb-value.js';\nexport { u as unwrap, w as wrap } from './wrap-idb-value.js';\n\n/**\n * Open a database.\n *\n * @param name Name of the database.\n * @param version Schema version.\n * @param callbacks Additional callbacks.\n */\nfunction openDB(name, version, { blocked, upgrade, blocking, terminated } = {}) {\n    const request = indexedDB.open(name, version);\n    const openPromise = wrap(request);\n    if (upgrade) {\n        request.addEventListener('upgradeneeded', (event) => {\n            upgrade(wrap(request.result), event.oldVersion, event.newVersion, wrap(request.transaction), event);\n        });\n    }\n    if (blocked) {\n        request.addEventListener('blocked', (event) => blocked(\n        // Casting due to https://github.com/microsoft/TypeScript-DOM-lib-generator/pull/1405\n        event.oldVersion, event.newVersion, event));\n    }\n    openPromise\n        .then((db) => {\n        if (terminated)\n            db.addEventListener('close', () => terminated());\n        if (blocking) {\n            db.addEventListener('versionchange', (event) => blocking(event.oldVersion, event.newVersion, event));\n        }\n    })\n        .catch(() => { });\n    return openPromise;\n}\n/**\n * Delete a database.\n *\n * @param name Name of the database.\n */\nfunction deleteDB(name, { blocked } = {}) {\n    const request = indexedDB.deleteDatabase(name);\n    if (blocked) {\n        request.addEventListener('blocked', (event) => blocked(\n        // Casting due to https://github.com/microsoft/TypeScript-DOM-lib-generator/pull/1405\n        event.oldVersion, event));\n    }\n    return wrap(request).then(() => undefined);\n}\n\nconst readMethods = ['get', 'getKey', 'getAll', 'getAllKeys', 'count'];\nconst writeMethods = ['put', 'add', 'delete', 'clear'];\nconst cachedMethods = new Map();\nfunction getMethod(target, prop) {\n    if (!(target instanceof IDBDatabase &&\n        !(prop in target) &&\n        typeof prop === 'string')) {\n        return;\n    }\n    if (cachedMethods.get(prop))\n        return cachedMethods.get(prop);\n    const targetFuncName = prop.replace(/FromIndex$/, '');\n    const useIndex = prop !== targetFuncName;\n    const isWrite = writeMethods.includes(targetFuncName);\n    if (\n    // Bail if the target doesn't exist on the target. Eg, getAll isn't in Edge.\n    !(targetFuncName in (useIndex ? IDBIndex : IDBObjectStore).prototype) ||\n        !(isWrite || readMethods.includes(targetFuncName))) {\n        return;\n    }\n    const method = async function (storeName, ...args) {\n        // isWrite ? 'readwrite' : undefined gzipps better, but fails in Edge :(\n        const tx = this.transaction(storeName, isWrite ? 'readwrite' : 'readonly');\n        let target = tx.store;\n        if (useIndex)\n            target = target.index(args.shift());\n        // Must reject if op rejects.\n        // If it's a write operation, must reject if tx.done rejects.\n        // Must reject with op rejection first.\n        // Must resolve with op value.\n        // Must handle both promises (no unhandled rejections)\n        return (await Promise.all([\n            target[targetFuncName](...args),\n            isWrite && tx.done,\n        ]))[0];\n    };\n    cachedMethods.set(prop, method);\n    return method;\n}\nreplaceTraps((oldTraps) => ({\n    ...oldTraps,\n    get: (target, prop, receiver) => getMethod(target, prop) || oldTraps.get(target, prop, receiver),\n    has: (target, prop) => !!getMethod(target, prop) || oldTraps.has(target, prop),\n}));\n\nexport { deleteDB, openDB };\n","\"use strict\";\n// @ts-ignore\ntry {\n    self['workbox:expiration:7.0.0'] && _();\n}\ncatch (e) { }\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { openDB, deleteDB } from 'idb';\nimport '../_version.js';\nconst DB_NAME = 'workbox-expiration';\nconst CACHE_OBJECT_STORE = 'cache-entries';\nconst normalizeURL = (unNormalizedUrl) => {\n    const url = new URL(unNormalizedUrl, location.href);\n    url.hash = '';\n    return url.href;\n};\n/**\n * Returns the timestamp model.\n *\n * @private\n */\nclass CacheTimestampsModel {\n    /**\n     *\n     * @param {string} cacheName\n     *\n     * @private\n     */\n    constructor(cacheName) {\n        this._db = null;\n        this._cacheName = cacheName;\n    }\n    /**\n     * Performs an upgrade of indexedDB.\n     *\n     * @param {IDBPDatabase<CacheDbSchema>} db\n     *\n     * @private\n     */\n    _upgradeDb(db) {\n        // TODO(philipwalton): EdgeHTML doesn't support arrays as a keyPath, so we\n        // have to use the `id` keyPath here and create our own values (a\n        // concatenation of `url + cacheName`) instead of simply using\n        // `keyPath: ['url', 'cacheName']`, which is supported in other browsers.\n        const objStore = db.createObjectStore(CACHE_OBJECT_STORE, { keyPath: 'id' });\n        // TODO(philipwalton): once we don't have to support EdgeHTML, we can\n        // create a single index with the keyPath `['cacheName', 'timestamp']`\n        // instead of doing both these indexes.\n        objStore.createIndex('cacheName', 'cacheName', { unique: false });\n        objStore.createIndex('timestamp', 'timestamp', { unique: false });\n    }\n    /**\n     * Performs an upgrade of indexedDB and deletes deprecated DBs.\n     *\n     * @param {IDBPDatabase<CacheDbSchema>} db\n     *\n     * @private\n     */\n    _upgradeDbAndDeleteOldDbs(db) {\n        this._upgradeDb(db);\n        if (this._cacheName) {\n            void deleteDB(this._cacheName);\n        }\n    }\n    /**\n     * @param {string} url\n     * @param {number} timestamp\n     *\n     * @private\n     */\n    async setTimestamp(url, timestamp) {\n        url = normalizeURL(url);\n        const entry = {\n            url,\n            timestamp,\n            cacheName: this._cacheName,\n            // Creating an ID from the URL and cache name won't be necessary once\n            // Edge switches to Chromium and all browsers we support work with\n            // array keyPaths.\n            id: this._getId(url),\n        };\n        const db = await this.getDb();\n        const tx = db.transaction(CACHE_OBJECT_STORE, 'readwrite', {\n            durability: 'relaxed',\n        });\n        await tx.store.put(entry);\n        await tx.done;\n    }\n    /**\n     * Returns the timestamp stored for a given URL.\n     *\n     * @param {string} url\n     * @return {number | undefined}\n     *\n     * @private\n     */\n    async getTimestamp(url) {\n        const db = await this.getDb();\n        const entry = await db.get(CACHE_OBJECT_STORE, this._getId(url));\n        return entry === null || entry === void 0 ? void 0 : entry.timestamp;\n    }\n    /**\n     * Iterates through all the entries in the object store (from newest to\n     * oldest) and removes entries once either `maxCount` is reached or the\n     * entry's timestamp is less than `minTimestamp`.\n     *\n     * @param {number} minTimestamp\n     * @param {number} maxCount\n     * @return {Array<string>}\n     *\n     * @private\n     */\n    async expireEntries(minTimestamp, maxCount) {\n        const db = await this.getDb();\n        let cursor = await db\n            .transaction(CACHE_OBJECT_STORE)\n            .store.index('timestamp')\n            .openCursor(null, 'prev');\n        const entriesToDelete = [];\n        let entriesNotDeletedCount = 0;\n        while (cursor) {\n            const result = cursor.value;\n            // TODO(philipwalton): once we can use a multi-key index, we\n            // won't have to check `cacheName` here.\n            if (result.cacheName === this._cacheName) {\n                // Delete an entry if it's older than the max age or\n                // if we already have the max number allowed.\n                if ((minTimestamp && result.timestamp < minTimestamp) ||\n                    (maxCount && entriesNotDeletedCount >= maxCount)) {\n                    // TODO(philipwalton): we should be able to delete the\n                    // entry right here, but doing so causes an iteration\n                    // bug in Safari stable (fixed in TP). Instead we can\n                    // store the keys of the entries to delete, and then\n                    // delete the separate transactions.\n                    // https://github.com/GoogleChrome/workbox/issues/1978\n                    // cursor.delete();\n                    // We only need to return the URL, not the whole entry.\n                    entriesToDelete.push(cursor.value);\n                }\n                else {\n                    entriesNotDeletedCount++;\n                }\n            }\n            cursor = await cursor.continue();\n        }\n        // TODO(philipwalton): once the Safari bug in the following issue is fixed,\n        // we should be able to remove this loop and do the entry deletion in the\n        // cursor loop above:\n        // https://github.com/GoogleChrome/workbox/issues/1978\n        const urlsDeleted = [];\n        for (const entry of entriesToDelete) {\n            await db.delete(CACHE_OBJECT_STORE, entry.id);\n            urlsDeleted.push(entry.url);\n        }\n        return urlsDeleted;\n    }\n    /**\n     * Takes a URL and returns an ID that will be unique in the object store.\n     *\n     * @param {string} url\n     * @return {string}\n     *\n     * @private\n     */\n    _getId(url) {\n        // Creating an ID from the URL and cache name won't be necessary once\n        // Edge switches to Chromium and all browsers we support work with\n        // array keyPaths.\n        return this._cacheName + '|' + normalizeURL(url);\n    }\n    /**\n     * Returns an open connection to the database.\n     *\n     * @private\n     */\n    async getDb() {\n        if (!this._db) {\n            this._db = await openDB(DB_NAME, 1, {\n                upgrade: this._upgradeDbAndDeleteOldDbs.bind(this),\n            });\n        }\n        return this._db;\n    }\n}\nexport { CacheTimestampsModel };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { dontWaitFor } from 'workbox-core/_private/dontWaitFor.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { CacheTimestampsModel } from './models/CacheTimestampsModel.js';\nimport './_version.js';\n/**\n * The `CacheExpiration` class allows you define an expiration and / or\n * limit on the number of responses stored in a\n * [`Cache`](https://developer.mozilla.org/en-US/docs/Web/API/Cache).\n *\n * @memberof workbox-expiration\n */\nclass CacheExpiration {\n    /**\n     * To construct a new CacheExpiration instance you must provide at least\n     * one of the `config` properties.\n     *\n     * @param {string} cacheName Name of the cache to apply restrictions to.\n     * @param {Object} config\n     * @param {number} [config.maxEntries] The maximum number of entries to cache.\n     * Entries used the least will be removed as the maximum is reached.\n     * @param {number} [config.maxAgeSeconds] The maximum age of an entry before\n     * it's treated as stale and removed.\n     * @param {Object} [config.matchOptions] The [`CacheQueryOptions`](https://developer.mozilla.org/en-US/docs/Web/API/Cache/delete#Parameters)\n     * that will be used when calling `delete()` on the cache.\n     */\n    constructor(cacheName, config = {}) {\n        this._isRunning = false;\n        this._rerunRequested = false;\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isType(cacheName, 'string', {\n                moduleName: 'workbox-expiration',\n                className: 'CacheExpiration',\n                funcName: 'constructor',\n                paramName: 'cacheName',\n            });\n            if (!(config.maxEntries || config.maxAgeSeconds)) {\n                throw new WorkboxError('max-entries-or-age-required', {\n                    moduleName: 'workbox-expiration',\n                    className: 'CacheExpiration',\n                    funcName: 'constructor',\n                });\n            }\n            if (config.maxEntries) {\n                assert.isType(config.maxEntries, 'number', {\n                    moduleName: 'workbox-expiration',\n                    className: 'CacheExpiration',\n                    funcName: 'constructor',\n                    paramName: 'config.maxEntries',\n                });\n            }\n            if (config.maxAgeSeconds) {\n                assert.isType(config.maxAgeSeconds, 'number', {\n                    moduleName: 'workbox-expiration',\n                    className: 'CacheExpiration',\n                    funcName: 'constructor',\n                    paramName: 'config.maxAgeSeconds',\n                });\n            }\n        }\n        this._maxEntries = config.maxEntries;\n        this._maxAgeSeconds = config.maxAgeSeconds;\n        this._matchOptions = config.matchOptions;\n        this._cacheName = cacheName;\n        this._timestampModel = new CacheTimestampsModel(cacheName);\n    }\n    /**\n     * Expires entries for the given cache and given criteria.\n     */\n    async expireEntries() {\n        if (this._isRunning) {\n            this._rerunRequested = true;\n            return;\n        }\n        this._isRunning = true;\n        const minTimestamp = this._maxAgeSeconds\n            ? Date.now() - this._maxAgeSeconds * 1000\n            : 0;\n        const urlsExpired = await this._timestampModel.expireEntries(minTimestamp, this._maxEntries);\n        // Delete URLs from the cache\n        const cache = await self.caches.open(this._cacheName);\n        for (const url of urlsExpired) {\n            await cache.delete(url, this._matchOptions);\n        }\n        if (process.env.NODE_ENV !== 'production') {\n            if (urlsExpired.length > 0) {\n                logger.groupCollapsed(`Expired ${urlsExpired.length} ` +\n                    `${urlsExpired.length === 1 ? 'entry' : 'entries'} and removed ` +\n                    `${urlsExpired.length === 1 ? 'it' : 'them'} from the ` +\n                    `'${this._cacheName}' cache.`);\n                logger.log(`Expired the following ${urlsExpired.length === 1 ? 'URL' : 'URLs'}:`);\n                urlsExpired.forEach((url) => logger.log(`    ${url}`));\n                logger.groupEnd();\n            }\n            else {\n                logger.debug(`Cache expiration ran and found no entries to remove.`);\n            }\n        }\n        this._isRunning = false;\n        if (this._rerunRequested) {\n            this._rerunRequested = false;\n            dontWaitFor(this.expireEntries());\n        }\n    }\n    /**\n     * Update the timestamp for the given URL. This ensures the when\n     * removing entries based on maximum entries, most recently used\n     * is accurate or when expiring, the timestamp is up-to-date.\n     *\n     * @param {string} url\n     */\n    async updateTimestamp(url) {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isType(url, 'string', {\n                moduleName: 'workbox-expiration',\n                className: 'CacheExpiration',\n                funcName: 'updateTimestamp',\n                paramName: 'url',\n            });\n        }\n        await this._timestampModel.setTimestamp(url, Date.now());\n    }\n    /**\n     * Can be used to check if a URL has expired or not before it's used.\n     *\n     * This requires a look up from IndexedDB, so can be slow.\n     *\n     * Note: This method will not remove the cached entry, call\n     * `expireEntries()` to remove indexedDB and Cache entries.\n     *\n     * @param {string} url\n     * @return {boolean}\n     */\n    async isURLExpired(url) {\n        if (!this._maxAgeSeconds) {\n            if (process.env.NODE_ENV !== 'production') {\n                throw new WorkboxError(`expired-test-without-max-age`, {\n                    methodName: 'isURLExpired',\n                    paramName: 'maxAgeSeconds',\n                });\n            }\n            return false;\n        }\n        else {\n            const timestamp = await this._timestampModel.getTimestamp(url);\n            const expireOlderThan = Date.now() - this._maxAgeSeconds * 1000;\n            return timestamp !== undefined ? timestamp < expireOlderThan : true;\n        }\n    }\n    /**\n     * Removes the IndexedDB object store used to keep track of cache expiration\n     * metadata.\n     */\n    async delete() {\n        // Make sure we don't attempt another rerun if we're called in the middle of\n        // a cache expiration.\n        this._rerunRequested = false;\n        await this._timestampModel.expireEntries(Infinity); // Expires all.\n    }\n}\nexport { CacheExpiration };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\nconst _cacheNameDetails = {\n    googleAnalytics: 'googleAnalytics',\n    precache: 'precache-v2',\n    prefix: 'workbox',\n    runtime: 'runtime',\n    suffix: typeof registration !== 'undefined' ? registration.scope : '',\n};\nconst _createCacheName = (cacheName) => {\n    return [_cacheNameDetails.prefix, cacheName, _cacheNameDetails.suffix]\n        .filter((value) => value && value.length > 0)\n        .join('-');\n};\nconst eachCacheNameDetail = (fn) => {\n    for (const key of Object.keys(_cacheNameDetails)) {\n        fn(key);\n    }\n};\nexport const cacheNames = {\n    updateDetails: (details) => {\n        eachCacheNameDetail((key) => {\n            if (typeof details[key] === 'string') {\n                _cacheNameDetails[key] = details[key];\n            }\n        });\n    },\n    getGoogleAnalyticsName: (userCacheName) => {\n        return userCacheName || _createCacheName(_cacheNameDetails.googleAnalytics);\n    },\n    getPrecacheName: (userCacheName) => {\n        return userCacheName || _createCacheName(_cacheNameDetails.precache);\n    },\n    getPrefix: () => {\n        return _cacheNameDetails.prefix;\n    },\n    getRuntimeName: (userCacheName) => {\n        return userCacheName || _createCacheName(_cacheNameDetails.runtime);\n    },\n    getSuffix: () => {\n        return _cacheNameDetails.suffix;\n    },\n};\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\n// Callbacks to be executed whenever there's a quota error.\n// Can't change Function type right now.\n// eslint-disable-next-line @typescript-eslint/ban-types\nconst quotaErrorCallbacks = new Set();\nexport { quotaErrorCallbacks };\n","/*\n  Copyright 2019 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { logger } from './_private/logger.js';\nimport { assert } from './_private/assert.js';\nimport { quotaErrorCallbacks } from './models/quotaErrorCallbacks.js';\nimport './_version.js';\n/**\n * Adds a function to the set of quotaErrorCallbacks that will be executed if\n * there's a quota error.\n *\n * @param {Function} callback\n * @memberof workbox-core\n */\n// Can't change Function type\n// eslint-disable-next-line @typescript-eslint/ban-types\nfunction registerQuotaErrorCallback(callback) {\n    if (process.env.NODE_ENV !== 'production') {\n        assert.isType(callback, 'function', {\n            moduleName: 'workbox-core',\n            funcName: 'register',\n            paramName: 'callback',\n        });\n    }\n    quotaErrorCallbacks.add(callback);\n    if (process.env.NODE_ENV !== 'production') {\n        logger.log('Registered a callback to respond to quota errors.', callback);\n    }\n}\nexport { registerQuotaErrorCallback };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { cacheNames } from 'workbox-core/_private/cacheNames.js';\nimport { dontWaitFor } from 'workbox-core/_private/dontWaitFor.js';\nimport { getFriendlyURL } from 'workbox-core/_private/getFriendlyURL.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { registerQuotaErrorCallback } from 'workbox-core/registerQuotaErrorCallback.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { CacheExpiration } from './CacheExpiration.js';\nimport './_version.js';\n/**\n * This plugin can be used in a `workbox-strategy` to regularly enforce a\n * limit on the age and / or the number of cached requests.\n *\n * It can only be used with `workbox-strategy` instances that have a\n * [custom `cacheName` property set](/web/tools/workbox/guides/configure-workbox#custom_cache_names_in_strategies).\n * In other words, it can't be used to expire entries in strategy that uses the\n * default runtime cache name.\n *\n * Whenever a cached response is used or updated, this plugin will look\n * at the associated cache and remove any old or extra responses.\n *\n * When using `maxAgeSeconds`, responses may be used *once* after expiring\n * because the expiration clean up will not have occurred until *after* the\n * cached response has been used. If the response has a \"Date\" header, then\n * a light weight expiration check is performed and the response will not be\n * used immediately.\n *\n * When using `maxEntries`, the entry least-recently requested will be removed\n * from the cache first.\n *\n * @memberof workbox-expiration\n */\nclass ExpirationPlugin {\n    /**\n     * @param {ExpirationPluginOptions} config\n     * @param {number} [config.maxEntries] The maximum number of entries to cache.\n     * Entries used the least will be removed as the maximum is reached.\n     * @param {number} [config.maxAgeSeconds] The maximum age of an entry before\n     * it's treated as stale and removed.\n     * @param {Object} [config.matchOptions] The [`CacheQueryOptions`](https://developer.mozilla.org/en-US/docs/Web/API/Cache/delete#Parameters)\n     * that will be used when calling `delete()` on the cache.\n     * @param {boolean} [config.purgeOnQuotaError] Whether to opt this cache in to\n     * automatic deletion if the available storage quota has been exceeded.\n     */\n    constructor(config = {}) {\n        /**\n         * A \"lifecycle\" callback that will be triggered automatically by the\n         * `workbox-strategies` handlers when a `Response` is about to be returned\n         * from a [Cache](https://developer.mozilla.org/en-US/docs/Web/API/Cache) to\n         * the handler. It allows the `Response` to be inspected for freshness and\n         * prevents it from being used if the `Response`'s `Date` header value is\n         * older than the configured `maxAgeSeconds`.\n         *\n         * @param {Object} options\n         * @param {string} options.cacheName Name of the cache the response is in.\n         * @param {Response} options.cachedResponse The `Response` object that's been\n         *     read from a cache and whose freshness should be checked.\n         * @return {Response} Either the `cachedResponse`, if it's\n         *     fresh, or `null` if the `Response` is older than `maxAgeSeconds`.\n         *\n         * @private\n         */\n        this.cachedResponseWillBeUsed = async ({ event, request, cacheName, cachedResponse, }) => {\n            if (!cachedResponse) {\n                return null;\n            }\n            const isFresh = this._isResponseDateFresh(cachedResponse);\n            // Expire entries to ensure that even if the expiration date has\n            // expired, it'll only be used once.\n            const cacheExpiration = this._getCacheExpiration(cacheName);\n            dontWaitFor(cacheExpiration.expireEntries());\n            // Update the metadata for the request URL to the current timestamp,\n            // but don't `await` it as we don't want to block the response.\n            const updateTimestampDone = cacheExpiration.updateTimestamp(request.url);\n            if (event) {\n                try {\n                    event.waitUntil(updateTimestampDone);\n                }\n                catch (error) {\n                    if (process.env.NODE_ENV !== 'production') {\n                        // The event may not be a fetch event; only log the URL if it is.\n                        if ('request' in event) {\n                            logger.warn(`Unable to ensure service worker stays alive when ` +\n                                `updating cache entry for ` +\n                                `'${getFriendlyURL(event.request.url)}'.`);\n                        }\n                    }\n                }\n            }\n            return isFresh ? cachedResponse : null;\n        };\n        /**\n         * A \"lifecycle\" callback that will be triggered automatically by the\n         * `workbox-strategies` handlers when an entry is added to a cache.\n         *\n         * @param {Object} options\n         * @param {string} options.cacheName Name of the cache that was updated.\n         * @param {string} options.request The Request for the cached entry.\n         *\n         * @private\n         */\n        this.cacheDidUpdate = async ({ cacheName, request, }) => {\n            if (process.env.NODE_ENV !== 'production') {\n                assert.isType(cacheName, 'string', {\n                    moduleName: 'workbox-expiration',\n                    className: 'Plugin',\n                    funcName: 'cacheDidUpdate',\n                    paramName: 'cacheName',\n                });\n                assert.isInstance(request, Request, {\n                    moduleName: 'workbox-expiration',\n                    className: 'Plugin',\n                    funcName: 'cacheDidUpdate',\n                    paramName: 'request',\n                });\n            }\n            const cacheExpiration = this._getCacheExpiration(cacheName);\n            await cacheExpiration.updateTimestamp(request.url);\n            await cacheExpiration.expireEntries();\n        };\n        if (process.env.NODE_ENV !== 'production') {\n            if (!(config.maxEntries || config.maxAgeSeconds)) {\n                throw new WorkboxError('max-entries-or-age-required', {\n                    moduleName: 'workbox-expiration',\n                    className: 'Plugin',\n                    funcName: 'constructor',\n                });\n            }\n            if (config.maxEntries) {\n                assert.isType(config.maxEntries, 'number', {\n                    moduleName: 'workbox-expiration',\n                    className: 'Plugin',\n                    funcName: 'constructor',\n                    paramName: 'config.maxEntries',\n                });\n            }\n            if (config.maxAgeSeconds) {\n                assert.isType(config.maxAgeSeconds, 'number', {\n                    moduleName: 'workbox-expiration',\n                    className: 'Plugin',\n                    funcName: 'constructor',\n                    paramName: 'config.maxAgeSeconds',\n                });\n            }\n        }\n        this._config = config;\n        this._maxAgeSeconds = config.maxAgeSeconds;\n        this._cacheExpirations = new Map();\n        if (config.purgeOnQuotaError) {\n            registerQuotaErrorCallback(() => this.deleteCacheAndMetadata());\n        }\n    }\n    /**\n     * A simple helper method to return a CacheExpiration instance for a given\n     * cache name.\n     *\n     * @param {string} cacheName\n     * @return {CacheExpiration}\n     *\n     * @private\n     */\n    _getCacheExpiration(cacheName) {\n        if (cacheName === cacheNames.getRuntimeName()) {\n            throw new WorkboxError('expire-custom-caches-only');\n        }\n        let cacheExpiration = this._cacheExpirations.get(cacheName);\n        if (!cacheExpiration) {\n            cacheExpiration = new CacheExpiration(cacheName, this._config);\n            this._cacheExpirations.set(cacheName, cacheExpiration);\n        }\n        return cacheExpiration;\n    }\n    /**\n     * @param {Response} cachedResponse\n     * @return {boolean}\n     *\n     * @private\n     */\n    _isResponseDateFresh(cachedResponse) {\n        if (!this._maxAgeSeconds) {\n            // We aren't expiring by age, so return true, it's fresh\n            return true;\n        }\n        // Check if the 'date' header will suffice a quick expiration check.\n        // See https://github.com/GoogleChromeLabs/sw-toolbox/issues/164 for\n        // discussion.\n        const dateHeaderTimestamp = this._getDateHeaderTimestamp(cachedResponse);\n        if (dateHeaderTimestamp === null) {\n            // Unable to parse date, so assume it's fresh.\n            return true;\n        }\n        // If we have a valid headerTime, then our response is fresh iff the\n        // headerTime plus maxAgeSeconds is greater than the current time.\n        const now = Date.now();\n        return dateHeaderTimestamp >= now - this._maxAgeSeconds * 1000;\n    }\n    /**\n     * This method will extract the data header and parse it into a useful\n     * value.\n     *\n     * @param {Response} cachedResponse\n     * @return {number|null}\n     *\n     * @private\n     */\n    _getDateHeaderTimestamp(cachedResponse) {\n        if (!cachedResponse.headers.has('date')) {\n            return null;\n        }\n        const dateHeader = cachedResponse.headers.get('date');\n        const parsedDate = new Date(dateHeader);\n        const headerTime = parsedDate.getTime();\n        // If the Date header was invalid for some reason, parsedDate.getTime()\n        // will return NaN.\n        if (isNaN(headerTime)) {\n            return null;\n        }\n        return headerTime;\n    }\n    /**\n     * This is a helper method that performs two operations:\n     *\n     * - Deletes *all* the underlying Cache instances associated with this plugin\n     * instance, by calling caches.delete() on your behalf.\n     * - Deletes the metadata from IndexedDB used to keep track of expiration\n     * details for each Cache instance.\n     *\n     * When using cache expiration, calling this method is preferable to calling\n     * `caches.delete()` directly, since this will ensure that the IndexedDB\n     * metadata is also cleanly removed and open IndexedDB instances are deleted.\n     *\n     * Note that if you're *not* using cache expiration for a given cache, calling\n     * `caches.delete()` and passing in the cache's name should be sufficient.\n     * There is no Workbox-specific method needed for cleanup in that case.\n     */\n    async deleteCacheAndMetadata() {\n        // Do this one at a time instead of all at once via `Promise.all()` to\n        // reduce the chance of inconsistency if a promise rejects.\n        for (const [cacheName, cacheExpiration] of this._cacheExpirations) {\n            await self.caches.delete(cacheName);\n            await cacheExpiration.delete();\n        }\n        // Reset this._cacheExpirations to its initial state.\n        this._cacheExpirations = new Map();\n    }\n}\nexport { ExpirationPlugin };\n","\"use strict\";\n// @ts-ignore\ntry {\n    self['workbox:routing:7.0.0'] && _();\n}\ncatch (e) { }\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\n/**\n * The default HTTP method, 'GET', used when there's no specific method\n * configured for a route.\n *\n * @type {string}\n *\n * @private\n */\nexport const defaultMethod = 'GET';\n/**\n * The list of valid HTTP methods associated with requests that could be routed.\n *\n * @type {Array<string>}\n *\n * @private\n */\nexport const validMethods = [\n    'DELETE',\n    'GET',\n    'HEAD',\n    'PATCH',\n    'POST',\n    'PUT',\n];\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport '../_version.js';\n/**\n * @param {function()|Object} handler Either a function, or an object with a\n * 'handle' method.\n * @return {Object} An object with a handle method.\n *\n * @private\n */\nexport const normalizeHandler = (handler) => {\n    if (handler && typeof handler === 'object') {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.hasMethod(handler, 'handle', {\n                moduleName: 'workbox-routing',\n                className: 'Route',\n                funcName: 'constructor',\n                paramName: 'handler',\n            });\n        }\n        return handler;\n    }\n    else {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isType(handler, 'function', {\n                moduleName: 'workbox-routing',\n                className: 'Route',\n                funcName: 'constructor',\n                paramName: 'handler',\n            });\n        }\n        return { handle: handler };\n    }\n};\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { defaultMethod, validMethods } from './utils/constants.js';\nimport { normalizeHandler } from './utils/normalizeHandler.js';\nimport './_version.js';\n/**\n * A `Route` consists of a pair of callback functions, \"match\" and \"handler\".\n * The \"match\" callback determine if a route should be used to \"handle\" a\n * request by returning a non-falsy value if it can. The \"handler\" callback\n * is called when there is a match and should return a Promise that resolves\n * to a `Response`.\n *\n * @memberof workbox-routing\n */\nclass Route {\n    /**\n     * Constructor for Route class.\n     *\n     * @param {workbox-routing~matchCallback} match\n     * A callback function that determines whether the route matches a given\n     * `fetch` event by returning a non-falsy value.\n     * @param {workbox-routing~handlerCallback} handler A callback\n     * function that returns a Promise resolving to a Response.\n     * @param {string} [method='GET'] The HTTP method to match the Route\n     * against.\n     */\n    constructor(match, handler, method = defaultMethod) {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isType(match, 'function', {\n                moduleName: 'workbox-routing',\n                className: 'Route',\n                funcName: 'constructor',\n                paramName: 'match',\n            });\n            if (method) {\n                assert.isOneOf(method, validMethods, { paramName: 'method' });\n            }\n        }\n        // These values are referenced directly by Router so cannot be\n        // altered by minificaton.\n        this.handler = normalizeHandler(handler);\n        this.match = match;\n        this.method = method;\n    }\n    /**\n     *\n     * @param {workbox-routing-handlerCallback} handler A callback\n     * function that returns a Promise resolving to a Response\n     */\n    setCatchHandler(handler) {\n        this.catchHandler = normalizeHandler(handler);\n    }\n}\nexport { Route };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { Route } from './Route.js';\nimport './_version.js';\n/**\n * RegExpRoute makes it easy to create a regular expression based\n * {@link workbox-routing.Route}.\n *\n * For same-origin requests the RegExp only needs to match part of the URL. For\n * requests against third-party servers, you must define a RegExp that matches\n * the start of the URL.\n *\n * @memberof workbox-routing\n * @extends workbox-routing.Route\n */\nclass RegExpRoute extends Route {\n    /**\n     * If the regular expression contains\n     * [capture groups]{@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp#grouping-back-references},\n     * the captured values will be passed to the\n     * {@link workbox-routing~handlerCallback} `params`\n     * argument.\n     *\n     * @param {RegExp} regExp The regular expression to match against URLs.\n     * @param {workbox-routing~handlerCallback} handler A callback\n     * function that returns a Promise resulting in a Response.\n     * @param {string} [method='GET'] The HTTP method to match the Route\n     * against.\n     */\n    constructor(regExp, handler, method) {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(regExp, RegExp, {\n                moduleName: 'workbox-routing',\n                className: 'RegExpRoute',\n                funcName: 'constructor',\n                paramName: 'pattern',\n            });\n        }\n        const match = ({ url }) => {\n            const result = regExp.exec(url.href);\n            // Return immediately if there's no match.\n            if (!result) {\n                return;\n            }\n            // Require that the match start at the first character in the URL string\n            // if it's a cross-origin request.\n            // See https://github.com/GoogleChrome/workbox/issues/281 for the context\n            // behind this behavior.\n            if (url.origin !== location.origin && result.index !== 0) {\n                if (process.env.NODE_ENV !== 'production') {\n                    logger.debug(`The regular expression '${regExp.toString()}' only partially matched ` +\n                        `against the cross-origin URL '${url.toString()}'. RegExpRoute's will only ` +\n                        `handle cross-origin requests if they match the entire URL.`);\n                }\n                return;\n            }\n            // If the route matches, but there aren't any capture groups defined, then\n            // this will return [], which is truthy and therefore sufficient to\n            // indicate a match.\n            // If there are capture groups, then it will return their values.\n            return result.slice(1);\n        };\n        super(match, handler, method);\n    }\n}\nexport { RegExpRoute };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { getFriendlyURL } from 'workbox-core/_private/getFriendlyURL.js';\nimport { defaultMethod } from './utils/constants.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { normalizeHandler } from './utils/normalizeHandler.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport './_version.js';\n/**\n * The Router can be used to process a `FetchEvent` using one or more\n * {@link workbox-routing.Route}, responding with a `Response` if\n * a matching route exists.\n *\n * If no route matches a given a request, the Router will use a \"default\"\n * handler if one is defined.\n *\n * Should the matching Route throw an error, the Router will use a \"catch\"\n * handler if one is defined to gracefully deal with issues and respond with a\n * Request.\n *\n * If a request matches multiple routes, the **earliest** registered route will\n * be used to respond to the request.\n *\n * @memberof workbox-routing\n */\nclass Router {\n    /**\n     * Initializes a new Router.\n     */\n    constructor() {\n        this._routes = new Map();\n        this._defaultHandlerMap = new Map();\n    }\n    /**\n     * @return {Map<string, Array<workbox-routing.Route>>} routes A `Map` of HTTP\n     * method name ('GET', etc.) to an array of all the corresponding `Route`\n     * instances that are registered.\n     */\n    get routes() {\n        return this._routes;\n    }\n    /**\n     * Adds a fetch event listener to respond to events when a route matches\n     * the event's request.\n     */\n    addFetchListener() {\n        // See https://github.com/Microsoft/TypeScript/issues/28357#issuecomment-436484705\n        self.addEventListener('fetch', ((event) => {\n            const { request } = event;\n            const responsePromise = this.handleRequest({ request, event });\n            if (responsePromise) {\n                event.respondWith(responsePromise);\n            }\n        }));\n    }\n    /**\n     * Adds a message event listener for URLs to cache from the window.\n     * This is useful to cache resources loaded on the page prior to when the\n     * service worker started controlling it.\n     *\n     * The format of the message data sent from the window should be as follows.\n     * Where the `urlsToCache` array may consist of URL strings or an array of\n     * URL string + `requestInit` object (the same as you'd pass to `fetch()`).\n     *\n     * ```\n     * {\n     *   type: 'CACHE_URLS',\n     *   payload: {\n     *     urlsToCache: [\n     *       './script1.js',\n     *       './script2.js',\n     *       ['./script3.js', {mode: 'no-cors'}],\n     *     ],\n     *   },\n     * }\n     * ```\n     */\n    addCacheListener() {\n        // See https://github.com/Microsoft/TypeScript/issues/28357#issuecomment-436484705\n        self.addEventListener('message', ((event) => {\n            // event.data is type 'any'\n            // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access\n            if (event.data && event.data.type === 'CACHE_URLS') {\n                // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment\n                const { payload } = event.data;\n                if (process.env.NODE_ENV !== 'production') {\n                    logger.debug(`Caching URLs from the window`, payload.urlsToCache);\n                }\n                const requestPromises = Promise.all(payload.urlsToCache.map((entry) => {\n                    if (typeof entry === 'string') {\n                        entry = [entry];\n                    }\n                    const request = new Request(...entry);\n                    return this.handleRequest({ request, event });\n                    // TODO(philipwalton): TypeScript errors without this typecast for\n                    // some reason (probably a bug). The real type here should work but\n                    // doesn't: `Array<Promise<Response> | undefined>`.\n                })); // TypeScript\n                event.waitUntil(requestPromises);\n                // If a MessageChannel was used, reply to the message on success.\n                if (event.ports && event.ports[0]) {\n                    void requestPromises.then(() => event.ports[0].postMessage(true));\n                }\n            }\n        }));\n    }\n    /**\n     * Apply the routing rules to a FetchEvent object to get a Response from an\n     * appropriate Route's handler.\n     *\n     * @param {Object} options\n     * @param {Request} options.request The request to handle.\n     * @param {ExtendableEvent} options.event The event that triggered the\n     *     request.\n     * @return {Promise<Response>|undefined} A promise is returned if a\n     *     registered route can handle the request. If there is no matching\n     *     route and there's no `defaultHandler`, `undefined` is returned.\n     */\n    handleRequest({ request, event, }) {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(request, Request, {\n                moduleName: 'workbox-routing',\n                className: 'Router',\n                funcName: 'handleRequest',\n                paramName: 'options.request',\n            });\n        }\n        const url = new URL(request.url, location.href);\n        if (!url.protocol.startsWith('http')) {\n            if (process.env.NODE_ENV !== 'production') {\n                logger.debug(`Workbox Router only supports URLs that start with 'http'.`);\n            }\n            return;\n        }\n        const sameOrigin = url.origin === location.origin;\n        const { params, route } = this.findMatchingRoute({\n            event,\n            request,\n            sameOrigin,\n            url,\n        });\n        let handler = route && route.handler;\n        const debugMessages = [];\n        if (process.env.NODE_ENV !== 'production') {\n            if (handler) {\n                debugMessages.push([`Found a route to handle this request:`, route]);\n                if (params) {\n                    debugMessages.push([\n                        `Passing the following params to the route's handler:`,\n                        params,\n                    ]);\n                }\n            }\n        }\n        // If we don't have a handler because there was no matching route, then\n        // fall back to defaultHandler if that's defined.\n        const method = request.method;\n        if (!handler && this._defaultHandlerMap.has(method)) {\n            if (process.env.NODE_ENV !== 'production') {\n                debugMessages.push(`Failed to find a matching route. Falling ` +\n                    `back to the default handler for ${method}.`);\n            }\n            handler = this._defaultHandlerMap.get(method);\n        }\n        if (!handler) {\n            if (process.env.NODE_ENV !== 'production') {\n                // No handler so Workbox will do nothing. If logs is set of debug\n                // i.e. verbose, we should print out this information.\n                logger.debug(`No route found for: ${getFriendlyURL(url)}`);\n            }\n            return;\n        }\n        if (process.env.NODE_ENV !== 'production') {\n            // We have a handler, meaning Workbox is going to handle the route.\n            // print the routing details to the console.\n            logger.groupCollapsed(`Router is responding to: ${getFriendlyURL(url)}`);\n            debugMessages.forEach((msg) => {\n                if (Array.isArray(msg)) {\n                    logger.log(...msg);\n                }\n                else {\n                    logger.log(msg);\n                }\n            });\n            logger.groupEnd();\n        }\n        // Wrap in try and catch in case the handle method throws a synchronous\n        // error. It should still callback to the catch handler.\n        let responsePromise;\n        try {\n            responsePromise = handler.handle({ url, request, event, params });\n        }\n        catch (err) {\n            responsePromise = Promise.reject(err);\n        }\n        // Get route's catch handler, if it exists\n        const catchHandler = route && route.catchHandler;\n        if (responsePromise instanceof Promise &&\n            (this._catchHandler || catchHandler)) {\n            responsePromise = responsePromise.catch(async (err) => {\n                // If there's a route catch handler, process that first\n                if (catchHandler) {\n                    if (process.env.NODE_ENV !== 'production') {\n                        // Still include URL here as it will be async from the console group\n                        // and may not make sense without the URL\n                        logger.groupCollapsed(`Error thrown when responding to: ` +\n                            ` ${getFriendlyURL(url)}. Falling back to route's Catch Handler.`);\n                        logger.error(`Error thrown by:`, route);\n                        logger.error(err);\n                        logger.groupEnd();\n                    }\n                    try {\n                        return await catchHandler.handle({ url, request, event, params });\n                    }\n                    catch (catchErr) {\n                        if (catchErr instanceof Error) {\n                            err = catchErr;\n                        }\n                    }\n                }\n                if (this._catchHandler) {\n                    if (process.env.NODE_ENV !== 'production') {\n                        // Still include URL here as it will be async from the console group\n                        // and may not make sense without the URL\n                        logger.groupCollapsed(`Error thrown when responding to: ` +\n                            ` ${getFriendlyURL(url)}. Falling back to global Catch Handler.`);\n                        logger.error(`Error thrown by:`, route);\n                        logger.error(err);\n                        logger.groupEnd();\n                    }\n                    return this._catchHandler.handle({ url, request, event });\n                }\n                throw err;\n            });\n        }\n        return responsePromise;\n    }\n    /**\n     * Checks a request and URL (and optionally an event) against the list of\n     * registered routes, and if there's a match, returns the corresponding\n     * route along with any params generated by the match.\n     *\n     * @param {Object} options\n     * @param {URL} options.url\n     * @param {boolean} options.sameOrigin The result of comparing `url.origin`\n     *     against the current origin.\n     * @param {Request} options.request The request to match.\n     * @param {Event} options.event The corresponding event.\n     * @return {Object} An object with `route` and `params` properties.\n     *     They are populated if a matching route was found or `undefined`\n     *     otherwise.\n     */\n    findMatchingRoute({ url, sameOrigin, request, event, }) {\n        const routes = this._routes.get(request.method) || [];\n        for (const route of routes) {\n            let params;\n            // route.match returns type any, not possible to change right now.\n            // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment\n            const matchResult = route.match({ url, sameOrigin, request, event });\n            if (matchResult) {\n                if (process.env.NODE_ENV !== 'production') {\n                    // Warn developers that using an async matchCallback is almost always\n                    // not the right thing to do.\n                    if (matchResult instanceof Promise) {\n                        logger.warn(`While routing ${getFriendlyURL(url)}, an async ` +\n                            `matchCallback function was used. Please convert the ` +\n                            `following route to use a synchronous matchCallback function:`, route);\n                    }\n                }\n                // See https://github.com/GoogleChrome/workbox/issues/2079\n                // eslint-disable-next-line @typescript-eslint/no-unsafe-assignment\n                params = matchResult;\n                if (Array.isArray(params) && params.length === 0) {\n                    // Instead of passing an empty array in as params, use undefined.\n                    params = undefined;\n                }\n                else if (matchResult.constructor === Object && // eslint-disable-line\n                    Object.keys(matchResult).length === 0) {\n                    // Instead of passing an empty object in as params, use undefined.\n                    params = undefined;\n                }\n                else if (typeof matchResult === 'boolean') {\n                    // For the boolean value true (rather than just something truth-y),\n                    // don't set params.\n                    // See https://github.com/GoogleChrome/workbox/pull/2134#issuecomment-513924353\n                    params = undefined;\n                }\n                // Return early if have a match.\n                return { route, params };\n            }\n        }\n        // If no match was found above, return and empty object.\n        return {};\n    }\n    /**\n     * Define a default `handler` that's called when no routes explicitly\n     * match the incoming request.\n     *\n     * Each HTTP method ('GET', 'POST', etc.) gets its own default handler.\n     *\n     * Without a default handler, unmatched requests will go against the\n     * network as if there were no service worker present.\n     *\n     * @param {workbox-routing~handlerCallback} handler A callback\n     * function that returns a Promise resulting in a Response.\n     * @param {string} [method='GET'] The HTTP method to associate with this\n     * default handler. Each method has its own default.\n     */\n    setDefaultHandler(handler, method = defaultMethod) {\n        this._defaultHandlerMap.set(method, normalizeHandler(handler));\n    }\n    /**\n     * If a Route throws an error while handling a request, this `handler`\n     * will be called and given a chance to provide a response.\n     *\n     * @param {workbox-routing~handlerCallback} handler A callback\n     * function that returns a Promise resulting in a Response.\n     */\n    setCatchHandler(handler) {\n        this._catchHandler = normalizeHandler(handler);\n    }\n    /**\n     * Registers a route with the router.\n     *\n     * @param {workbox-routing.Route} route The route to register.\n     */\n    registerRoute(route) {\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isType(route, 'object', {\n                moduleName: 'workbox-routing',\n                className: 'Router',\n                funcName: 'registerRoute',\n                paramName: 'route',\n            });\n            assert.hasMethod(route, 'match', {\n                moduleName: 'workbox-routing',\n                className: 'Router',\n                funcName: 'registerRoute',\n                paramName: 'route',\n            });\n            assert.isType(route.handler, 'object', {\n                moduleName: 'workbox-routing',\n                className: 'Router',\n                funcName: 'registerRoute',\n                paramName: 'route',\n            });\n            assert.hasMethod(route.handler, 'handle', {\n                moduleName: 'workbox-routing',\n                className: 'Router',\n                funcName: 'registerRoute',\n                paramName: 'route.handler',\n            });\n            assert.isType(route.method, 'string', {\n                moduleName: 'workbox-routing',\n                className: 'Router',\n                funcName: 'registerRoute',\n                paramName: 'route.method',\n            });\n        }\n        if (!this._routes.has(route.method)) {\n            this._routes.set(route.method, []);\n        }\n        // Give precedence to all of the earlier routes by adding this additional\n        // route to the end of the array.\n        this._routes.get(route.method).push(route);\n    }\n    /**\n     * Unregisters a route with the router.\n     *\n     * @param {workbox-routing.Route} route The route to unregister.\n     */\n    unregisterRoute(route) {\n        if (!this._routes.has(route.method)) {\n            throw new WorkboxError('unregister-route-but-not-found-with-method', {\n                method: route.method,\n            });\n        }\n        const routeIndex = this._routes.get(route.method).indexOf(route);\n        if (routeIndex > -1) {\n            this._routes.get(route.method).splice(routeIndex, 1);\n        }\n        else {\n            throw new WorkboxError('unregister-route-route-not-registered');\n        }\n    }\n}\nexport { Router };\n","/*\n  Copyright 2019 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { Router } from '../Router.js';\nimport '../_version.js';\nlet defaultRouter;\n/**\n * Creates a new, singleton Router instance if one does not exist. If one\n * does already exist, that instance is returned.\n *\n * @private\n * @return {Router}\n */\nexport const getOrCreateDefaultRouter = () => {\n    if (!defaultRouter) {\n        defaultRouter = new Router();\n        // The helpers that use the default Router assume these listeners exist.\n        defaultRouter.addFetchListener();\n        defaultRouter.addCacheListener();\n    }\n    return defaultRouter;\n};\n","/*\n  Copyright 2019 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { Route } from './Route.js';\nimport { RegExpRoute } from './RegExpRoute.js';\nimport { getOrCreateDefaultRouter } from './utils/getOrCreateDefaultRouter.js';\nimport './_version.js';\n/**\n * Easily register a RegExp, string, or function with a caching\n * strategy to a singleton Router instance.\n *\n * This method will generate a Route for you if needed and\n * call {@link workbox-routing.Router#registerRoute}.\n *\n * @param {RegExp|string|workbox-routing.Route~matchCallback|workbox-routing.Route} capture\n * If the capture param is a `Route`, all other arguments will be ignored.\n * @param {workbox-routing~handlerCallback} [handler] A callback\n * function that returns a Promise resulting in a Response. This parameter\n * is required if `capture` is not a `Route` object.\n * @param {string} [method='GET'] The HTTP method to match the Route\n * against.\n * @return {workbox-routing.Route} The generated `Route`.\n *\n * @memberof workbox-routing\n */\nfunction registerRoute(capture, handler, method) {\n    let route;\n    if (typeof capture === 'string') {\n        const captureUrl = new URL(capture, location.href);\n        if (process.env.NODE_ENV !== 'production') {\n            if (!(capture.startsWith('/') || capture.startsWith('http'))) {\n                throw new WorkboxError('invalid-string', {\n                    moduleName: 'workbox-routing',\n                    funcName: 'registerRoute',\n                    paramName: 'capture',\n                });\n            }\n            // We want to check if Express-style wildcards are in the pathname only.\n            // TODO: Remove this log message in v4.\n            const valueToCheck = capture.startsWith('http')\n                ? captureUrl.pathname\n                : capture;\n            // See https://github.com/pillarjs/path-to-regexp#parameters\n            const wildcards = '[*:?+]';\n            if (new RegExp(`${wildcards}`).exec(valueToCheck)) {\n                logger.debug(`The '$capture' parameter contains an Express-style wildcard ` +\n                    `character (${wildcards}). Strings are now always interpreted as ` +\n                    `exact matches; use a RegExp for partial or wildcard matches.`);\n            }\n        }\n        const matchCallback = ({ url }) => {\n            if (process.env.NODE_ENV !== 'production') {\n                if (url.pathname === captureUrl.pathname &&\n                    url.origin !== captureUrl.origin) {\n                    logger.debug(`${capture} only partially matches the cross-origin URL ` +\n                        `${url.toString()}. This route will only handle cross-origin requests ` +\n                        `if they match the entire URL.`);\n                }\n            }\n            return url.href === captureUrl.href;\n        };\n        // If `capture` is a string then `handler` and `method` must be present.\n        route = new Route(matchCallback, handler, method);\n    }\n    else if (capture instanceof RegExp) {\n        // If `capture` is a `RegExp` then `handler` and `method` must be present.\n        route = new RegExpRoute(capture, handler, method);\n    }\n    else if (typeof capture === 'function') {\n        // If `capture` is a function then `handler` and `method` must be present.\n        route = new Route(capture, handler, method);\n    }\n    else if (capture instanceof Route) {\n        route = capture;\n    }\n    else {\n        throw new WorkboxError('unsupported-route-type', {\n            moduleName: 'workbox-routing',\n            funcName: 'registerRoute',\n            paramName: 'capture',\n        });\n    }\n    const defaultRouter = getOrCreateDefaultRouter();\n    defaultRouter.registerRoute(route);\n    return route;\n}\nexport { registerRoute };\n","/*\n  Copyright 2020 Google LLC\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\nfunction stripParams(fullURL, ignoreParams) {\n    const strippedURL = new URL(fullURL);\n    for (const param of ignoreParams) {\n        strippedURL.searchParams.delete(param);\n    }\n    return strippedURL.href;\n}\n/**\n * Matches an item in the cache, ignoring specific URL params. This is similar\n * to the `ignoreSearch` option, but it allows you to ignore just specific\n * params (while continuing to match on the others).\n *\n * @private\n * @param {Cache} cache\n * @param {Request} request\n * @param {Object} matchOptions\n * @param {Array<string>} ignoreParams\n * @return {Promise<Response|undefined>}\n */\nasync function cacheMatchIgnoreParams(cache, request, ignoreParams, matchOptions) {\n    const strippedRequestURL = stripParams(request.url, ignoreParams);\n    // If the request doesn't include any ignored params, match as normal.\n    if (request.url === strippedRequestURL) {\n        return cache.match(request, matchOptions);\n    }\n    // Otherwise, match by comparing keys\n    const keysOptions = Object.assign(Object.assign({}, matchOptions), { ignoreSearch: true });\n    const cacheKeys = await cache.keys(request, keysOptions);\n    for (const cacheKey of cacheKeys) {\n        const strippedCacheKeyURL = stripParams(cacheKey.url, ignoreParams);\n        if (strippedRequestURL === strippedCacheKeyURL) {\n            return cache.match(cacheKey, matchOptions);\n        }\n    }\n    return;\n}\nexport { cacheMatchIgnoreParams };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\n/**\n * The Deferred class composes Promises in a way that allows for them to be\n * resolved or rejected from outside the constructor. In most cases promises\n * should be used directly, but Deferreds can be necessary when the logic to\n * resolve a promise must be separate.\n *\n * @private\n */\nclass Deferred {\n    /**\n     * Creates a promise and exposes its resolve and reject functions as methods.\n     */\n    constructor() {\n        this.promise = new Promise((resolve, reject) => {\n            this.resolve = resolve;\n            this.reject = reject;\n        });\n    }\n}\nexport { Deferred };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { logger } from '../_private/logger.js';\nimport { quotaErrorCallbacks } from '../models/quotaErrorCallbacks.js';\nimport '../_version.js';\n/**\n * Runs all of the callback functions, one at a time sequentially, in the order\n * in which they were registered.\n *\n * @memberof workbox-core\n * @private\n */\nasync function executeQuotaErrorCallbacks() {\n    if (process.env.NODE_ENV !== 'production') {\n        logger.log(`About to run ${quotaErrorCallbacks.size} ` +\n            `callbacks to clean up caches.`);\n    }\n    for (const callback of quotaErrorCallbacks) {\n        await callback();\n        if (process.env.NODE_ENV !== 'production') {\n            logger.log(callback, 'is complete.');\n        }\n    }\n    if (process.env.NODE_ENV !== 'production') {\n        logger.log('Finished running callbacks.');\n    }\n}\nexport { executeQuotaErrorCallbacks };\n","/*\n  Copyright 2019 Google LLC\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\n/**\n * Returns a promise that resolves and the passed number of milliseconds.\n * This utility is an async/await-friendly version of `setTimeout`.\n *\n * @param {number} ms\n * @return {Promise}\n * @private\n */\nexport function timeout(ms) {\n    return new Promise((resolve) => setTimeout(resolve, ms));\n}\n","\"use strict\";\n// @ts-ignore\ntry {\n    self['workbox:strategies:7.0.0'] && _();\n}\ncatch (e) { }\n","/*\n  Copyright 2020 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { cacheMatchIgnoreParams } from 'workbox-core/_private/cacheMatchIgnoreParams.js';\nimport { Deferred } from 'workbox-core/_private/Deferred.js';\nimport { executeQuotaErrorCallbacks } from 'workbox-core/_private/executeQuotaErrorCallbacks.js';\nimport { getFriendlyURL } from 'workbox-core/_private/getFriendlyURL.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { timeout } from 'workbox-core/_private/timeout.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport './_version.js';\nfunction toRequest(input) {\n    return typeof input === 'string' ? new Request(input) : input;\n}\n/**\n * A class created every time a Strategy instance instance calls\n * {@link workbox-strategies.Strategy~handle} or\n * {@link workbox-strategies.Strategy~handleAll} that wraps all fetch and\n * cache actions around plugin callbacks and keeps track of when the strategy\n * is \"done\" (i.e. all added `event.waitUntil()` promises have resolved).\n *\n * @memberof workbox-strategies\n */\nclass StrategyHandler {\n    /**\n     * Creates a new instance associated with the passed strategy and event\n     * that's handling the request.\n     *\n     * The constructor also initializes the state that will be passed to each of\n     * the plugins handling this request.\n     *\n     * @param {workbox-strategies.Strategy} strategy\n     * @param {Object} options\n     * @param {Request|string} options.request A request to run this strategy for.\n     * @param {ExtendableEvent} options.event The event associated with the\n     *     request.\n     * @param {URL} [options.url]\n     * @param {*} [options.params] The return value from the\n     *     {@link workbox-routing~matchCallback} (if applicable).\n     */\n    constructor(strategy, options) {\n        this._cacheKeys = {};\n        /**\n         * The request the strategy is performing (passed to the strategy's\n         * `handle()` or `handleAll()` method).\n         * @name request\n         * @instance\n         * @type {Request}\n         * @memberof workbox-strategies.StrategyHandler\n         */\n        /**\n         * The event associated with this request.\n         * @name event\n         * @instance\n         * @type {ExtendableEvent}\n         * @memberof workbox-strategies.StrategyHandler\n         */\n        /**\n         * A `URL` instance of `request.url` (if passed to the strategy's\n         * `handle()` or `handleAll()` method).\n         * Note: the `url` param will be present if the strategy was invoked\n         * from a workbox `Route` object.\n         * @name url\n         * @instance\n         * @type {URL|undefined}\n         * @memberof workbox-strategies.StrategyHandler\n         */\n        /**\n         * A `param` value (if passed to the strategy's\n         * `handle()` or `handleAll()` method).\n         * Note: the `param` param will be present if the strategy was invoked\n         * from a workbox `Route` object and the\n         * {@link workbox-routing~matchCallback} returned\n         * a truthy value (it will be that value).\n         * @name params\n         * @instance\n         * @type {*|undefined}\n         * @memberof workbox-strategies.StrategyHandler\n         */\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(options.event, ExtendableEvent, {\n                moduleName: 'workbox-strategies',\n                className: 'StrategyHandler',\n                funcName: 'constructor',\n                paramName: 'options.event',\n            });\n        }\n        Object.assign(this, options);\n        this.event = options.event;\n        this._strategy = strategy;\n        this._handlerDeferred = new Deferred();\n        this._extendLifetimePromises = [];\n        // Copy the plugins list (since it's mutable on the strategy),\n        // so any mutations don't affect this handler instance.\n        this._plugins = [...strategy.plugins];\n        this._pluginStateMap = new Map();\n        for (const plugin of this._plugins) {\n            this._pluginStateMap.set(plugin, {});\n        }\n        this.event.waitUntil(this._handlerDeferred.promise);\n    }\n    /**\n     * Fetches a given request (and invokes any applicable plugin callback\n     * methods) using the `fetchOptions` (for non-navigation requests) and\n     * `plugins` defined on the `Strategy` object.\n     *\n     * The following plugin lifecycle methods are invoked when using this method:\n     * - `requestWillFetch()`\n     * - `fetchDidSucceed()`\n     * - `fetchDidFail()`\n     *\n     * @param {Request|string} input The URL or request to fetch.\n     * @return {Promise<Response>}\n     */\n    async fetch(input) {\n        const { event } = this;\n        let request = toRequest(input);\n        if (request.mode === 'navigate' &&\n            event instanceof FetchEvent &&\n            event.preloadResponse) {\n            const possiblePreloadResponse = (await event.preloadResponse);\n            if (possiblePreloadResponse) {\n                if (process.env.NODE_ENV !== 'production') {\n                    logger.log(`Using a preloaded navigation response for ` +\n                        `'${getFriendlyURL(request.url)}'`);\n                }\n                return possiblePreloadResponse;\n            }\n        }\n        // If there is a fetchDidFail plugin, we need to save a clone of the\n        // original request before it's either modified by a requestWillFetch\n        // plugin or before the original request's body is consumed via fetch().\n        const originalRequest = this.hasCallback('fetchDidFail')\n            ? request.clone()\n            : null;\n        try {\n            for (const cb of this.iterateCallbacks('requestWillFetch')) {\n                request = await cb({ request: request.clone(), event });\n            }\n        }\n        catch (err) {\n            if (err instanceof Error) {\n                throw new WorkboxError('plugin-error-request-will-fetch', {\n                    thrownErrorMessage: err.message,\n                });\n            }\n        }\n        // The request can be altered by plugins with `requestWillFetch` making\n        // the original request (most likely from a `fetch` event) different\n        // from the Request we make. Pass both to `fetchDidFail` to aid debugging.\n        const pluginFilteredRequest = request.clone();\n        try {\n            let fetchResponse;\n            // See https://github.com/GoogleChrome/workbox/issues/1796\n            fetchResponse = await fetch(request, request.mode === 'navigate' ? undefined : this._strategy.fetchOptions);\n            if (process.env.NODE_ENV !== 'production') {\n                logger.debug(`Network request for ` +\n                    `'${getFriendlyURL(request.url)}' returned a response with ` +\n                    `status '${fetchResponse.status}'.`);\n            }\n            for (const callback of this.iterateCallbacks('fetchDidSucceed')) {\n                fetchResponse = await callback({\n                    event,\n                    request: pluginFilteredRequest,\n                    response: fetchResponse,\n                });\n            }\n            return fetchResponse;\n        }\n        catch (error) {\n            if (process.env.NODE_ENV !== 'production') {\n                logger.log(`Network request for ` +\n                    `'${getFriendlyURL(request.url)}' threw an error.`, error);\n            }\n            // `originalRequest` will only exist if a `fetchDidFail` callback\n            // is being used (see above).\n            if (originalRequest) {\n                await this.runCallbacks('fetchDidFail', {\n                    error: error,\n                    event,\n                    originalRequest: originalRequest.clone(),\n                    request: pluginFilteredRequest.clone(),\n                });\n            }\n            throw error;\n        }\n    }\n    /**\n     * Calls `this.fetch()` and (in the background) runs `this.cachePut()` on\n     * the response generated by `this.fetch()`.\n     *\n     * The call to `this.cachePut()` automatically invokes `this.waitUntil()`,\n     * so you do not have to manually call `waitUntil()` on the event.\n     *\n     * @param {Request|string} input The request or URL to fetch and cache.\n     * @return {Promise<Response>}\n     */\n    async fetchAndCachePut(input) {\n        const response = await this.fetch(input);\n        const responseClone = response.clone();\n        void this.waitUntil(this.cachePut(input, responseClone));\n        return response;\n    }\n    /**\n     * Matches a request from the cache (and invokes any applicable plugin\n     * callback methods) using the `cacheName`, `matchOptions`, and `plugins`\n     * defined on the strategy object.\n     *\n     * The following plugin lifecycle methods are invoked when using this method:\n     * - cacheKeyWillByUsed()\n     * - cachedResponseWillByUsed()\n     *\n     * @param {Request|string} key The Request or URL to use as the cache key.\n     * @return {Promise<Response|undefined>} A matching response, if found.\n     */\n    async cacheMatch(key) {\n        const request = toRequest(key);\n        let cachedResponse;\n        const { cacheName, matchOptions } = this._strategy;\n        const effectiveRequest = await this.getCacheKey(request, 'read');\n        const multiMatchOptions = Object.assign(Object.assign({}, matchOptions), { cacheName });\n        cachedResponse = await caches.match(effectiveRequest, multiMatchOptions);\n        if (process.env.NODE_ENV !== 'production') {\n            if (cachedResponse) {\n                logger.debug(`Found a cached response in '${cacheName}'.`);\n            }\n            else {\n                logger.debug(`No cached response found in '${cacheName}'.`);\n            }\n        }\n        for (const callback of this.iterateCallbacks('cachedResponseWillBeUsed')) {\n            cachedResponse =\n                (await callback({\n                    cacheName,\n                    matchOptions,\n                    cachedResponse,\n                    request: effectiveRequest,\n                    event: this.event,\n                })) || undefined;\n        }\n        return cachedResponse;\n    }\n    /**\n     * Puts a request/response pair in the cache (and invokes any applicable\n     * plugin callback methods) using the `cacheName` and `plugins` defined on\n     * the strategy object.\n     *\n     * The following plugin lifecycle methods are invoked when using this method:\n     * - cacheKeyWillByUsed()\n     * - cacheWillUpdate()\n     * - cacheDidUpdate()\n     *\n     * @param {Request|string} key The request or URL to use as the cache key.\n     * @param {Response} response The response to cache.\n     * @return {Promise<boolean>} `false` if a cacheWillUpdate caused the response\n     * not be cached, and `true` otherwise.\n     */\n    async cachePut(key, response) {\n        const request = toRequest(key);\n        // Run in the next task to avoid blocking other cache reads.\n        // https://github.com/w3c/ServiceWorker/issues/1397\n        await timeout(0);\n        const effectiveRequest = await this.getCacheKey(request, 'write');\n        if (process.env.NODE_ENV !== 'production') {\n            if (effectiveRequest.method && effectiveRequest.method !== 'GET') {\n                throw new WorkboxError('attempt-to-cache-non-get-request', {\n                    url: getFriendlyURL(effectiveRequest.url),\n                    method: effectiveRequest.method,\n                });\n            }\n            // See https://github.com/GoogleChrome/workbox/issues/2818\n            const vary = response.headers.get('Vary');\n            if (vary) {\n                logger.debug(`The response for ${getFriendlyURL(effectiveRequest.url)} ` +\n                    `has a 'Vary: ${vary}' header. ` +\n                    `Consider setting the {ignoreVary: true} option on your strategy ` +\n                    `to ensure cache matching and deletion works as expected.`);\n            }\n        }\n        if (!response) {\n            if (process.env.NODE_ENV !== 'production') {\n                logger.error(`Cannot cache non-existent response for ` +\n                    `'${getFriendlyURL(effectiveRequest.url)}'.`);\n            }\n            throw new WorkboxError('cache-put-with-no-response', {\n                url: getFriendlyURL(effectiveRequest.url),\n            });\n        }\n        const responseToCache = await this._ensureResponseSafeToCache(response);\n        if (!responseToCache) {\n            if (process.env.NODE_ENV !== 'production') {\n                logger.debug(`Response '${getFriendlyURL(effectiveRequest.url)}' ` +\n                    `will not be cached.`, responseToCache);\n            }\n            return false;\n        }\n        const { cacheName, matchOptions } = this._strategy;\n        const cache = await self.caches.open(cacheName);\n        const hasCacheUpdateCallback = this.hasCallback('cacheDidUpdate');\n        const oldResponse = hasCacheUpdateCallback\n            ? await cacheMatchIgnoreParams(\n            // TODO(philipwalton): the `__WB_REVISION__` param is a precaching\n            // feature. Consider into ways to only add this behavior if using\n            // precaching.\n            cache, effectiveRequest.clone(), ['__WB_REVISION__'], matchOptions)\n            : null;\n        if (process.env.NODE_ENV !== 'production') {\n            logger.debug(`Updating the '${cacheName}' cache with a new Response ` +\n                `for ${getFriendlyURL(effectiveRequest.url)}.`);\n        }\n        try {\n            await cache.put(effectiveRequest, hasCacheUpdateCallback ? responseToCache.clone() : responseToCache);\n        }\n        catch (error) {\n            if (error instanceof Error) {\n                // See https://developer.mozilla.org/en-US/docs/Web/API/DOMException#exception-QuotaExceededError\n                if (error.name === 'QuotaExceededError') {\n                    await executeQuotaErrorCallbacks();\n                }\n                throw error;\n            }\n        }\n        for (const callback of this.iterateCallbacks('cacheDidUpdate')) {\n            await callback({\n                cacheName,\n                oldResponse,\n                newResponse: responseToCache.clone(),\n                request: effectiveRequest,\n                event: this.event,\n            });\n        }\n        return true;\n    }\n    /**\n     * Checks the list of plugins for the `cacheKeyWillBeUsed` callback, and\n     * executes any of those callbacks found in sequence. The final `Request`\n     * object returned by the last plugin is treated as the cache key for cache\n     * reads and/or writes. If no `cacheKeyWillBeUsed` plugin callbacks have\n     * been registered, the passed request is returned unmodified\n     *\n     * @param {Request} request\n     * @param {string} mode\n     * @return {Promise<Request>}\n     */\n    async getCacheKey(request, mode) {\n        const key = `${request.url} | ${mode}`;\n        if (!this._cacheKeys[key]) {\n            let effectiveRequest = request;\n            for (const callback of this.iterateCallbacks('cacheKeyWillBeUsed')) {\n                effectiveRequest = toRequest(await callback({\n                    mode,\n                    request: effectiveRequest,\n                    event: this.event,\n                    // params has a type any can't change right now.\n                    params: this.params, // eslint-disable-line\n                }));\n            }\n            this._cacheKeys[key] = effectiveRequest;\n        }\n        return this._cacheKeys[key];\n    }\n    /**\n     * Returns true if the strategy has at least one plugin with the given\n     * callback.\n     *\n     * @param {string} name The name of the callback to check for.\n     * @return {boolean}\n     */\n    hasCallback(name) {\n        for (const plugin of this._strategy.plugins) {\n            if (name in plugin) {\n                return true;\n            }\n        }\n        return false;\n    }\n    /**\n     * Runs all plugin callbacks matching the given name, in order, passing the\n     * given param object (merged ith the current plugin state) as the only\n     * argument.\n     *\n     * Note: since this method runs all plugins, it's not suitable for cases\n     * where the return value of a callback needs to be applied prior to calling\n     * the next callback. See\n     * {@link workbox-strategies.StrategyHandler#iterateCallbacks}\n     * below for how to handle that case.\n     *\n     * @param {string} name The name of the callback to run within each plugin.\n     * @param {Object} param The object to pass as the first (and only) param\n     *     when executing each callback. This object will be merged with the\n     *     current plugin state prior to callback execution.\n     */\n    async runCallbacks(name, param) {\n        for (const callback of this.iterateCallbacks(name)) {\n            // TODO(philipwalton): not sure why `any` is needed. It seems like\n            // this should work with `as WorkboxPluginCallbackParam[C]`.\n            await callback(param);\n        }\n    }\n    /**\n     * Accepts a callback and returns an iterable of matching plugin callbacks,\n     * where each callback is wrapped with the current handler state (i.e. when\n     * you call each callback, whatever object parameter you pass it will\n     * be merged with the plugin's current state).\n     *\n     * @param {string} name The name fo the callback to run\n     * @return {Array<Function>}\n     */\n    *iterateCallbacks(name) {\n        for (const plugin of this._strategy.plugins) {\n            if (typeof plugin[name] === 'function') {\n                const state = this._pluginStateMap.get(plugin);\n                const statefulCallback = (param) => {\n                    const statefulParam = Object.assign(Object.assign({}, param), { state });\n                    // TODO(philipwalton): not sure why `any` is needed. It seems like\n                    // this should work with `as WorkboxPluginCallbackParam[C]`.\n                    return plugin[name](statefulParam);\n                };\n                yield statefulCallback;\n            }\n        }\n    }\n    /**\n     * Adds a promise to the\n     * [extend lifetime promises]{@link https://w3c.github.io/ServiceWorker/#extendableevent-extend-lifetime-promises}\n     * of the event event associated with the request being handled (usually a\n     * `FetchEvent`).\n     *\n     * Note: you can await\n     * {@link workbox-strategies.StrategyHandler~doneWaiting}\n     * to know when all added promises have settled.\n     *\n     * @param {Promise} promise A promise to add to the extend lifetime promises\n     *     of the event that triggered the request.\n     */\n    waitUntil(promise) {\n        this._extendLifetimePromises.push(promise);\n        return promise;\n    }\n    /**\n     * Returns a promise that resolves once all promises passed to\n     * {@link workbox-strategies.StrategyHandler~waitUntil}\n     * have settled.\n     *\n     * Note: any work done after `doneWaiting()` settles should be manually\n     * passed to an event's `waitUntil()` method (not this handler's\n     * `waitUntil()` method), otherwise the service worker thread my be killed\n     * prior to your work completing.\n     */\n    async doneWaiting() {\n        let promise;\n        while ((promise = this._extendLifetimePromises.shift())) {\n            await promise;\n        }\n    }\n    /**\n     * Stops running the strategy and immediately resolves any pending\n     * `waitUntil()` promises.\n     */\n    destroy() {\n        this._handlerDeferred.resolve(null);\n    }\n    /**\n     * This method will call cacheWillUpdate on the available plugins (or use\n     * status === 200) to determine if the Response is safe and valid to cache.\n     *\n     * @param {Request} options.request\n     * @param {Response} options.response\n     * @return {Promise<Response|undefined>}\n     *\n     * @private\n     */\n    async _ensureResponseSafeToCache(response) {\n        let responseToCache = response;\n        let pluginsUsed = false;\n        for (const callback of this.iterateCallbacks('cacheWillUpdate')) {\n            responseToCache =\n                (await callback({\n                    request: this.request,\n                    response: responseToCache,\n                    event: this.event,\n                })) || undefined;\n            pluginsUsed = true;\n            if (!responseToCache) {\n                break;\n            }\n        }\n        if (!pluginsUsed) {\n            if (responseToCache && responseToCache.status !== 200) {\n                responseToCache = undefined;\n            }\n            if (process.env.NODE_ENV !== 'production') {\n                if (responseToCache) {\n                    if (responseToCache.status !== 200) {\n                        if (responseToCache.status === 0) {\n                            logger.warn(`The response for '${this.request.url}' ` +\n                                `is an opaque response. The caching strategy that you're ` +\n                                `using will not cache opaque responses by default.`);\n                        }\n                        else {\n                            logger.debug(`The response for '${this.request.url}' ` +\n                                `returned a status code of '${response.status}' and won't ` +\n                                `be cached as a result.`);\n                        }\n                    }\n                }\n            }\n        }\n        return responseToCache;\n    }\n}\nexport { StrategyHandler };\n","/*\n  Copyright 2020 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { cacheNames } from 'workbox-core/_private/cacheNames.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { getFriendlyURL } from 'workbox-core/_private/getFriendlyURL.js';\nimport { StrategyHandler } from './StrategyHandler.js';\nimport './_version.js';\n/**\n * An abstract base class that all other strategy classes must extend from:\n *\n * @memberof workbox-strategies\n */\nclass Strategy {\n    /**\n     * Creates a new instance of the strategy and sets all documented option\n     * properties as public instance properties.\n     *\n     * Note: if a custom strategy class extends the base Strategy class and does\n     * not need more than these properties, it does not need to define its own\n     * constructor.\n     *\n     * @param {Object} [options]\n     * @param {string} [options.cacheName] Cache name to store and retrieve\n     * requests. Defaults to the cache names provided by\n     * {@link workbox-core.cacheNames}.\n     * @param {Array<Object>} [options.plugins] [Plugins]{@link https://developers.google.com/web/tools/workbox/guides/using-plugins}\n     * to use in conjunction with this caching strategy.\n     * @param {Object} [options.fetchOptions] Values passed along to the\n     * [`init`](https://developer.mozilla.org/en-US/docs/Web/API/WindowOrWorkerGlobalScope/fetch#Parameters)\n     * of [non-navigation](https://github.com/GoogleChrome/workbox/issues/1796)\n     * `fetch()` requests made by this strategy.\n     * @param {Object} [options.matchOptions] The\n     * [`CacheQueryOptions`]{@link https://w3c.github.io/ServiceWorker/#dictdef-cachequeryoptions}\n     * for any `cache.match()` or `cache.put()` calls made by this strategy.\n     */\n    constructor(options = {}) {\n        /**\n         * Cache name to store and retrieve\n         * requests. Defaults to the cache names provided by\n         * {@link workbox-core.cacheNames}.\n         *\n         * @type {string}\n         */\n        this.cacheName = cacheNames.getRuntimeName(options.cacheName);\n        /**\n         * The list\n         * [Plugins]{@link https://developers.google.com/web/tools/workbox/guides/using-plugins}\n         * used by this strategy.\n         *\n         * @type {Array<Object>}\n         */\n        this.plugins = options.plugins || [];\n        /**\n         * Values passed along to the\n         * [`init`]{@link https://developer.mozilla.org/en-US/docs/Web/API/WindowOrWorkerGlobalScope/fetch#Parameters}\n         * of all fetch() requests made by this strategy.\n         *\n         * @type {Object}\n         */\n        this.fetchOptions = options.fetchOptions;\n        /**\n         * The\n         * [`CacheQueryOptions`]{@link https://w3c.github.io/ServiceWorker/#dictdef-cachequeryoptions}\n         * for any `cache.match()` or `cache.put()` calls made by this strategy.\n         *\n         * @type {Object}\n         */\n        this.matchOptions = options.matchOptions;\n    }\n    /**\n     * Perform a request strategy and returns a `Promise` that will resolve with\n     * a `Response`, invoking all relevant plugin callbacks.\n     *\n     * When a strategy instance is registered with a Workbox\n     * {@link workbox-routing.Route}, this method is automatically\n     * called when the route matches.\n     *\n     * Alternatively, this method can be used in a standalone `FetchEvent`\n     * listener by passing it to `event.respondWith()`.\n     *\n     * @param {FetchEvent|Object} options A `FetchEvent` or an object with the\n     *     properties listed below.\n     * @param {Request|string} options.request A request to run this strategy for.\n     * @param {ExtendableEvent} options.event The event associated with the\n     *     request.\n     * @param {URL} [options.url]\n     * @param {*} [options.params]\n     */\n    handle(options) {\n        const [responseDone] = this.handleAll(options);\n        return responseDone;\n    }\n    /**\n     * Similar to {@link workbox-strategies.Strategy~handle}, but\n     * instead of just returning a `Promise` that resolves to a `Response` it\n     * it will return an tuple of `[response, done]` promises, where the former\n     * (`response`) is equivalent to what `handle()` returns, and the latter is a\n     * Promise that will resolve once any promises that were added to\n     * `event.waitUntil()` as part of performing the strategy have completed.\n     *\n     * You can await the `done` promise to ensure any extra work performed by\n     * the strategy (usually caching responses) completes successfully.\n     *\n     * @param {FetchEvent|Object} options A `FetchEvent` or an object with the\n     *     properties listed below.\n     * @param {Request|string} options.request A request to run this strategy for.\n     * @param {ExtendableEvent} options.event The event associated with the\n     *     request.\n     * @param {URL} [options.url]\n     * @param {*} [options.params]\n     * @return {Array<Promise>} A tuple of [response, done]\n     *     promises that can be used to determine when the response resolves as\n     *     well as when the handler has completed all its work.\n     */\n    handleAll(options) {\n        // Allow for flexible options to be passed.\n        if (options instanceof FetchEvent) {\n            options = {\n                event: options,\n                request: options.request,\n            };\n        }\n        const event = options.event;\n        const request = typeof options.request === 'string'\n            ? new Request(options.request)\n            : options.request;\n        const params = 'params' in options ? options.params : undefined;\n        const handler = new StrategyHandler(this, { event, request, params });\n        const responseDone = this._getResponse(handler, request, event);\n        const handlerDone = this._awaitComplete(responseDone, handler, request, event);\n        // Return an array of promises, suitable for use with Promise.all().\n        return [responseDone, handlerDone];\n    }\n    async _getResponse(handler, request, event) {\n        await handler.runCallbacks('handlerWillStart', { event, request });\n        let response = undefined;\n        try {\n            response = await this._handle(request, handler);\n            // The \"official\" Strategy subclasses all throw this error automatically,\n            // but in case a third-party Strategy doesn't, ensure that we have a\n            // consistent failure when there's no response or an error response.\n            if (!response || response.type === 'error') {\n                throw new WorkboxError('no-response', { url: request.url });\n            }\n        }\n        catch (error) {\n            if (error instanceof Error) {\n                for (const callback of handler.iterateCallbacks('handlerDidError')) {\n                    response = await callback({ error, event, request });\n                    if (response) {\n                        break;\n                    }\n                }\n            }\n            if (!response) {\n                throw error;\n            }\n            else if (process.env.NODE_ENV !== 'production') {\n                logger.log(`While responding to '${getFriendlyURL(request.url)}', ` +\n                    `an ${error instanceof Error ? error.toString() : ''} error occurred. Using a fallback response provided by ` +\n                    `a handlerDidError plugin.`);\n            }\n        }\n        for (const callback of handler.iterateCallbacks('handlerWillRespond')) {\n            response = await callback({ event, request, response });\n        }\n        return response;\n    }\n    async _awaitComplete(responseDone, handler, request, event) {\n        let response;\n        let error;\n        try {\n            response = await responseDone;\n        }\n        catch (error) {\n            // Ignore errors, as response errors should be caught via the `response`\n            // promise above. The `done` promise will only throw for errors in\n            // promises passed to `handler.waitUntil()`.\n        }\n        try {\n            await handler.runCallbacks('handlerDidRespond', {\n                event,\n                request,\n                response,\n            });\n            await handler.doneWaiting();\n        }\n        catch (waitUntilError) {\n            if (waitUntilError instanceof Error) {\n                error = waitUntilError;\n            }\n        }\n        await handler.runCallbacks('handlerDidComplete', {\n            event,\n            request,\n            response,\n            error: error,\n        });\n        handler.destroy();\n        if (error) {\n            throw error;\n        }\n    }\n}\nexport { Strategy };\n/**\n * Classes extending the `Strategy` based class should implement this method,\n * and leverage the {@link workbox-strategies.StrategyHandler}\n * arg to perform all fetching and cache logic, which will ensure all relevant\n * cache, cache options, fetch options and plugins are used (per the current\n * strategy instance).\n *\n * @name _handle\n * @instance\n * @abstract\n * @function\n * @param {Request} request\n * @param {workbox-strategies.StrategyHandler} handler\n * @return {Promise<Response>}\n *\n * @memberof workbox-strategies.Strategy\n */\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { Strategy } from './Strategy.js';\nimport { messages } from './utils/messages.js';\nimport './_version.js';\n/**\n * An implementation of a [cache-first](https://developer.chrome.com/docs/workbox/caching-strategies-overview/#cache-first-falling-back-to-network)\n * request strategy.\n *\n * A cache first strategy is useful for assets that have been revisioned,\n * such as URLs like `/styles/example.a8f5f1.css`, since they\n * can be cached for long periods of time.\n *\n * If the network request fails, and there is no cache match, this will throw\n * a `WorkboxError` exception.\n *\n * @extends workbox-strategies.Strategy\n * @memberof workbox-strategies\n */\nclass CacheFirst extends Strategy {\n    /**\n     * @private\n     * @param {Request|string} request A request to run this strategy for.\n     * @param {workbox-strategies.StrategyHandler} handler The event that\n     *     triggered the request.\n     * @return {Promise<Response>}\n     */\n    async _handle(request, handler) {\n        const logs = [];\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(request, Request, {\n                moduleName: 'workbox-strategies',\n                className: this.constructor.name,\n                funcName: 'makeRequest',\n                paramName: 'request',\n            });\n        }\n        let response = await handler.cacheMatch(request);\n        let error = undefined;\n        if (!response) {\n            if (process.env.NODE_ENV !== 'production') {\n                logs.push(`No response found in the '${this.cacheName}' cache. ` +\n                    `Will respond with a network request.`);\n            }\n            try {\n                response = await handler.fetchAndCachePut(request);\n            }\n            catch (err) {\n                if (err instanceof Error) {\n                    error = err;\n                }\n            }\n            if (process.env.NODE_ENV !== 'production') {\n                if (response) {\n                    logs.push(`Got response from network.`);\n                }\n                else {\n                    logs.push(`Unable to get a response from the network.`);\n                }\n            }\n        }\n        else {\n            if (process.env.NODE_ENV !== 'production') {\n                logs.push(`Found a cached response in the '${this.cacheName}' cache.`);\n            }\n        }\n        if (process.env.NODE_ENV !== 'production') {\n            logger.groupCollapsed(messages.strategyStart(this.constructor.name, request));\n            for (const log of logs) {\n                logger.log(log);\n            }\n            messages.printFinalResponse(response);\n            logger.groupEnd();\n        }\n        if (!response) {\n            throw new WorkboxError('no-response', { url: request.url, error });\n        }\n        return response;\n    }\n}\nexport { CacheFirst };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport '../_version.js';\nexport const cacheOkAndOpaquePlugin = {\n    /**\n     * Returns a valid response (to allow caching) if the status is 200 (OK) or\n     * 0 (opaque).\n     *\n     * @param {Object} options\n     * @param {Response} options.response\n     * @return {Response|null}\n     *\n     * @private\n     */\n    cacheWillUpdate: async ({ response }) => {\n        if (response.status === 200 || response.status === 0) {\n            return response;\n        }\n        return null;\n    },\n};\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { cacheOkAndOpaquePlugin } from './plugins/cacheOkAndOpaquePlugin.js';\nimport { Strategy } from './Strategy.js';\nimport { messages } from './utils/messages.js';\nimport './_version.js';\n/**\n * An implementation of a\n * [network first](https://developer.chrome.com/docs/workbox/caching-strategies-overview/#network-first-falling-back-to-cache)\n * request strategy.\n *\n * By default, this strategy will cache responses with a 200 status code as\n * well as [opaque responses](https://developer.chrome.com/docs/workbox/caching-resources-during-runtime/#opaque-responses).\n * Opaque responses are are cross-origin requests where the response doesn't\n * support [CORS](https://enable-cors.org/).\n *\n * If the network request fails, and there is no cache match, this will throw\n * a `WorkboxError` exception.\n *\n * @extends workbox-strategies.Strategy\n * @memberof workbox-strategies\n */\nclass NetworkFirst extends Strategy {\n    /**\n     * @param {Object} [options]\n     * @param {string} [options.cacheName] Cache name to store and retrieve\n     * requests. Defaults to cache names provided by\n     * {@link workbox-core.cacheNames}.\n     * @param {Array<Object>} [options.plugins] [Plugins]{@link https://developers.google.com/web/tools/workbox/guides/using-plugins}\n     * to use in conjunction with this caching strategy.\n     * @param {Object} [options.fetchOptions] Values passed along to the\n     * [`init`](https://developer.mozilla.org/en-US/docs/Web/API/WindowOrWorkerGlobalScope/fetch#Parameters)\n     * of [non-navigation](https://github.com/GoogleChrome/workbox/issues/1796)\n     * `fetch()` requests made by this strategy.\n     * @param {Object} [options.matchOptions] [`CacheQueryOptions`](https://w3c.github.io/ServiceWorker/#dictdef-cachequeryoptions)\n     * @param {number} [options.networkTimeoutSeconds] If set, any network requests\n     * that fail to respond within the timeout will fallback to the cache.\n     *\n     * This option can be used to combat\n     * \"[lie-fi]{@link https://developers.google.com/web/fundamentals/performance/poor-connectivity/#lie-fi}\"\n     * scenarios.\n     */\n    constructor(options = {}) {\n        super(options);\n        // If this instance contains no plugins with a 'cacheWillUpdate' callback,\n        // prepend the `cacheOkAndOpaquePlugin` plugin to the plugins list.\n        if (!this.plugins.some((p) => 'cacheWillUpdate' in p)) {\n            this.plugins.unshift(cacheOkAndOpaquePlugin);\n        }\n        this._networkTimeoutSeconds = options.networkTimeoutSeconds || 0;\n        if (process.env.NODE_ENV !== 'production') {\n            if (this._networkTimeoutSeconds) {\n                assert.isType(this._networkTimeoutSeconds, 'number', {\n                    moduleName: 'workbox-strategies',\n                    className: this.constructor.name,\n                    funcName: 'constructor',\n                    paramName: 'networkTimeoutSeconds',\n                });\n            }\n        }\n    }\n    /**\n     * @private\n     * @param {Request|string} request A request to run this strategy for.\n     * @param {workbox-strategies.StrategyHandler} handler The event that\n     *     triggered the request.\n     * @return {Promise<Response>}\n     */\n    async _handle(request, handler) {\n        const logs = [];\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(request, Request, {\n                moduleName: 'workbox-strategies',\n                className: this.constructor.name,\n                funcName: 'handle',\n                paramName: 'makeRequest',\n            });\n        }\n        const promises = [];\n        let timeoutId;\n        if (this._networkTimeoutSeconds) {\n            const { id, promise } = this._getTimeoutPromise({ request, logs, handler });\n            timeoutId = id;\n            promises.push(promise);\n        }\n        const networkPromise = this._getNetworkPromise({\n            timeoutId,\n            request,\n            logs,\n            handler,\n        });\n        promises.push(networkPromise);\n        const response = await handler.waitUntil((async () => {\n            // Promise.race() will resolve as soon as the first promise resolves.\n            return ((await handler.waitUntil(Promise.race(promises))) ||\n                // If Promise.race() resolved with null, it might be due to a network\n                // timeout + a cache miss. If that were to happen, we'd rather wait until\n                // the networkPromise resolves instead of returning null.\n                // Note that it's fine to await an already-resolved promise, so we don't\n                // have to check to see if it's still \"in flight\".\n                (await networkPromise));\n        })());\n        if (process.env.NODE_ENV !== 'production') {\n            logger.groupCollapsed(messages.strategyStart(this.constructor.name, request));\n            for (const log of logs) {\n                logger.log(log);\n            }\n            messages.printFinalResponse(response);\n            logger.groupEnd();\n        }\n        if (!response) {\n            throw new WorkboxError('no-response', { url: request.url });\n        }\n        return response;\n    }\n    /**\n     * @param {Object} options\n     * @param {Request} options.request\n     * @param {Array} options.logs A reference to the logs array\n     * @param {Event} options.event\n     * @return {Promise<Response>}\n     *\n     * @private\n     */\n    _getTimeoutPromise({ request, logs, handler, }) {\n        let timeoutId;\n        const timeoutPromise = new Promise((resolve) => {\n            const onNetworkTimeout = async () => {\n                if (process.env.NODE_ENV !== 'production') {\n                    logs.push(`Timing out the network response at ` +\n                        `${this._networkTimeoutSeconds} seconds.`);\n                }\n                resolve(await handler.cacheMatch(request));\n            };\n            timeoutId = setTimeout(onNetworkTimeout, this._networkTimeoutSeconds * 1000);\n        });\n        return {\n            promise: timeoutPromise,\n            id: timeoutId,\n        };\n    }\n    /**\n     * @param {Object} options\n     * @param {number|undefined} options.timeoutId\n     * @param {Request} options.request\n     * @param {Array} options.logs A reference to the logs Array.\n     * @param {Event} options.event\n     * @return {Promise<Response>}\n     *\n     * @private\n     */\n    async _getNetworkPromise({ timeoutId, request, logs, handler, }) {\n        let error;\n        let response;\n        try {\n            response = await handler.fetchAndCachePut(request);\n        }\n        catch (fetchError) {\n            if (fetchError instanceof Error) {\n                error = fetchError;\n            }\n        }\n        if (timeoutId) {\n            clearTimeout(timeoutId);\n        }\n        if (process.env.NODE_ENV !== 'production') {\n            if (response) {\n                logs.push(`Got response from network.`);\n            }\n            else {\n                logs.push(`Unable to get a response from the network. Will respond ` +\n                    `with a cached response.`);\n            }\n        }\n        if (error || !response) {\n            response = await handler.cacheMatch(request);\n            if (process.env.NODE_ENV !== 'production') {\n                if (response) {\n                    logs.push(`Found a cached response in the '${this.cacheName}'` + ` cache.`);\n                }\n                else {\n                    logs.push(`No response found in the '${this.cacheName}' cache.`);\n                }\n            }\n        }\n        return response;\n    }\n}\nexport { NetworkFirst };\n","/*\n  Copyright 2018 Google LLC\n\n  Use of this source code is governed by an MIT-style\n  license that can be found in the LICENSE file or at\n  https://opensource.org/licenses/MIT.\n*/\nimport { assert } from 'workbox-core/_private/assert.js';\nimport { logger } from 'workbox-core/_private/logger.js';\nimport { WorkboxError } from 'workbox-core/_private/WorkboxError.js';\nimport { cacheOkAndOpaquePlugin } from './plugins/cacheOkAndOpaquePlugin.js';\nimport { Strategy } from './Strategy.js';\nimport { messages } from './utils/messages.js';\nimport './_version.js';\n/**\n * An implementation of a\n * [stale-while-revalidate](https://developer.chrome.com/docs/workbox/caching-strategies-overview/#stale-while-revalidate)\n * request strategy.\n *\n * Resources are requested from both the cache and the network in parallel.\n * The strategy will respond with the cached version if available, otherwise\n * wait for the network response. The cache is updated with the network response\n * with each successful request.\n *\n * By default, this strategy will cache responses with a 200 status code as\n * well as [opaque responses](https://developer.chrome.com/docs/workbox/caching-resources-during-runtime/#opaque-responses).\n * Opaque responses are cross-origin requests where the response doesn't\n * support [CORS](https://enable-cors.org/).\n *\n * If the network request fails, and there is no cache match, this will throw\n * a `WorkboxError` exception.\n *\n * @extends workbox-strategies.Strategy\n * @memberof workbox-strategies\n */\nclass StaleWhileRevalidate extends Strategy {\n    /**\n     * @param {Object} [options]\n     * @param {string} [options.cacheName] Cache name to store and retrieve\n     * requests. Defaults to cache names provided by\n     * {@link workbox-core.cacheNames}.\n     * @param {Array<Object>} [options.plugins] [Plugins]{@link https://developers.google.com/web/tools/workbox/guides/using-plugins}\n     * to use in conjunction with this caching strategy.\n     * @param {Object} [options.fetchOptions] Values passed along to the\n     * [`init`](https://developer.mozilla.org/en-US/docs/Web/API/WindowOrWorkerGlobalScope/fetch#Parameters)\n     * of [non-navigation](https://github.com/GoogleChrome/workbox/issues/1796)\n     * `fetch()` requests made by this strategy.\n     * @param {Object} [options.matchOptions] [`CacheQueryOptions`](https://w3c.github.io/ServiceWorker/#dictdef-cachequeryoptions)\n     */\n    constructor(options = {}) {\n        super(options);\n        // If this instance contains no plugins with a 'cacheWillUpdate' callback,\n        // prepend the `cacheOkAndOpaquePlugin` plugin to the plugins list.\n        if (!this.plugins.some((p) => 'cacheWillUpdate' in p)) {\n            this.plugins.unshift(cacheOkAndOpaquePlugin);\n        }\n    }\n    /**\n     * @private\n     * @param {Request|string} request A request to run this strategy for.\n     * @param {workbox-strategies.StrategyHandler} handler The event that\n     *     triggered the request.\n     * @return {Promise<Response>}\n     */\n    async _handle(request, handler) {\n        const logs = [];\n        if (process.env.NODE_ENV !== 'production') {\n            assert.isInstance(request, Request, {\n                moduleName: 'workbox-strategies',\n                className: this.constructor.name,\n                funcName: 'handle',\n                paramName: 'request',\n            });\n        }\n        const fetchAndCachePromise = handler.fetchAndCachePut(request).catch(() => {\n            // Swallow this error because a 'no-response' error will be thrown in\n            // main handler return flow. This will be in the `waitUntil()` flow.\n        });\n        void handler.waitUntil(fetchAndCachePromise);\n        let response = await handler.cacheMatch(request);\n        let error;\n        if (response) {\n            if (process.env.NODE_ENV !== 'production') {\n                logs.push(`Found a cached response in the '${this.cacheName}'` +\n                    ` cache. Will update with the network response in the background.`);\n            }\n        }\n        else {\n            if (process.env.NODE_ENV !== 'production') {\n                logs.push(`No response found in the '${this.cacheName}' cache. ` +\n                    `Will wait for the network response.`);\n            }\n            try {\n                // NOTE(philipwalton): Really annoying that we have to type cast here.\n                // https://github.com/microsoft/TypeScript/issues/20006\n                response = (await fetchAndCachePromise);\n            }\n            catch (err) {\n                if (err instanceof Error) {\n                    error = err;\n                }\n            }\n        }\n        if (process.env.NODE_ENV !== 'production') {\n            logger.groupCollapsed(messages.strategyStart(this.constructor.name, request));\n            for (const log of logs) {\n                logger.log(log);\n            }\n            messages.printFinalResponse(response);\n            logger.groupEnd();\n        }\n        if (!response) {\n            throw new WorkboxError('no-response', { url: request.url, error });\n        }\n        return response;\n    }\n}\nexport { StaleWhileRevalidate };\n","import { CacheableResponsePlugin } from 'workbox-cacheable-response';\nimport { ExpirationPlugin } from 'workbox-expiration';\nimport { RegExpRoute, registerRoute, Route } from 'workbox-routing';\nimport {\n  CacheFirst,\n  NetworkFirst,\n  StaleWhileRevalidate,\n} from 'workbox-strategies';\n\nself.__WB_DISABLE_DEV_LOGS = true;\n\nconst assetsRoute = new Route(\n  ({ request, sameOrigin }) => {\n    const isAsset =\n      request.destination === 'style' || request.destination === 'script';\n    const hasHash = /-[0-9a-f]{4,}\\./i.test(request.url);\n    return sameOrigin && isAsset && hasHash;\n  },\n  new NetworkFirst({\n    cacheName: 'assets',\n    networkTimeoutSeconds: 5,\n    plugins: [\n      new CacheableResponsePlugin({\n        statuses: [0, 200],\n      }),\n    ],\n  }),\n);\nregisterRoute(assetsRoute);\n\nconst imageRoute = new Route(\n  ({ request, sameOrigin }) => {\n    const isRemote = !sameOrigin;\n    const isImage = request.destination === 'image';\n    const isAvatar = request.url.includes('/avatars/');\n    const isCustomEmoji = request.url.includes('/custom/_emojis');\n    const isEmoji = request.url.includes('/emoji/');\n    return isRemote && isImage && (isAvatar || isCustomEmoji || isEmoji);\n  },\n  new CacheFirst({\n    cacheName: 'remote-images',\n    plugins: [\n      new ExpirationPlugin({\n        maxEntries: 50,\n        maxAgeSeconds: 3 * 24 * 60 * 60, // 3 days\n        purgeOnQuotaError: true,\n      }),\n      new CacheableResponsePlugin({\n        statuses: [0, 200],\n      }),\n    ],\n  }),\n);\nregisterRoute(imageRoute);\n\nconst iconsRoute = new Route(\n  ({ request, sameOrigin }) => {\n    const isIcon = request.url.includes('/icons/');\n    return sameOrigin && isIcon;\n  },\n  new CacheFirst({\n    cacheName: 'icons',\n    plugins: [\n      new ExpirationPlugin({\n        maxEntries: 300,\n        maxAgeSeconds: 3 * 24 * 60 * 60, // 3 days\n        purgeOnQuotaError: true,\n      }),\n      new CacheableResponsePlugin({\n        statuses: [0, 200],\n      }),\n    ],\n  }),\n);\nregisterRoute(iconsRoute);\n\n// 1-day cache for\n// - /api/v1/instance\n// - /api/v1/custom_emojis\n// - /api/v1/preferences\n// - /api/v1/lists/:id\n// - /api/v1/announcements\nconst apiExtendedRoute = new RegExpRoute(\n  /^https?:\\/\\/[^\\/]+\\/api\\/v\\d+\\/(instance|custom_emojis|preferences|lists\\/\\d+|announcements)$/,\n  new StaleWhileRevalidate({\n    cacheName: 'api-extended',\n    plugins: [\n      new ExpirationPlugin({\n        maxAgeSeconds: 24 * 60 * 60, // 1 day\n      }),\n      new CacheableResponsePlugin({\n        statuses: [0, 200],\n      }),\n    ],\n  }),\n);\nregisterRoute(apiExtendedRoute);\n\n// Note: expiration is not working as expected\n// https://github.com/GoogleChrome/workbox/issues/3316\n//\n// const apiIntermediateRoute = new RegExpRoute(\n//   // Matches:\n//   // - trends/*\n//   // - timelines/link\n//   /^https?:\\/\\/[^\\/]+\\/api\\/v\\d+\\/(trends|timelines\\/link)/,\n//   new StaleWhileRevalidate({\n//     cacheName: 'api-intermediate',\n//     plugins: [\n//       new ExpirationPlugin({\n//         maxAgeSeconds: 1 * 60, // 1min\n//       }),\n//       new CacheableResponsePlugin({\n//         statuses: [0, 200],\n//       }),\n//     ],\n//   }),\n// );\n// registerRoute(apiIntermediateRoute);\n\nconst apiRoute = new RegExpRoute(\n  // Matches:\n  // - statuses/:id/context - some contexts are really huge\n  /^https?:\\/\\/[^\\/]+\\/api\\/v\\d+\\/(statuses\\/\\d+\\/context)/,\n  new NetworkFirst({\n    cacheName: 'api',\n    networkTimeoutSeconds: 5,\n    plugins: [\n      new ExpirationPlugin({\n        maxAgeSeconds: 5 * 60, // 5 minutes\n      }),\n      new CacheableResponsePlugin({\n        statuses: [0, 200],\n      }),\n    ],\n  }),\n);\nregisterRoute(apiRoute);\n\n// PUSH NOTIFICATIONS\n// ==================\n\nself.addEventListener('push', (event) => {\n  const { data } = event;\n  if (data) {\n    const payload = data.json();\n    console.log('PUSH payload', payload);\n    const {\n      access_token,\n      title,\n      body,\n      icon,\n      notification_id,\n      notification_type,\n      preferred_locale,\n    } = payload;\n\n    if (!!navigator.setAppBadge) {\n      if (notification_type === 'mention') {\n        navigator.setAppBadge(1);\n      }\n    }\n\n    event.waitUntil(\n      self.registration.showNotification(title, {\n        body,\n        icon,\n        dir: 'auto',\n        badge: '/logo-badge-72.png',\n        lang: preferred_locale,\n        tag: notification_id,\n        timestamp: Date.now(),\n        data: {\n          access_token,\n          notification_type,\n        },\n      }),\n    );\n  }\n});\n\nself.addEventListener('notificationclick', (event) => {\n  const payload = event.notification;\n  console.log('NOTIFICATION CLICK payload', payload);\n  const { badge, body, data, dir, icon, lang, tag, timestamp, title } = payload;\n  const { access_token, notification_type } = data;\n  const url = `/#/notifications?id=${tag}&access_token=${btoa(access_token)}`;\n\n  event.waitUntil(\n    (async () => {\n      const clients = await self.clients.matchAll({\n        type: 'window',\n        includeUncontrolled: true,\n      });\n      console.log('NOTIFICATION CLICK clients 1', clients);\n      if (clients.length && 'navigate' in clients[0]) {\n        console.log('NOTIFICATION CLICK clients 2', clients);\n        const bestClient =\n          clients.find(\n            (client) => client.focused || client.visibilityState === 'visible',\n          ) || clients[0];\n        console.log('NOTIFICATION CLICK navigate', url);\n        if (bestClient) {\n          console.log('NOTIFICATION CLICK postMessage', bestClient);\n          bestClient.focus();\n          bestClient.postMessage?.({\n            type: 'notification',\n            id: tag,\n            accessToken: access_token,\n          });\n        } else {\n          console.log('NOTIFICATION CLICK openWindow', url);\n          await self.clients.openWindow(url);\n        }\n        // }\n      } else {\n        console.log('NOTIFICATION CLICK openWindow', url);\n        await self.clients.openWindow(url);\n      }\n      await event.notification.close();\n    })(),\n  );\n});\n"],"names":["fallback","code","args","msg","messageGenerator","WorkboxError","errorCode","details","message","getFriendlyURL","url","CacheableResponse","config","response","cacheable","headerName","CacheableResponsePlugin","dontWaitFor","promise","instanceOfAny","object","constructors","c","idbProxyableTypes","cursorAdvanceMethods","getIdbProxyableTypes","getCursorAdvanceMethods","cursorRequestMap","transactionDoneMap","transactionStoreNamesMap","transformCache","reverseTransformCache","promisifyRequest","request","resolve","reject","unlisten","success","error","wrap","value","cacheDonePromiseForTransaction","tx","done","complete","idbProxyTraps","target","prop","receiver","replaceTraps","callback","wrapFunction","func","storeNames","unwrap","transformCachableValue","newValue","openDB","name","version","blocked","upgrade","blocking","terminated","openPromise","event","db","deleteDB","readMethods","writeMethods","cachedMethods","getMethod","targetFuncName","useIndex","isWrite","method","storeName","oldTraps","DB_NAME","CACHE_OBJECT_STORE","normalizeURL","unNormalizedUrl","CacheTimestampsModel","cacheName","objStore","timestamp","entry","minTimestamp","maxCount","cursor","entriesToDelete","entriesNotDeletedCount","result","urlsDeleted","CacheExpiration","urlsExpired","cache","expireOlderThan","_cacheNameDetails","_createCacheName","eachCacheNameDetail","fn","key","cacheNames","userCacheName","quotaErrorCallbacks","registerQuotaErrorCallback","ExpirationPlugin","cachedResponse","isFresh","cacheExpiration","updateTimestampDone","dateHeaderTimestamp","now","dateHeader","headerTime","defaultMethod","normalizeHandler","handler","Route","match","RegExpRoute","regExp","Router","responsePromise","payload","requestPromises","sameOrigin","params","route","err","catchHandler","catchErr","routes","matchResult","routeIndex","defaultRouter","getOrCreateDefaultRouter","registerRoute","capture","captureUrl","matchCallback","stripParams","fullURL","ignoreParams","strippedURL","param","cacheMatchIgnoreParams","matchOptions","strippedRequestURL","keysOptions","cacheKeys","cacheKey","strippedCacheKeyURL","Deferred","executeQuotaErrorCallbacks","timeout","ms","toRequest","input","StrategyHandler","strategy","options","plugin","possiblePreloadResponse","originalRequest","cb","pluginFilteredRequest","fetchResponse","responseClone","effectiveRequest","multiMatchOptions","responseToCache","hasCacheUpdateCallback","oldResponse","mode","state","statefulParam","pluginsUsed","Strategy","responseDone","handlerDone","waitUntilError","CacheFirst","cacheOkAndOpaquePlugin","NetworkFirst","p","logs","promises","timeoutId","id","networkPromise","fetchError","StaleWhileRevalidate","fetchAndCachePromise","assetsRoute","isAsset","hasHash","imageRoute","isRemote","isImage","isAvatar","isCustomEmoji","isEmoji","iconsRoute","isIcon","apiExtendedRoute","apiRoute","data","access_token","title","body","icon","notification_id","notification_type","preferred_locale","badge","dir","lang","tag","_a","clients","bestClient","client"],"mappings":"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","x_google_ignoreList":[0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35]}