g(x,C)?(a[d]=x,a[n]=c,d=n):(a[d]=C,a[m]=c,d=m);else if(ng(x,c))a[d]=x,a[n]=c,d=n;else break a}}return b}\nfunction g(a,b){var c=a.sortIndex-b.sortIndex;return 0!==c?c:a.id-b.id}if(\"object\"===typeof performance&&\"function\"===typeof performance.now){var l=performance;exports.unstable_now=function(){return l.now()}}else{var p=Date,q=p.now();exports.unstable_now=function(){return p.now()-q}}var r=[],t=[],u=1,v=null,y=3,z=!1,A=!1,B=!1,D=\"function\"===typeof setTimeout?setTimeout:null,E=\"function\"===typeof clearTimeout?clearTimeout:null,F=\"undefined\"!==typeof setImmediate?setImmediate:null;\n\"undefined\"!==typeof navigator&&void 0!==navigator.scheduling&&void 0!==navigator.scheduling.isInputPending&&navigator.scheduling.isInputPending.bind(navigator.scheduling);function G(a){for(var b=h(t);null!==b;){if(null===b.callback)k(t);else if(b.startTime<=a)k(t),b.sortIndex=b.expirationTime,f(r,b);else break;b=h(t)}}function H(a){B=!1;G(a);if(!A)if(null!==h(r))A=!0,I(J);else{var b=h(t);null!==b&&K(H,b.startTime-a)}}\nfunction J(a,b){A=!1;B&&(B=!1,E(L),L=-1);z=!0;var c=y;try{G(b);for(v=h(r);null!==v&&(!(v.expirationTime>b)||a&&!M());){var d=v.callback;if(\"function\"===typeof d){v.callback=null;y=v.priorityLevel;var e=d(v.expirationTime<=b);b=exports.unstable_now();\"function\"===typeof e?v.callback=e:v===h(r)&&k(r);G(b)}else k(r);v=h(r)}if(null!==v)var w=!0;else{var m=h(t);null!==m&&K(H,m.startTime-b);w=!1}return w}finally{v=null,y=c,z=!1}}var N=!1,O=null,L=-1,P=5,Q=-1;\nfunction M(){return exports.unstable_now()-Qa||125d?(a.sortIndex=c,f(t,a),null===h(r)&&a===h(t)&&(B?(E(L),L=-1):B=!0,K(H,c-d))):(a.sortIndex=e,f(r,a),A||z||(A=!0,I(J)));return a};\nexports.unstable_shouldYield=M;exports.unstable_wrapCallback=function(a){var b=y;return function(){var c=y;y=b;try{return a.apply(this,arguments)}finally{y=c}}};\n","'use strict';\n\nif (process.env.NODE_ENV === 'production') {\n module.exports = require('./cjs/scheduler.production.min.js');\n} else {\n module.exports = require('./cjs/scheduler.development.js');\n}\n","/**\n * Copyright (c) 2014-present, Facebook, Inc.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE file in the root directory of this source tree.\n */\n\n'use strict';\n\n/**\n * Similar to invariant but only logs a warning if the condition is not met.\n * This can be used to log issues in development environments in critical\n * paths. Removing the logging code for production environments will keep the\n * same logic and follow the same code paths.\n */\n\nvar __DEV__ = process.env.NODE_ENV !== 'production';\n\nvar warning = function() {};\n\nif (__DEV__) {\n var printWarning = function printWarning(format, args) {\n var len = arguments.length;\n args = new Array(len > 1 ? len - 1 : 0);\n for (var key = 1; key < len; key++) {\n args[key - 1] = arguments[key];\n }\n var argIndex = 0;\n var message = 'Warning: ' +\n format.replace(/%s/g, function() {\n return args[argIndex++];\n });\n if (typeof console !== 'undefined') {\n console.error(message);\n }\n try {\n // --- Welcome to debugging React ---\n // This error was thrown as a convenience so that you can use this stack\n // to find the callsite that caused this warning to fire.\n throw new Error(message);\n } catch (x) {}\n }\n\n warning = function(condition, format, args) {\n var len = arguments.length;\n args = new Array(len > 2 ? len - 2 : 0);\n for (var key = 2; key < len; key++) {\n args[key - 2] = arguments[key];\n }\n if (format === undefined) {\n throw new Error(\n '`warning(condition, format, ...args)` requires a warning ' +\n 'message argument'\n );\n }\n if (!condition) {\n printWarning.apply(null, [format].concat(args));\n }\n };\n}\n\nmodule.exports = warning;\n","/*!\n\tCopyright (c) 2018 Jed Watson.\n\tLicensed under the MIT License (MIT), see\n\thttp://jedwatson.github.io/classnames\n*/\n/* global define */\n\n(function () {\n\t'use strict';\n\n\tvar hasOwn = {}.hasOwnProperty;\n\n\tfunction classNames () {\n\t\tvar classes = '';\n\n\t\tfor (var i = 0; i < arguments.length; i++) {\n\t\t\tvar arg = arguments[i];\n\t\t\tif (arg) {\n\t\t\t\tclasses = appendClass(classes, parseValue(arg));\n\t\t\t}\n\t\t}\n\n\t\treturn classes;\n\t}\n\n\tfunction parseValue (arg) {\n\t\tif (typeof arg === 'string' || typeof arg === 'number') {\n\t\t\treturn arg;\n\t\t}\n\n\t\tif (typeof arg !== 'object') {\n\t\t\treturn '';\n\t\t}\n\n\t\tif (Array.isArray(arg)) {\n\t\t\treturn classNames.apply(null, arg);\n\t\t}\n\n\t\tif (arg.toString !== Object.prototype.toString && !arg.toString.toString().includes('[native code]')) {\n\t\t\treturn arg.toString();\n\t\t}\n\n\t\tvar classes = '';\n\n\t\tfor (var key in arg) {\n\t\t\tif (hasOwn.call(arg, key) && arg[key]) {\n\t\t\t\tclasses = appendClass(classes, key);\n\t\t\t}\n\t\t}\n\n\t\treturn classes;\n\t}\n\n\tfunction appendClass (value, newClass) {\n\t\tif (!newClass) {\n\t\t\treturn value;\n\t\t}\n\t\n\t\tif (value) {\n\t\t\treturn value + ' ' + newClass;\n\t\t}\n\t\n\t\treturn value + newClass;\n\t}\n\n\tif (typeof module !== 'undefined' && module.exports) {\n\t\tclassNames.default = classNames;\n\t\tmodule.exports = classNames;\n\t} else if (typeof define === 'function' && typeof define.amd === 'object' && define.amd) {\n\t\t// register as 'classnames', consistent with npm package name\n\t\tdefine('classnames', [], function () {\n\t\t\treturn classNames;\n\t\t});\n\t} else {\n\t\twindow.classNames = classNames;\n\t}\n}());\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\tid: moduleId,\n\t\tloaded: false,\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n\t// Flag the module as loaded\n\tmodule.loaded = true;\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// getDefaultExport function for compatibility with non-harmony modules\n__webpack_require__.n = (module) => {\n\tvar getter = module && module.__esModule ?\n\t\t() => (module['default']) :\n\t\t() => (module);\n\t__webpack_require__.d(getter, { a: getter });\n\treturn getter;\n};","// define getter functions for harmony exports\n__webpack_require__.d = (exports, definition) => {\n\tfor(var key in definition) {\n\t\tif(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {\n\t\t\tObject.defineProperty(exports, key, { enumerable: true, get: definition[key] });\n\t\t}\n\t}\n};","__webpack_require__.g = (function() {\n\tif (typeof globalThis === 'object') return globalThis;\n\ttry {\n\t\treturn this || new Function('return this')();\n\t} catch (e) {\n\t\tif (typeof window === 'object') return window;\n\t}\n})();","__webpack_require__.hmd = (module) => {\n\tmodule = Object.create(module);\n\tif (!module.children) module.children = [];\n\tObject.defineProperty(module, 'exports', {\n\t\tenumerable: true,\n\t\tset: () => {\n\t\t\tthrow new Error('ES Modules may not assign module.exports or exports.*, Use ESM export syntax, instead: ' + module.id);\n\t\t}\n\t});\n\treturn module;\n};","__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))","// define __esModule on exports\n__webpack_require__.r = (exports) => {\n\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n\t}\n\tObject.defineProperty(exports, '__esModule', { value: true });\n};","__webpack_require__.nmd = (module) => {\n\tmodule.paths = [];\n\tif (!module.children) module.children = [];\n\treturn module;\n};","/**\n * @remix-run/router v1.14.2\n *\n * Copyright (c) Remix Software Inc.\n *\n * This source code is licensed under the MIT license found in the\n * LICENSE.md file in the root directory of this source tree.\n *\n * @license MIT\n */\nfunction _extends() {\n _extends = Object.assign ? Object.assign.bind() : function (target) {\n for (var i = 1; i < arguments.length; i++) {\n var source = arguments[i];\n for (var key in source) {\n if (Object.prototype.hasOwnProperty.call(source, key)) {\n target[key] = source[key];\n }\n }\n }\n return target;\n };\n return _extends.apply(this, arguments);\n}\n\n////////////////////////////////////////////////////////////////////////////////\n//#region Types and Constants\n////////////////////////////////////////////////////////////////////////////////\n/**\n * Actions represent the type of change to a location value.\n */\nvar Action;\n(function (Action) {\n /**\n * A POP indicates a change to an arbitrary index in the history stack, such\n * as a back or forward navigation. It does not describe the direction of the\n * navigation, only that the current index changed.\n *\n * Note: This is the default action for newly created history objects.\n */\n Action[\"Pop\"] = \"POP\";\n /**\n * A PUSH indicates a new entry being added to the history stack, such as when\n * a link is clicked and a new page loads. When this happens, all subsequent\n * entries in the stack are lost.\n */\n Action[\"Push\"] = \"PUSH\";\n /**\n * A REPLACE indicates the entry at the current index in the history stack\n * being replaced by a new one.\n */\n Action[\"Replace\"] = \"REPLACE\";\n})(Action || (Action = {}));\nconst PopStateEventType = \"popstate\";\n/**\n * Memory history stores the current location in memory. It is designed for use\n * in stateful non-browser environments like tests and React Native.\n */\nfunction createMemoryHistory(options) {\n if (options === void 0) {\n options = {};\n }\n let {\n initialEntries = [\"/\"],\n initialIndex,\n v5Compat = false\n } = options;\n let entries; // Declare so we can access from createMemoryLocation\n entries = initialEntries.map((entry, index) => createMemoryLocation(entry, typeof entry === \"string\" ? null : entry.state, index === 0 ? \"default\" : undefined));\n let index = clampIndex(initialIndex == null ? entries.length - 1 : initialIndex);\n let action = Action.Pop;\n let listener = null;\n function clampIndex(n) {\n return Math.min(Math.max(n, 0), entries.length - 1);\n }\n function getCurrentLocation() {\n return entries[index];\n }\n function createMemoryLocation(to, state, key) {\n if (state === void 0) {\n state = null;\n }\n let location = createLocation(entries ? getCurrentLocation().pathname : \"/\", to, state, key);\n warning(location.pathname.charAt(0) === \"/\", \"relative pathnames are not supported in memory history: \" + JSON.stringify(to));\n return location;\n }\n function createHref(to) {\n return typeof to === \"string\" ? to : createPath(to);\n }\n let history = {\n get index() {\n return index;\n },\n get action() {\n return action;\n },\n get location() {\n return getCurrentLocation();\n },\n createHref,\n createURL(to) {\n return new URL(createHref(to), \"http://localhost\");\n },\n encodeLocation(to) {\n let path = typeof to === \"string\" ? parsePath(to) : to;\n return {\n pathname: path.pathname || \"\",\n search: path.search || \"\",\n hash: path.hash || \"\"\n };\n },\n push(to, state) {\n action = Action.Push;\n let nextLocation = createMemoryLocation(to, state);\n index += 1;\n entries.splice(index, entries.length, nextLocation);\n if (v5Compat && listener) {\n listener({\n action,\n location: nextLocation,\n delta: 1\n });\n }\n },\n replace(to, state) {\n action = Action.Replace;\n let nextLocation = createMemoryLocation(to, state);\n entries[index] = nextLocation;\n if (v5Compat && listener) {\n listener({\n action,\n location: nextLocation,\n delta: 0\n });\n }\n },\n go(delta) {\n action = Action.Pop;\n let nextIndex = clampIndex(index + delta);\n let nextLocation = entries[nextIndex];\n index = nextIndex;\n if (listener) {\n listener({\n action,\n location: nextLocation,\n delta\n });\n }\n },\n listen(fn) {\n listener = fn;\n return () => {\n listener = null;\n };\n }\n };\n return history;\n}\n/**\n * Browser history stores the location in regular URLs. This is the standard for\n * most web apps, but it requires some configuration on the server to ensure you\n * serve the same app at multiple URLs.\n *\n * @see https://github.com/remix-run/history/tree/main/docs/api-reference.md#createbrowserhistory\n */\nfunction createBrowserHistory(options) {\n if (options === void 0) {\n options = {};\n }\n function createBrowserLocation(window, globalHistory) {\n let {\n pathname,\n search,\n hash\n } = window.location;\n return createLocation(\"\", {\n pathname,\n search,\n hash\n },\n // state defaults to `null` because `window.history.state` does\n globalHistory.state && globalHistory.state.usr || null, globalHistory.state && globalHistory.state.key || \"default\");\n }\n function createBrowserHref(window, to) {\n return typeof to === \"string\" ? to : createPath(to);\n }\n return getUrlBasedHistory(createBrowserLocation, createBrowserHref, null, options);\n}\n/**\n * Hash history stores the location in window.location.hash. This makes it ideal\n * for situations where you don't want to send the location to the server for\n * some reason, either because you do cannot configure it or the URL space is\n * reserved for something else.\n *\n * @see https://github.com/remix-run/history/tree/main/docs/api-reference.md#createhashhistory\n */\nfunction createHashHistory(options) {\n if (options === void 0) {\n options = {};\n }\n function createHashLocation(window, globalHistory) {\n let {\n pathname = \"/\",\n search = \"\",\n hash = \"\"\n } = parsePath(window.location.hash.substr(1));\n // Hash URL should always have a leading / just like window.location.pathname\n // does, so if an app ends up at a route like /#something then we add a\n // leading slash so all of our path-matching behaves the same as if it would\n // in a browser router. This is particularly important when there exists a\n // root splat route () since that matches internally against\n // \"/*\" and we'd expect /#something to 404 in a hash router app.\n if (!pathname.startsWith(\"/\") && !pathname.startsWith(\".\")) {\n pathname = \"/\" + pathname;\n }\n return createLocation(\"\", {\n pathname,\n search,\n hash\n },\n // state defaults to `null` because `window.history.state` does\n globalHistory.state && globalHistory.state.usr || null, globalHistory.state && globalHistory.state.key || \"default\");\n }\n function createHashHref(window, to) {\n let base = window.document.querySelector(\"base\");\n let href = \"\";\n if (base && base.getAttribute(\"href\")) {\n let url = window.location.href;\n let hashIndex = url.indexOf(\"#\");\n href = hashIndex === -1 ? url : url.slice(0, hashIndex);\n }\n return href + \"#\" + (typeof to === \"string\" ? to : createPath(to));\n }\n function validateHashLocation(location, to) {\n warning(location.pathname.charAt(0) === \"/\", \"relative pathnames are not supported in hash history.push(\" + JSON.stringify(to) + \")\");\n }\n return getUrlBasedHistory(createHashLocation, createHashHref, validateHashLocation, options);\n}\nfunction invariant(value, message) {\n if (value === false || value === null || typeof value === \"undefined\") {\n throw new Error(message);\n }\n}\nfunction warning(cond, message) {\n if (!cond) {\n // eslint-disable-next-line no-console\n if (typeof console !== \"undefined\") console.warn(message);\n try {\n // Welcome to debugging history!\n //\n // This error is thrown as a convenience, so you can more easily\n // find the source for a warning that appears in the console by\n // enabling \"pause on exceptions\" in your JavaScript debugger.\n throw new Error(message);\n // eslint-disable-next-line no-empty\n } catch (e) {}\n }\n}\nfunction createKey() {\n return Math.random().toString(36).substr(2, 8);\n}\n/**\n * For browser-based histories, we combine the state and key into an object\n */\nfunction getHistoryState(location, index) {\n return {\n usr: location.state,\n key: location.key,\n idx: index\n };\n}\n/**\n * Creates a Location object with a unique key from the given Path\n */\nfunction createLocation(current, to, state, key) {\n if (state === void 0) {\n state = null;\n }\n let location = _extends({\n pathname: typeof current === \"string\" ? current : current.pathname,\n search: \"\",\n hash: \"\"\n }, typeof to === \"string\" ? parsePath(to) : to, {\n state,\n // TODO: This could be cleaned up. push/replace should probably just take\n // full Locations now and avoid the need to run through this flow at all\n // But that's a pretty big refactor to the current test suite so going to\n // keep as is for the time being and just let any incoming keys take precedence\n key: to && to.key || key || createKey()\n });\n return location;\n}\n/**\n * Creates a string URL path from the given pathname, search, and hash components.\n */\nfunction createPath(_ref) {\n let {\n pathname = \"/\",\n search = \"\",\n hash = \"\"\n } = _ref;\n if (search && search !== \"?\") pathname += search.charAt(0) === \"?\" ? search : \"?\" + search;\n if (hash && hash !== \"#\") pathname += hash.charAt(0) === \"#\" ? hash : \"#\" + hash;\n return pathname;\n}\n/**\n * Parses a string URL path into its separate pathname, search, and hash components.\n */\nfunction parsePath(path) {\n let parsedPath = {};\n if (path) {\n let hashIndex = path.indexOf(\"#\");\n if (hashIndex >= 0) {\n parsedPath.hash = path.substr(hashIndex);\n path = path.substr(0, hashIndex);\n }\n let searchIndex = path.indexOf(\"?\");\n if (searchIndex >= 0) {\n parsedPath.search = path.substr(searchIndex);\n path = path.substr(0, searchIndex);\n }\n if (path) {\n parsedPath.pathname = path;\n }\n }\n return parsedPath;\n}\nfunction getUrlBasedHistory(getLocation, createHref, validateLocation, options) {\n if (options === void 0) {\n options = {};\n }\n let {\n window = document.defaultView,\n v5Compat = false\n } = options;\n let globalHistory = window.history;\n let action = Action.Pop;\n let listener = null;\n let index = getIndex();\n // Index should only be null when we initialize. If not, it's because the\n // user called history.pushState or history.replaceState directly, in which\n // case we should log a warning as it will result in bugs.\n if (index == null) {\n index = 0;\n globalHistory.replaceState(_extends({}, globalHistory.state, {\n idx: index\n }), \"\");\n }\n function getIndex() {\n let state = globalHistory.state || {\n idx: null\n };\n return state.idx;\n }\n function handlePop() {\n action = Action.Pop;\n let nextIndex = getIndex();\n let delta = nextIndex == null ? null : nextIndex - index;\n index = nextIndex;\n if (listener) {\n listener({\n action,\n location: history.location,\n delta\n });\n }\n }\n function push(to, state) {\n action = Action.Push;\n let location = createLocation(history.location, to, state);\n if (validateLocation) validateLocation(location, to);\n index = getIndex() + 1;\n let historyState = getHistoryState(location, index);\n let url = history.createHref(location);\n // try...catch because iOS limits us to 100 pushState calls :/\n try {\n globalHistory.pushState(historyState, \"\", url);\n } catch (error) {\n // If the exception is because `state` can't be serialized, let that throw\n // outwards just like a replace call would so the dev knows the cause\n // https://html.spec.whatwg.org/multipage/nav-history-apis.html#shared-history-push/replace-state-steps\n // https://html.spec.whatwg.org/multipage/structured-data.html#structuredserializeinternal\n if (error instanceof DOMException && error.name === \"DataCloneError\") {\n throw error;\n }\n // They are going to lose state here, but there is no real\n // way to warn them about it since the page will refresh...\n window.location.assign(url);\n }\n if (v5Compat && listener) {\n listener({\n action,\n location: history.location,\n delta: 1\n });\n }\n }\n function replace(to, state) {\n action = Action.Replace;\n let location = createLocation(history.location, to, state);\n if (validateLocation) validateLocation(location, to);\n index = getIndex();\n let historyState = getHistoryState(location, index);\n let url = history.createHref(location);\n globalHistory.replaceState(historyState, \"\", url);\n if (v5Compat && listener) {\n listener({\n action,\n location: history.location,\n delta: 0\n });\n }\n }\n function createURL(to) {\n // window.location.origin is \"null\" (the literal string value) in Firefox\n // under certain conditions, notably when serving from a local HTML file\n // See https://bugzilla.mozilla.org/show_bug.cgi?id=878297\n let base = window.location.origin !== \"null\" ? window.location.origin : window.location.href;\n let href = typeof to === \"string\" ? to : createPath(to);\n invariant(base, \"No window.location.(origin|href) available to create URL for href: \" + href);\n return new URL(href, base);\n }\n let history = {\n get action() {\n return action;\n },\n get location() {\n return getLocation(window, globalHistory);\n },\n listen(fn) {\n if (listener) {\n throw new Error(\"A history only accepts one active listener\");\n }\n window.addEventListener(PopStateEventType, handlePop);\n listener = fn;\n return () => {\n window.removeEventListener(PopStateEventType, handlePop);\n listener = null;\n };\n },\n createHref(to) {\n return createHref(window, to);\n },\n createURL,\n encodeLocation(to) {\n // Encode a Location the same way window.location would\n let url = createURL(to);\n return {\n pathname: url.pathname,\n search: url.search,\n hash: url.hash\n };\n },\n push,\n replace,\n go(n) {\n return globalHistory.go(n);\n }\n };\n return history;\n}\n//#endregion\n\nvar ResultType;\n(function (ResultType) {\n ResultType[\"data\"] = \"data\";\n ResultType[\"deferred\"] = \"deferred\";\n ResultType[\"redirect\"] = \"redirect\";\n ResultType[\"error\"] = \"error\";\n})(ResultType || (ResultType = {}));\nconst immutableRouteKeys = new Set([\"lazy\", \"caseSensitive\", \"path\", \"id\", \"index\", \"children\"]);\nfunction isIndexRoute(route) {\n return route.index === true;\n}\n// Walk the route tree generating unique IDs where necessary, so we are working\n// solely with AgnosticDataRouteObject's within the Router\nfunction convertRoutesToDataRoutes(routes, mapRouteProperties, parentPath, manifest) {\n if (parentPath === void 0) {\n parentPath = [];\n }\n if (manifest === void 0) {\n manifest = {};\n }\n return routes.map((route, index) => {\n let treePath = [...parentPath, index];\n let id = typeof route.id === \"string\" ? route.id : treePath.join(\"-\");\n invariant(route.index !== true || !route.children, \"Cannot specify children on an index route\");\n invariant(!manifest[id], \"Found a route id collision on id \\\"\" + id + \"\\\". Route \" + \"id's must be globally unique within Data Router usages\");\n if (isIndexRoute(route)) {\n let indexRoute = _extends({}, route, mapRouteProperties(route), {\n id\n });\n manifest[id] = indexRoute;\n return indexRoute;\n } else {\n let pathOrLayoutRoute = _extends({}, route, mapRouteProperties(route), {\n id,\n children: undefined\n });\n manifest[id] = pathOrLayoutRoute;\n if (route.children) {\n pathOrLayoutRoute.children = convertRoutesToDataRoutes(route.children, mapRouteProperties, treePath, manifest);\n }\n return pathOrLayoutRoute;\n }\n });\n}\n/**\n * Matches the given routes to a location and returns the match data.\n *\n * @see https://reactrouter.com/utils/match-routes\n */\nfunction matchRoutes(routes, locationArg, basename) {\n if (basename === void 0) {\n basename = \"/\";\n }\n let location = typeof locationArg === \"string\" ? parsePath(locationArg) : locationArg;\n let pathname = stripBasename(location.pathname || \"/\", basename);\n if (pathname == null) {\n return null;\n }\n let branches = flattenRoutes(routes);\n rankRouteBranches(branches);\n let matches = null;\n for (let i = 0; matches == null && i < branches.length; ++i) {\n matches = matchRouteBranch(branches[i],\n // Incoming pathnames are generally encoded from either window.location\n // or from router.navigate, but we want to match against the unencoded\n // paths in the route definitions. Memory router locations won't be\n // encoded here but there also shouldn't be anything to decode so this\n // should be a safe operation. This avoids needing matchRoutes to be\n // history-aware.\n safelyDecodeURI(pathname));\n }\n return matches;\n}\nfunction convertRouteMatchToUiMatch(match, loaderData) {\n let {\n route,\n pathname,\n params\n } = match;\n return {\n id: route.id,\n pathname,\n params,\n data: loaderData[route.id],\n handle: route.handle\n };\n}\nfunction flattenRoutes(routes, branches, parentsMeta, parentPath) {\n if (branches === void 0) {\n branches = [];\n }\n if (parentsMeta === void 0) {\n parentsMeta = [];\n }\n if (parentPath === void 0) {\n parentPath = \"\";\n }\n let flattenRoute = (route, index, relativePath) => {\n let meta = {\n relativePath: relativePath === undefined ? route.path || \"\" : relativePath,\n caseSensitive: route.caseSensitive === true,\n childrenIndex: index,\n route\n };\n if (meta.relativePath.startsWith(\"/\")) {\n invariant(meta.relativePath.startsWith(parentPath), \"Absolute route path \\\"\" + meta.relativePath + \"\\\" nested under path \" + (\"\\\"\" + parentPath + \"\\\" is not valid. An absolute child route path \") + \"must start with the combined path of all its parent routes.\");\n meta.relativePath = meta.relativePath.slice(parentPath.length);\n }\n let path = joinPaths([parentPath, meta.relativePath]);\n let routesMeta = parentsMeta.concat(meta);\n // Add the children before adding this route to the array, so we traverse the\n // route tree depth-first and child routes appear before their parents in\n // the \"flattened\" version.\n if (route.children && route.children.length > 0) {\n invariant(\n // Our types know better, but runtime JS may not!\n // @ts-expect-error\n route.index !== true, \"Index routes must not have child routes. Please remove \" + (\"all child routes from route path \\\"\" + path + \"\\\".\"));\n flattenRoutes(route.children, branches, routesMeta, path);\n }\n // Routes without a path shouldn't ever match by themselves unless they are\n // index routes, so don't add them to the list of possible branches.\n if (route.path == null && !route.index) {\n return;\n }\n branches.push({\n path,\n score: computeScore(path, route.index),\n routesMeta\n });\n };\n routes.forEach((route, index) => {\n var _route$path;\n // coarse-grain check for optional params\n if (route.path === \"\" || !((_route$path = route.path) != null && _route$path.includes(\"?\"))) {\n flattenRoute(route, index);\n } else {\n for (let exploded of explodeOptionalSegments(route.path)) {\n flattenRoute(route, index, exploded);\n }\n }\n });\n return branches;\n}\n/**\n * Computes all combinations of optional path segments for a given path,\n * excluding combinations that are ambiguous and of lower priority.\n *\n * For example, `/one/:two?/three/:four?/:five?` explodes to:\n * - `/one/three`\n * - `/one/:two/three`\n * - `/one/three/:four`\n * - `/one/three/:five`\n * - `/one/:two/three/:four`\n * - `/one/:two/three/:five`\n * - `/one/three/:four/:five`\n * - `/one/:two/three/:four/:five`\n */\nfunction explodeOptionalSegments(path) {\n let segments = path.split(\"/\");\n if (segments.length === 0) return [];\n let [first, ...rest] = segments;\n // Optional path segments are denoted by a trailing `?`\n let isOptional = first.endsWith(\"?\");\n // Compute the corresponding required segment: `foo?` -> `foo`\n let required = first.replace(/\\?$/, \"\");\n if (rest.length === 0) {\n // Intepret empty string as omitting an optional segment\n // `[\"one\", \"\", \"three\"]` corresponds to omitting `:two` from `/one/:two?/three` -> `/one/three`\n return isOptional ? [required, \"\"] : [required];\n }\n let restExploded = explodeOptionalSegments(rest.join(\"/\"));\n let result = [];\n // All child paths with the prefix. Do this for all children before the\n // optional version for all children, so we get consistent ordering where the\n // parent optional aspect is preferred as required. Otherwise, we can get\n // child sections interspersed where deeper optional segments are higher than\n // parent optional segments, where for example, /:two would explode _earlier_\n // then /:one. By always including the parent as required _for all children_\n // first, we avoid this issue\n result.push(...restExploded.map(subpath => subpath === \"\" ? required : [required, subpath].join(\"/\")));\n // Then, if this is an optional value, add all child versions without\n if (isOptional) {\n result.push(...restExploded);\n }\n // for absolute paths, ensure `/` instead of empty segment\n return result.map(exploded => path.startsWith(\"/\") && exploded === \"\" ? \"/\" : exploded);\n}\nfunction rankRouteBranches(branches) {\n branches.sort((a, b) => a.score !== b.score ? b.score - a.score // Higher score first\n : compareIndexes(a.routesMeta.map(meta => meta.childrenIndex), b.routesMeta.map(meta => meta.childrenIndex)));\n}\nconst paramRe = /^:[\\w-]+$/;\nconst dynamicSegmentValue = 3;\nconst indexRouteValue = 2;\nconst emptySegmentValue = 1;\nconst staticSegmentValue = 10;\nconst splatPenalty = -2;\nconst isSplat = s => s === \"*\";\nfunction computeScore(path, index) {\n let segments = path.split(\"/\");\n let initialScore = segments.length;\n if (segments.some(isSplat)) {\n initialScore += splatPenalty;\n }\n if (index) {\n initialScore += indexRouteValue;\n }\n return segments.filter(s => !isSplat(s)).reduce((score, segment) => score + (paramRe.test(segment) ? dynamicSegmentValue : segment === \"\" ? emptySegmentValue : staticSegmentValue), initialScore);\n}\nfunction compareIndexes(a, b) {\n let siblings = a.length === b.length && a.slice(0, -1).every((n, i) => n === b[i]);\n return siblings ?\n // If two routes are siblings, we should try to match the earlier sibling\n // first. This allows people to have fine-grained control over the matching\n // behavior by simply putting routes with identical paths in the order they\n // want them tried.\n a[a.length - 1] - b[b.length - 1] :\n // Otherwise, it doesn't really make sense to rank non-siblings by index,\n // so they sort equally.\n 0;\n}\nfunction matchRouteBranch(branch, pathname) {\n let {\n routesMeta\n } = branch;\n let matchedParams = {};\n let matchedPathname = \"/\";\n let matches = [];\n for (let i = 0; i < routesMeta.length; ++i) {\n let meta = routesMeta[i];\n let end = i === routesMeta.length - 1;\n let remainingPathname = matchedPathname === \"/\" ? pathname : pathname.slice(matchedPathname.length) || \"/\";\n let match = matchPath({\n path: meta.relativePath,\n caseSensitive: meta.caseSensitive,\n end\n }, remainingPathname);\n if (!match) return null;\n Object.assign(matchedParams, match.params);\n let route = meta.route;\n matches.push({\n // TODO: Can this as be avoided?\n params: matchedParams,\n pathname: joinPaths([matchedPathname, match.pathname]),\n pathnameBase: normalizePathname(joinPaths([matchedPathname, match.pathnameBase])),\n route\n });\n if (match.pathnameBase !== \"/\") {\n matchedPathname = joinPaths([matchedPathname, match.pathnameBase]);\n }\n }\n return matches;\n}\n/**\n * Returns a path with params interpolated.\n *\n * @see https://reactrouter.com/utils/generate-path\n */\nfunction generatePath(originalPath, params) {\n if (params === void 0) {\n params = {};\n }\n let path = originalPath;\n if (path.endsWith(\"*\") && path !== \"*\" && !path.endsWith(\"/*\")) {\n warning(false, \"Route path \\\"\" + path + \"\\\" will be treated as if it were \" + (\"\\\"\" + path.replace(/\\*$/, \"/*\") + \"\\\" because the `*` character must \") + \"always follow a `/` in the pattern. To get rid of this warning, \" + (\"please change the route path to \\\"\" + path.replace(/\\*$/, \"/*\") + \"\\\".\"));\n path = path.replace(/\\*$/, \"/*\");\n }\n // ensure `/` is added at the beginning if the path is absolute\n const prefix = path.startsWith(\"/\") ? \"/\" : \"\";\n const stringify = p => p == null ? \"\" : typeof p === \"string\" ? p : String(p);\n const segments = path.split(/\\/+/).map((segment, index, array) => {\n const isLastSegment = index === array.length - 1;\n // only apply the splat if it's the last segment\n if (isLastSegment && segment === \"*\") {\n const star = \"*\";\n // Apply the splat\n return stringify(params[star]);\n }\n const keyMatch = segment.match(/^:([\\w-]+)(\\??)$/);\n if (keyMatch) {\n const [, key, optional] = keyMatch;\n let param = params[key];\n invariant(optional === \"?\" || param != null, \"Missing \\\":\" + key + \"\\\" param\");\n return stringify(param);\n }\n // Remove any optional markers from optional static segments\n return segment.replace(/\\?$/g, \"\");\n })\n // Remove empty segments\n .filter(segment => !!segment);\n return prefix + segments.join(\"/\");\n}\n/**\n * Performs pattern matching on a URL pathname and returns information about\n * the match.\n *\n * @see https://reactrouter.com/utils/match-path\n */\nfunction matchPath(pattern, pathname) {\n if (typeof pattern === \"string\") {\n pattern = {\n path: pattern,\n caseSensitive: false,\n end: true\n };\n }\n let [matcher, compiledParams] = compilePath(pattern.path, pattern.caseSensitive, pattern.end);\n let match = pathname.match(matcher);\n if (!match) return null;\n let matchedPathname = match[0];\n let pathnameBase = matchedPathname.replace(/(.)\\/+$/, \"$1\");\n let captureGroups = match.slice(1);\n let params = compiledParams.reduce((memo, _ref, index) => {\n let {\n paramName,\n isOptional\n } = _ref;\n // We need to compute the pathnameBase here using the raw splat value\n // instead of using params[\"*\"] later because it will be decoded then\n if (paramName === \"*\") {\n let splatValue = captureGroups[index] || \"\";\n pathnameBase = matchedPathname.slice(0, matchedPathname.length - splatValue.length).replace(/(.)\\/+$/, \"$1\");\n }\n const value = captureGroups[index];\n if (isOptional && !value) {\n memo[paramName] = undefined;\n } else {\n memo[paramName] = safelyDecodeURIComponent(value || \"\", paramName);\n }\n return memo;\n }, {});\n return {\n params,\n pathname: matchedPathname,\n pathnameBase,\n pattern\n };\n}\nfunction compilePath(path, caseSensitive, end) {\n if (caseSensitive === void 0) {\n caseSensitive = false;\n }\n if (end === void 0) {\n end = true;\n }\n warning(path === \"*\" || !path.endsWith(\"*\") || path.endsWith(\"/*\"), \"Route path \\\"\" + path + \"\\\" will be treated as if it were \" + (\"\\\"\" + path.replace(/\\*$/, \"/*\") + \"\\\" because the `*` character must \") + \"always follow a `/` in the pattern. To get rid of this warning, \" + (\"please change the route path to \\\"\" + path.replace(/\\*$/, \"/*\") + \"\\\".\"));\n let params = [];\n let regexpSource = \"^\" + path.replace(/\\/*\\*?$/, \"\") // Ignore trailing / and /*, we'll handle it below\n .replace(/^\\/*/, \"/\") // Make sure it has a leading /\n .replace(/[\\\\.*+^${}|()[\\]]/g, \"\\\\$&\") // Escape special regex chars\n .replace(/\\/:([\\w-]+)(\\?)?/g, (_, paramName, isOptional) => {\n params.push({\n paramName,\n isOptional: isOptional != null\n });\n return isOptional ? \"/?([^\\\\/]+)?\" : \"/([^\\\\/]+)\";\n });\n if (path.endsWith(\"*\")) {\n params.push({\n paramName: \"*\"\n });\n regexpSource += path === \"*\" || path === \"/*\" ? \"(.*)$\" // Already matched the initial /, just match the rest\n : \"(?:\\\\/(.+)|\\\\/*)$\"; // Don't include the / in params[\"*\"]\n } else if (end) {\n // When matching to the end, ignore trailing slashes\n regexpSource += \"\\\\/*$\";\n } else if (path !== \"\" && path !== \"/\") {\n // If our path is non-empty and contains anything beyond an initial slash,\n // then we have _some_ form of path in our regex, so we should expect to\n // match only if we find the end of this path segment. Look for an optional\n // non-captured trailing slash (to match a portion of the URL) or the end\n // of the path (if we've matched to the end). We used to do this with a\n // word boundary but that gives false positives on routes like\n // /user-preferences since `-` counts as a word boundary.\n regexpSource += \"(?:(?=\\\\/|$))\";\n } else ;\n let matcher = new RegExp(regexpSource, caseSensitive ? undefined : \"i\");\n return [matcher, params];\n}\nfunction safelyDecodeURI(value) {\n try {\n return decodeURI(value);\n } catch (error) {\n warning(false, \"The URL path \\\"\" + value + \"\\\" could not be decoded because it is is a \" + \"malformed URL segment. This is probably due to a bad percent \" + (\"encoding (\" + error + \").\"));\n return value;\n }\n}\nfunction safelyDecodeURIComponent(value, paramName) {\n try {\n return decodeURIComponent(value);\n } catch (error) {\n warning(false, \"The value for the URL param \\\"\" + paramName + \"\\\" will not be decoded because\" + (\" the string \\\"\" + value + \"\\\" is a malformed URL segment. This is probably\") + (\" due to a bad percent encoding (\" + error + \").\"));\n return value;\n }\n}\n/**\n * @private\n */\nfunction stripBasename(pathname, basename) {\n if (basename === \"/\") return pathname;\n if (!pathname.toLowerCase().startsWith(basename.toLowerCase())) {\n return null;\n }\n // We want to leave trailing slash behavior in the user's control, so if they\n // specify a basename with a trailing slash, we should support it\n let startIndex = basename.endsWith(\"/\") ? basename.length - 1 : basename.length;\n let nextChar = pathname.charAt(startIndex);\n if (nextChar && nextChar !== \"/\") {\n // pathname does not start with basename/\n return null;\n }\n return pathname.slice(startIndex) || \"/\";\n}\n/**\n * Returns a resolved path object relative to the given pathname.\n *\n * @see https://reactrouter.com/utils/resolve-path\n */\nfunction resolvePath(to, fromPathname) {\n if (fromPathname === void 0) {\n fromPathname = \"/\";\n }\n let {\n pathname: toPathname,\n search = \"\",\n hash = \"\"\n } = typeof to === \"string\" ? parsePath(to) : to;\n let pathname = toPathname ? toPathname.startsWith(\"/\") ? toPathname : resolvePathname(toPathname, fromPathname) : fromPathname;\n return {\n pathname,\n search: normalizeSearch(search),\n hash: normalizeHash(hash)\n };\n}\nfunction resolvePathname(relativePath, fromPathname) {\n let segments = fromPathname.replace(/\\/+$/, \"\").split(\"/\");\n let relativeSegments = relativePath.split(\"/\");\n relativeSegments.forEach(segment => {\n if (segment === \"..\") {\n // Keep the root \"\" segment so the pathname starts at /\n if (segments.length > 1) segments.pop();\n } else if (segment !== \".\") {\n segments.push(segment);\n }\n });\n return segments.length > 1 ? segments.join(\"/\") : \"/\";\n}\nfunction getInvalidPathError(char, field, dest, path) {\n return \"Cannot include a '\" + char + \"' character in a manually specified \" + (\"`to.\" + field + \"` field [\" + JSON.stringify(path) + \"]. Please separate it out to the \") + (\"`to.\" + dest + \"` field. Alternatively you may provide the full path as \") + \"a string in and the router will parse it for you.\";\n}\n/**\n * @private\n *\n * When processing relative navigation we want to ignore ancestor routes that\n * do not contribute to the path, such that index/pathless layout routes don't\n * interfere.\n *\n * For example, when moving a route element into an index route and/or a\n * pathless layout route, relative link behavior contained within should stay\n * the same. Both of the following examples should link back to the root:\n *\n * \n * \n * \n *\n * \n * \n * }> // <-- Does not contribute\n * // <-- Does not contribute\n * \n * \n */\nfunction getPathContributingMatches(matches) {\n return matches.filter((match, index) => index === 0 || match.route.path && match.route.path.length > 0);\n}\n// Return the array of pathnames for the current route matches - used to\n// generate the routePathnames input for resolveTo()\nfunction getResolveToMatches(matches, v7_relativeSplatPath) {\n let pathMatches = getPathContributingMatches(matches);\n // When v7_relativeSplatPath is enabled, use the full pathname for the leaf\n // match so we include splat values for \".\" links. See:\n // https://github.com/remix-run/react-router/issues/11052#issuecomment-1836589329\n if (v7_relativeSplatPath) {\n return pathMatches.map((match, idx) => idx === matches.length - 1 ? match.pathname : match.pathnameBase);\n }\n return pathMatches.map(match => match.pathnameBase);\n}\n/**\n * @private\n */\nfunction resolveTo(toArg, routePathnames, locationPathname, isPathRelative) {\n if (isPathRelative === void 0) {\n isPathRelative = false;\n }\n let to;\n if (typeof toArg === \"string\") {\n to = parsePath(toArg);\n } else {\n to = _extends({}, toArg);\n invariant(!to.pathname || !to.pathname.includes(\"?\"), getInvalidPathError(\"?\", \"pathname\", \"search\", to));\n invariant(!to.pathname || !to.pathname.includes(\"#\"), getInvalidPathError(\"#\", \"pathname\", \"hash\", to));\n invariant(!to.search || !to.search.includes(\"#\"), getInvalidPathError(\"#\", \"search\", \"hash\", to));\n }\n let isEmptyPath = toArg === \"\" || to.pathname === \"\";\n let toPathname = isEmptyPath ? \"/\" : to.pathname;\n let from;\n // Routing is relative to the current pathname if explicitly requested.\n //\n // If a pathname is explicitly provided in `to`, it should be relative to the\n // route context. This is explained in `Note on `` values` in our\n // migration guide from v5 as a means of disambiguation between `to` values\n // that begin with `/` and those that do not. However, this is problematic for\n // `to` values that do not provide a pathname. `to` can simply be a search or\n // hash string, in which case we should assume that the navigation is relative\n // to the current location's pathname and *not* the route pathname.\n if (toPathname == null) {\n from = locationPathname;\n } else {\n let routePathnameIndex = routePathnames.length - 1;\n // With relative=\"route\" (the default), each leading .. segment means\n // \"go up one route\" instead of \"go up one URL segment\". This is a key\n // difference from how works and a major reason we call this a\n // \"to\" value instead of a \"href\".\n if (!isPathRelative && toPathname.startsWith(\"..\")) {\n let toSegments = toPathname.split(\"/\");\n while (toSegments[0] === \"..\") {\n toSegments.shift();\n routePathnameIndex -= 1;\n }\n to.pathname = toSegments.join(\"/\");\n }\n from = routePathnameIndex >= 0 ? routePathnames[routePathnameIndex] : \"/\";\n }\n let path = resolvePath(to, from);\n // Ensure the pathname has a trailing slash if the original \"to\" had one\n let hasExplicitTrailingSlash = toPathname && toPathname !== \"/\" && toPathname.endsWith(\"/\");\n // Or if this was a link to the current path which has a trailing slash\n let hasCurrentTrailingSlash = (isEmptyPath || toPathname === \".\") && locationPathname.endsWith(\"/\");\n if (!path.pathname.endsWith(\"/\") && (hasExplicitTrailingSlash || hasCurrentTrailingSlash)) {\n path.pathname += \"/\";\n }\n return path;\n}\n/**\n * @private\n */\nfunction getToPathname(to) {\n // Empty strings should be treated the same as / paths\n return to === \"\" || to.pathname === \"\" ? \"/\" : typeof to === \"string\" ? parsePath(to).pathname : to.pathname;\n}\n/**\n * @private\n */\nconst joinPaths = paths => paths.join(\"/\").replace(/\\/\\/+/g, \"/\");\n/**\n * @private\n */\nconst normalizePathname = pathname => pathname.replace(/\\/+$/, \"\").replace(/^\\/*/, \"/\");\n/**\n * @private\n */\nconst normalizeSearch = search => !search || search === \"?\" ? \"\" : search.startsWith(\"?\") ? search : \"?\" + search;\n/**\n * @private\n */\nconst normalizeHash = hash => !hash || hash === \"#\" ? \"\" : hash.startsWith(\"#\") ? hash : \"#\" + hash;\n/**\n * This is a shortcut for creating `application/json` responses. Converts `data`\n * to JSON and sets the `Content-Type` header.\n */\nconst json = function json(data, init) {\n if (init === void 0) {\n init = {};\n }\n let responseInit = typeof init === \"number\" ? {\n status: init\n } : init;\n let headers = new Headers(responseInit.headers);\n if (!headers.has(\"Content-Type\")) {\n headers.set(\"Content-Type\", \"application/json; charset=utf-8\");\n }\n return new Response(JSON.stringify(data), _extends({}, responseInit, {\n headers\n }));\n};\nclass AbortedDeferredError extends Error {}\nclass DeferredData {\n constructor(data, responseInit) {\n this.pendingKeysSet = new Set();\n this.subscribers = new Set();\n this.deferredKeys = [];\n invariant(data && typeof data === \"object\" && !Array.isArray(data), \"defer() only accepts plain objects\");\n // Set up an AbortController + Promise we can race against to exit early\n // cancellation\n let reject;\n this.abortPromise = new Promise((_, r) => reject = r);\n this.controller = new AbortController();\n let onAbort = () => reject(new AbortedDeferredError(\"Deferred data aborted\"));\n this.unlistenAbortSignal = () => this.controller.signal.removeEventListener(\"abort\", onAbort);\n this.controller.signal.addEventListener(\"abort\", onAbort);\n this.data = Object.entries(data).reduce((acc, _ref2) => {\n let [key, value] = _ref2;\n return Object.assign(acc, {\n [key]: this.trackPromise(key, value)\n });\n }, {});\n if (this.done) {\n // All incoming values were resolved\n this.unlistenAbortSignal();\n }\n this.init = responseInit;\n }\n trackPromise(key, value) {\n if (!(value instanceof Promise)) {\n return value;\n }\n this.deferredKeys.push(key);\n this.pendingKeysSet.add(key);\n // We store a little wrapper promise that will be extended with\n // _data/_error props upon resolve/reject\n let promise = Promise.race([value, this.abortPromise]).then(data => this.onSettle(promise, key, undefined, data), error => this.onSettle(promise, key, error));\n // Register rejection listeners to avoid uncaught promise rejections on\n // errors or aborted deferred values\n promise.catch(() => {});\n Object.defineProperty(promise, \"_tracked\", {\n get: () => true\n });\n return promise;\n }\n onSettle(promise, key, error, data) {\n if (this.controller.signal.aborted && error instanceof AbortedDeferredError) {\n this.unlistenAbortSignal();\n Object.defineProperty(promise, \"_error\", {\n get: () => error\n });\n return Promise.reject(error);\n }\n this.pendingKeysSet.delete(key);\n if (this.done) {\n // Nothing left to abort!\n this.unlistenAbortSignal();\n }\n // If the promise was resolved/rejected with undefined, we'll throw an error as you\n // should always resolve with a value or null\n if (error === undefined && data === undefined) {\n let undefinedError = new Error(\"Deferred data for key \\\"\" + key + \"\\\" resolved/rejected with `undefined`, \" + \"you must resolve/reject with a value or `null`.\");\n Object.defineProperty(promise, \"_error\", {\n get: () => undefinedError\n });\n this.emit(false, key);\n return Promise.reject(undefinedError);\n }\n if (data === undefined) {\n Object.defineProperty(promise, \"_error\", {\n get: () => error\n });\n this.emit(false, key);\n return Promise.reject(error);\n }\n Object.defineProperty(promise, \"_data\", {\n get: () => data\n });\n this.emit(false, key);\n return data;\n }\n emit(aborted, settledKey) {\n this.subscribers.forEach(subscriber => subscriber(aborted, settledKey));\n }\n subscribe(fn) {\n this.subscribers.add(fn);\n return () => this.subscribers.delete(fn);\n }\n cancel() {\n this.controller.abort();\n this.pendingKeysSet.forEach((v, k) => this.pendingKeysSet.delete(k));\n this.emit(true);\n }\n async resolveData(signal) {\n let aborted = false;\n if (!this.done) {\n let onAbort = () => this.cancel();\n signal.addEventListener(\"abort\", onAbort);\n aborted = await new Promise(resolve => {\n this.subscribe(aborted => {\n signal.removeEventListener(\"abort\", onAbort);\n if (aborted || this.done) {\n resolve(aborted);\n }\n });\n });\n }\n return aborted;\n }\n get done() {\n return this.pendingKeysSet.size === 0;\n }\n get unwrappedData() {\n invariant(this.data !== null && this.done, \"Can only unwrap data on initialized and settled deferreds\");\n return Object.entries(this.data).reduce((acc, _ref3) => {\n let [key, value] = _ref3;\n return Object.assign(acc, {\n [key]: unwrapTrackedPromise(value)\n });\n }, {});\n }\n get pendingKeys() {\n return Array.from(this.pendingKeysSet);\n }\n}\nfunction isTrackedPromise(value) {\n return value instanceof Promise && value._tracked === true;\n}\nfunction unwrapTrackedPromise(value) {\n if (!isTrackedPromise(value)) {\n return value;\n }\n if (value._error) {\n throw value._error;\n }\n return value._data;\n}\nconst defer = function defer(data, init) {\n if (init === void 0) {\n init = {};\n }\n let responseInit = typeof init === \"number\" ? {\n status: init\n } : init;\n return new DeferredData(data, responseInit);\n};\n/**\n * A redirect response. Sets the status code and the `Location` header.\n * Defaults to \"302 Found\".\n */\nconst redirect = function redirect(url, init) {\n if (init === void 0) {\n init = 302;\n }\n let responseInit = init;\n if (typeof responseInit === \"number\") {\n responseInit = {\n status: responseInit\n };\n } else if (typeof responseInit.status === \"undefined\") {\n responseInit.status = 302;\n }\n let headers = new Headers(responseInit.headers);\n headers.set(\"Location\", url);\n return new Response(null, _extends({}, responseInit, {\n headers\n }));\n};\n/**\n * A redirect response that will force a document reload to the new location.\n * Sets the status code and the `Location` header.\n * Defaults to \"302 Found\".\n */\nconst redirectDocument = (url, init) => {\n let response = redirect(url, init);\n response.headers.set(\"X-Remix-Reload-Document\", \"true\");\n return response;\n};\n/**\n * @private\n * Utility class we use to hold auto-unwrapped 4xx/5xx Response bodies\n *\n * We don't export the class for public use since it's an implementation\n * detail, but we export the interface above so folks can build their own\n * abstractions around instances via isRouteErrorResponse()\n */\nclass ErrorResponseImpl {\n constructor(status, statusText, data, internal) {\n if (internal === void 0) {\n internal = false;\n }\n this.status = status;\n this.statusText = statusText || \"\";\n this.internal = internal;\n if (data instanceof Error) {\n this.data = data.toString();\n this.error = data;\n } else {\n this.data = data;\n }\n }\n}\n/**\n * Check if the given error is an ErrorResponse generated from a 4xx/5xx\n * Response thrown from an action/loader\n */\nfunction isRouteErrorResponse(error) {\n return error != null && typeof error.status === \"number\" && typeof error.statusText === \"string\" && typeof error.internal === \"boolean\" && \"data\" in error;\n}\n\nconst validMutationMethodsArr = [\"post\", \"put\", \"patch\", \"delete\"];\nconst validMutationMethods = new Set(validMutationMethodsArr);\nconst validRequestMethodsArr = [\"get\", ...validMutationMethodsArr];\nconst validRequestMethods = new Set(validRequestMethodsArr);\nconst redirectStatusCodes = new Set([301, 302, 303, 307, 308]);\nconst redirectPreserveMethodStatusCodes = new Set([307, 308]);\nconst IDLE_NAVIGATION = {\n state: \"idle\",\n location: undefined,\n formMethod: undefined,\n formAction: undefined,\n formEncType: undefined,\n formData: undefined,\n json: undefined,\n text: undefined\n};\nconst IDLE_FETCHER = {\n state: \"idle\",\n data: undefined,\n formMethod: undefined,\n formAction: undefined,\n formEncType: undefined,\n formData: undefined,\n json: undefined,\n text: undefined\n};\nconst IDLE_BLOCKER = {\n state: \"unblocked\",\n proceed: undefined,\n reset: undefined,\n location: undefined\n};\nconst ABSOLUTE_URL_REGEX = /^(?:[a-z][a-z0-9+.-]*:|\\/\\/)/i;\nconst defaultMapRouteProperties = route => ({\n hasErrorBoundary: Boolean(route.hasErrorBoundary)\n});\nconst TRANSITIONS_STORAGE_KEY = \"remix-router-transitions\";\n//#endregion\n////////////////////////////////////////////////////////////////////////////////\n//#region createRouter\n////////////////////////////////////////////////////////////////////////////////\n/**\n * Create a router and listen to history POP navigations\n */\nfunction createRouter(init) {\n const routerWindow = init.window ? init.window : typeof window !== \"undefined\" ? window : undefined;\n const isBrowser = typeof routerWindow !== \"undefined\" && typeof routerWindow.document !== \"undefined\" && typeof routerWindow.document.createElement !== \"undefined\";\n const isServer = !isBrowser;\n invariant(init.routes.length > 0, \"You must provide a non-empty routes array to createRouter\");\n let mapRouteProperties;\n if (init.mapRouteProperties) {\n mapRouteProperties = init.mapRouteProperties;\n } else if (init.detectErrorBoundary) {\n // If they are still using the deprecated version, wrap it with the new API\n let detectErrorBoundary = init.detectErrorBoundary;\n mapRouteProperties = route => ({\n hasErrorBoundary: detectErrorBoundary(route)\n });\n } else {\n mapRouteProperties = defaultMapRouteProperties;\n }\n // Routes keyed by ID\n let manifest = {};\n // Routes in tree format for matching\n let dataRoutes = convertRoutesToDataRoutes(init.routes, mapRouteProperties, undefined, manifest);\n let inFlightDataRoutes;\n let basename = init.basename || \"/\";\n // Config driven behavior flags\n let future = _extends({\n v7_fetcherPersist: false,\n v7_normalizeFormMethod: false,\n v7_partialHydration: false,\n v7_prependBasename: false,\n v7_relativeSplatPath: false\n }, init.future);\n // Cleanup function for history\n let unlistenHistory = null;\n // Externally-provided functions to call on all state changes\n let subscribers = new Set();\n // Externally-provided object to hold scroll restoration locations during routing\n let savedScrollPositions = null;\n // Externally-provided function to get scroll restoration keys\n let getScrollRestorationKey = null;\n // Externally-provided function to get current scroll position\n let getScrollPosition = null;\n // One-time flag to control the initial hydration scroll restoration. Because\n // we don't get the saved positions from until _after_\n // the initial render, we need to manually trigger a separate updateState to\n // send along the restoreScrollPosition\n // Set to true if we have `hydrationData` since we assume we were SSR'd and that\n // SSR did the initial scroll restoration.\n let initialScrollRestored = init.hydrationData != null;\n let initialMatches = matchRoutes(dataRoutes, init.history.location, basename);\n let initialErrors = null;\n if (initialMatches == null) {\n // If we do not match a user-provided-route, fall back to the root\n // to allow the error boundary to take over\n let error = getInternalRouterError(404, {\n pathname: init.history.location.pathname\n });\n let {\n matches,\n route\n } = getShortCircuitMatches(dataRoutes);\n initialMatches = matches;\n initialErrors = {\n [route.id]: error\n };\n }\n let initialized;\n let hasLazyRoutes = initialMatches.some(m => m.route.lazy);\n let hasLoaders = initialMatches.some(m => m.route.loader);\n if (hasLazyRoutes) {\n // All initialMatches need to be loaded before we're ready. If we have lazy\n // functions around still then we'll need to run them in initialize()\n initialized = false;\n } else if (!hasLoaders) {\n // If we've got no loaders to run, then we're good to go\n initialized = true;\n } else if (future.v7_partialHydration) {\n // If partial hydration is enabled, we're initialized so long as we were\n // provided with hydrationData for every route with a loader, and no loaders\n // were marked for explicit hydration\n let loaderData = init.hydrationData ? init.hydrationData.loaderData : null;\n let errors = init.hydrationData ? init.hydrationData.errors : null;\n initialized = initialMatches.every(m => m.route.loader && m.route.loader.hydrate !== true && (loaderData && loaderData[m.route.id] !== undefined || errors && errors[m.route.id] !== undefined));\n } else {\n // Without partial hydration - we're initialized if we were provided any\n // hydrationData - which is expected to be complete\n initialized = init.hydrationData != null;\n }\n let router;\n let state = {\n historyAction: init.history.action,\n location: init.history.location,\n matches: initialMatches,\n initialized,\n navigation: IDLE_NAVIGATION,\n // Don't restore on initial updateState() if we were SSR'd\n restoreScrollPosition: init.hydrationData != null ? false : null,\n preventScrollReset: false,\n revalidation: \"idle\",\n loaderData: init.hydrationData && init.hydrationData.loaderData || {},\n actionData: init.hydrationData && init.hydrationData.actionData || null,\n errors: init.hydrationData && init.hydrationData.errors || initialErrors,\n fetchers: new Map(),\n blockers: new Map()\n };\n // -- Stateful internal variables to manage navigations --\n // Current navigation in progress (to be committed in completeNavigation)\n let pendingAction = Action.Pop;\n // Should the current navigation prevent the scroll reset if scroll cannot\n // be restored?\n let pendingPreventScrollReset = false;\n // AbortController for the active navigation\n let pendingNavigationController;\n // Should the current navigation enable document.startViewTransition?\n let pendingViewTransitionEnabled = false;\n // Store applied view transitions so we can apply them on POP\n let appliedViewTransitions = new Map();\n // Cleanup function for persisting applied transitions to sessionStorage\n let removePageHideEventListener = null;\n // We use this to avoid touching history in completeNavigation if a\n // revalidation is entirely uninterrupted\n let isUninterruptedRevalidation = false;\n // Use this internal flag to force revalidation of all loaders:\n // - submissions (completed or interrupted)\n // - useRevalidator()\n // - X-Remix-Revalidate (from redirect)\n let isRevalidationRequired = false;\n // Use this internal array to capture routes that require revalidation due\n // to a cancelled deferred on action submission\n let cancelledDeferredRoutes = [];\n // Use this internal array to capture fetcher loads that were cancelled by an\n // action navigation and require revalidation\n let cancelledFetcherLoads = [];\n // AbortControllers for any in-flight fetchers\n let fetchControllers = new Map();\n // Track loads based on the order in which they started\n let incrementingLoadId = 0;\n // Track the outstanding pending navigation data load to be compared against\n // the globally incrementing load when a fetcher load lands after a completed\n // navigation\n let pendingNavigationLoadId = -1;\n // Fetchers that triggered data reloads as a result of their actions\n let fetchReloadIds = new Map();\n // Fetchers that triggered redirect navigations\n let fetchRedirectIds = new Set();\n // Most recent href/match for fetcher.load calls for fetchers\n let fetchLoadMatches = new Map();\n // Ref-count mounted fetchers so we know when it's ok to clean them up\n let activeFetchers = new Map();\n // Fetchers that have requested a delete when using v7_fetcherPersist,\n // they'll be officially removed after they return to idle\n let deletedFetchers = new Set();\n // Store DeferredData instances for active route matches. When a\n // route loader returns defer() we stick one in here. Then, when a nested\n // promise resolves we update loaderData. If a new navigation starts we\n // cancel active deferreds for eliminated routes.\n let activeDeferreds = new Map();\n // Store blocker functions in a separate Map outside of router state since\n // we don't need to update UI state if they change\n let blockerFunctions = new Map();\n // Flag to ignore the next history update, so we can revert the URL change on\n // a POP navigation that was blocked by the user without touching router state\n let ignoreNextHistoryUpdate = false;\n // Initialize the router, all side effects should be kicked off from here.\n // Implemented as a Fluent API for ease of:\n // let router = createRouter(init).initialize();\n function initialize() {\n // If history informs us of a POP navigation, start the navigation but do not update\n // state. We'll update our own state once the navigation completes\n unlistenHistory = init.history.listen(_ref => {\n let {\n action: historyAction,\n location,\n delta\n } = _ref;\n // Ignore this event if it was just us resetting the URL from a\n // blocked POP navigation\n if (ignoreNextHistoryUpdate) {\n ignoreNextHistoryUpdate = false;\n return;\n }\n warning(blockerFunctions.size === 0 || delta != null, \"You are trying to use a blocker on a POP navigation to a location \" + \"that was not created by @remix-run/router. This will fail silently in \" + \"production. This can happen if you are navigating outside the router \" + \"via `window.history.pushState`/`window.location.hash` instead of using \" + \"router navigation APIs. This can also happen if you are using \" + \"createHashRouter and the user manually changes the URL.\");\n let blockerKey = shouldBlockNavigation({\n currentLocation: state.location,\n nextLocation: location,\n historyAction\n });\n if (blockerKey && delta != null) {\n // Restore the URL to match the current UI, but don't update router state\n ignoreNextHistoryUpdate = true;\n init.history.go(delta * -1);\n // Put the blocker into a blocked state\n updateBlocker(blockerKey, {\n state: \"blocked\",\n location,\n proceed() {\n updateBlocker(blockerKey, {\n state: \"proceeding\",\n proceed: undefined,\n reset: undefined,\n location\n });\n // Re-do the same POP navigation we just blocked\n init.history.go(delta);\n },\n reset() {\n let blockers = new Map(state.blockers);\n blockers.set(blockerKey, IDLE_BLOCKER);\n updateState({\n blockers\n });\n }\n });\n return;\n }\n return startNavigation(historyAction, location);\n });\n if (isBrowser) {\n // FIXME: This feels gross. How can we cleanup the lines between\n // scrollRestoration/appliedTransitions persistance?\n restoreAppliedTransitions(routerWindow, appliedViewTransitions);\n let _saveAppliedTransitions = () => persistAppliedTransitions(routerWindow, appliedViewTransitions);\n routerWindow.addEventListener(\"pagehide\", _saveAppliedTransitions);\n removePageHideEventListener = () => routerWindow.removeEventListener(\"pagehide\", _saveAppliedTransitions);\n }\n // Kick off initial data load if needed. Use Pop to avoid modifying history\n // Note we don't do any handling of lazy here. For SPA's it'll get handled\n // in the normal navigation flow. For SSR it's expected that lazy modules are\n // resolved prior to router creation since we can't go into a fallbackElement\n // UI for SSR'd apps\n if (!state.initialized) {\n startNavigation(Action.Pop, state.location, {\n initialHydration: true\n });\n }\n return router;\n }\n // Clean up a router and it's side effects\n function dispose() {\n if (unlistenHistory) {\n unlistenHistory();\n }\n if (removePageHideEventListener) {\n removePageHideEventListener();\n }\n subscribers.clear();\n pendingNavigationController && pendingNavigationController.abort();\n state.fetchers.forEach((_, key) => deleteFetcher(key));\n state.blockers.forEach((_, key) => deleteBlocker(key));\n }\n // Subscribe to state updates for the router\n function subscribe(fn) {\n subscribers.add(fn);\n return () => subscribers.delete(fn);\n }\n // Update our state and notify the calling context of the change\n function updateState(newState, opts) {\n if (opts === void 0) {\n opts = {};\n }\n state = _extends({}, state, newState);\n // Prep fetcher cleanup so we can tell the UI which fetcher data entries\n // can be removed\n let completedFetchers = [];\n let deletedFetchersKeys = [];\n if (future.v7_fetcherPersist) {\n state.fetchers.forEach((fetcher, key) => {\n if (fetcher.state === \"idle\") {\n if (deletedFetchers.has(key)) {\n // Unmounted from the UI and can be totally removed\n deletedFetchersKeys.push(key);\n } else {\n // Returned to idle but still mounted in the UI, so semi-remains for\n // revalidations and such\n completedFetchers.push(key);\n }\n }\n });\n }\n // Iterate over a local copy so that if flushSync is used and we end up\n // removing and adding a new subscriber due to the useCallback dependencies,\n // we don't get ourselves into a loop calling the new subscriber immediately\n [...subscribers].forEach(subscriber => subscriber(state, {\n deletedFetchers: deletedFetchersKeys,\n unstable_viewTransitionOpts: opts.viewTransitionOpts,\n unstable_flushSync: opts.flushSync === true\n }));\n // Remove idle fetchers from state since we only care about in-flight fetchers.\n if (future.v7_fetcherPersist) {\n completedFetchers.forEach(key => state.fetchers.delete(key));\n deletedFetchersKeys.forEach(key => deleteFetcher(key));\n }\n }\n // Complete a navigation returning the state.navigation back to the IDLE_NAVIGATION\n // and setting state.[historyAction/location/matches] to the new route.\n // - Location is a required param\n // - Navigation will always be set to IDLE_NAVIGATION\n // - Can pass any other state in newState\n function completeNavigation(location, newState, _temp) {\n var _location$state, _location$state2;\n let {\n flushSync\n } = _temp === void 0 ? {} : _temp;\n // Deduce if we're in a loading/actionReload state:\n // - We have committed actionData in the store\n // - The current navigation was a mutation submission\n // - We're past the submitting state and into the loading state\n // - The location being loaded is not the result of a redirect\n let isActionReload = state.actionData != null && state.navigation.formMethod != null && isMutationMethod(state.navigation.formMethod) && state.navigation.state === \"loading\" && ((_location$state = location.state) == null ? void 0 : _location$state._isRedirect) !== true;\n let actionData;\n if (newState.actionData) {\n if (Object.keys(newState.actionData).length > 0) {\n actionData = newState.actionData;\n } else {\n // Empty actionData -> clear prior actionData due to an action error\n actionData = null;\n }\n } else if (isActionReload) {\n // Keep the current data if we're wrapping up the action reload\n actionData = state.actionData;\n } else {\n // Clear actionData on any other completed navigations\n actionData = null;\n }\n // Always preserve any existing loaderData from re-used routes\n let loaderData = newState.loaderData ? mergeLoaderData(state.loaderData, newState.loaderData, newState.matches || [], newState.errors) : state.loaderData;\n // On a successful navigation we can assume we got through all blockers\n // so we can start fresh\n let blockers = state.blockers;\n if (blockers.size > 0) {\n blockers = new Map(blockers);\n blockers.forEach((_, k) => blockers.set(k, IDLE_BLOCKER));\n }\n // Always respect the user flag. Otherwise don't reset on mutation\n // submission navigations unless they redirect\n let preventScrollReset = pendingPreventScrollReset === true || state.navigation.formMethod != null && isMutationMethod(state.navigation.formMethod) && ((_location$state2 = location.state) == null ? void 0 : _location$state2._isRedirect) !== true;\n if (inFlightDataRoutes) {\n dataRoutes = inFlightDataRoutes;\n inFlightDataRoutes = undefined;\n }\n if (isUninterruptedRevalidation) ; else if (pendingAction === Action.Pop) ; else if (pendingAction === Action.Push) {\n init.history.push(location, location.state);\n } else if (pendingAction === Action.Replace) {\n init.history.replace(location, location.state);\n }\n let viewTransitionOpts;\n // On POP, enable transitions if they were enabled on the original navigation\n if (pendingAction === Action.Pop) {\n // Forward takes precedence so they behave like the original navigation\n let priorPaths = appliedViewTransitions.get(state.location.pathname);\n if (priorPaths && priorPaths.has(location.pathname)) {\n viewTransitionOpts = {\n currentLocation: state.location,\n nextLocation: location\n };\n } else if (appliedViewTransitions.has(location.pathname)) {\n // If we don't have a previous forward nav, assume we're popping back to\n // the new location and enable if that location previously enabled\n viewTransitionOpts = {\n currentLocation: location,\n nextLocation: state.location\n };\n }\n } else if (pendingViewTransitionEnabled) {\n // Store the applied transition on PUSH/REPLACE\n let toPaths = appliedViewTransitions.get(state.location.pathname);\n if (toPaths) {\n toPaths.add(location.pathname);\n } else {\n toPaths = new Set([location.pathname]);\n appliedViewTransitions.set(state.location.pathname, toPaths);\n }\n viewTransitionOpts = {\n currentLocation: state.location,\n nextLocation: location\n };\n }\n updateState(_extends({}, newState, {\n actionData,\n loaderData,\n historyAction: pendingAction,\n location,\n initialized: true,\n navigation: IDLE_NAVIGATION,\n revalidation: \"idle\",\n restoreScrollPosition: getSavedScrollPosition(location, newState.matches || state.matches),\n preventScrollReset,\n blockers\n }), {\n viewTransitionOpts,\n flushSync: flushSync === true\n });\n // Reset stateful navigation vars\n pendingAction = Action.Pop;\n pendingPreventScrollReset = false;\n pendingViewTransitionEnabled = false;\n isUninterruptedRevalidation = false;\n isRevalidationRequired = false;\n cancelledDeferredRoutes = [];\n cancelledFetcherLoads = [];\n }\n // Trigger a navigation event, which can either be a numerical POP or a PUSH\n // replace with an optional submission\n async function navigate(to, opts) {\n if (typeof to === \"number\") {\n init.history.go(to);\n return;\n }\n let normalizedPath = normalizeTo(state.location, state.matches, basename, future.v7_prependBasename, to, future.v7_relativeSplatPath, opts == null ? void 0 : opts.fromRouteId, opts == null ? void 0 : opts.relative);\n let {\n path,\n submission,\n error\n } = normalizeNavigateOptions(future.v7_normalizeFormMethod, false, normalizedPath, opts);\n let currentLocation = state.location;\n let nextLocation = createLocation(state.location, path, opts && opts.state);\n // When using navigate as a PUSH/REPLACE we aren't reading an already-encoded\n // URL from window.location, so we need to encode it here so the behavior\n // remains the same as POP and non-data-router usages. new URL() does all\n // the same encoding we'd get from a history.pushState/window.location read\n // without having to touch history\n nextLocation = _extends({}, nextLocation, init.history.encodeLocation(nextLocation));\n let userReplace = opts && opts.replace != null ? opts.replace : undefined;\n let historyAction = Action.Push;\n if (userReplace === true) {\n historyAction = Action.Replace;\n } else if (userReplace === false) ; else if (submission != null && isMutationMethod(submission.formMethod) && submission.formAction === state.location.pathname + state.location.search) {\n // By default on submissions to the current location we REPLACE so that\n // users don't have to double-click the back button to get to the prior\n // location. If the user redirects to a different location from the\n // action/loader this will be ignored and the redirect will be a PUSH\n historyAction = Action.Replace;\n }\n let preventScrollReset = opts && \"preventScrollReset\" in opts ? opts.preventScrollReset === true : undefined;\n let flushSync = (opts && opts.unstable_flushSync) === true;\n let blockerKey = shouldBlockNavigation({\n currentLocation,\n nextLocation,\n historyAction\n });\n if (blockerKey) {\n // Put the blocker into a blocked state\n updateBlocker(blockerKey, {\n state: \"blocked\",\n location: nextLocation,\n proceed() {\n updateBlocker(blockerKey, {\n state: \"proceeding\",\n proceed: undefined,\n reset: undefined,\n location: nextLocation\n });\n // Send the same navigation through\n navigate(to, opts);\n },\n reset() {\n let blockers = new Map(state.blockers);\n blockers.set(blockerKey, IDLE_BLOCKER);\n updateState({\n blockers\n });\n }\n });\n return;\n }\n return await startNavigation(historyAction, nextLocation, {\n submission,\n // Send through the formData serialization error if we have one so we can\n // render at the right error boundary after we match routes\n pendingError: error,\n preventScrollReset,\n replace: opts && opts.replace,\n enableViewTransition: opts && opts.unstable_viewTransition,\n flushSync\n });\n }\n // Revalidate all current loaders. If a navigation is in progress or if this\n // is interrupted by a navigation, allow this to \"succeed\" by calling all\n // loaders during the next loader round\n function revalidate() {\n interruptActiveLoads();\n updateState({\n revalidation: \"loading\"\n });\n // If we're currently submitting an action, we don't need to start a new\n // navigation, we'll just let the follow up loader execution call all loaders\n if (state.navigation.state === \"submitting\") {\n return;\n }\n // If we're currently in an idle state, start a new navigation for the current\n // action/location and mark it as uninterrupted, which will skip the history\n // update in completeNavigation\n if (state.navigation.state === \"idle\") {\n startNavigation(state.historyAction, state.location, {\n startUninterruptedRevalidation: true\n });\n return;\n }\n // Otherwise, if we're currently in a loading state, just start a new\n // navigation to the navigation.location but do not trigger an uninterrupted\n // revalidation so that history correctly updates once the navigation completes\n startNavigation(pendingAction || state.historyAction, state.navigation.location, {\n overrideNavigation: state.navigation\n });\n }\n // Start a navigation to the given action/location. Can optionally provide a\n // overrideNavigation which will override the normalLoad in the case of a redirect\n // navigation\n async function startNavigation(historyAction, location, opts) {\n // Abort any in-progress navigations and start a new one. Unset any ongoing\n // uninterrupted revalidations unless told otherwise, since we want this\n // new navigation to update history normally\n pendingNavigationController && pendingNavigationController.abort();\n pendingNavigationController = null;\n pendingAction = historyAction;\n isUninterruptedRevalidation = (opts && opts.startUninterruptedRevalidation) === true;\n // Save the current scroll position every time we start a new navigation,\n // and track whether we should reset scroll on completion\n saveScrollPosition(state.location, state.matches);\n pendingPreventScrollReset = (opts && opts.preventScrollReset) === true;\n pendingViewTransitionEnabled = (opts && opts.enableViewTransition) === true;\n let routesToUse = inFlightDataRoutes || dataRoutes;\n let loadingNavigation = opts && opts.overrideNavigation;\n let matches = matchRoutes(routesToUse, location, basename);\n let flushSync = (opts && opts.flushSync) === true;\n // Short circuit with a 404 on the root error boundary if we match nothing\n if (!matches) {\n let error = getInternalRouterError(404, {\n pathname: location.pathname\n });\n let {\n matches: notFoundMatches,\n route\n } = getShortCircuitMatches(routesToUse);\n // Cancel all pending deferred on 404s since we don't keep any routes\n cancelActiveDeferreds();\n completeNavigation(location, {\n matches: notFoundMatches,\n loaderData: {},\n errors: {\n [route.id]: error\n }\n }, {\n flushSync\n });\n return;\n }\n // Short circuit if it's only a hash change and not a revalidation or\n // mutation submission.\n //\n // Ignore on initial page loads because since the initial load will always\n // be \"same hash\". For example, on /page#hash and submit a