wevu 6.25.1 → 7.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/dev/index.mjs +1 -1
- package/dist/dev/internal-runtime.mjs +1 -1
- package/dist/dev/package.mjs +1 -1
- package/dist/dev/router/createRouter.mjs +80 -12
- package/dist/dev/router/createRouter.mjs.map +1 -1
- package/dist/dev/router/initialNavigation.mjs +141 -0
- package/dist/dev/router/initialNavigation.mjs.map +1 -0
- package/dist/dev/router/navigationTarget.mjs +3 -2
- package/dist/dev/router/navigationTarget.mjs.map +1 -1
- package/dist/dev/router/types.mjs.map +1 -1
- package/dist/dev/router/useRoute.mjs +14 -1
- package/dist/dev/router/useRoute.mjs.map +1 -1
- package/dist/dev/routerInternal/snapshots.mjs +3 -1
- package/dist/dev/routerInternal/snapshots.mjs.map +1 -1
- package/dist/dev/runtime/register/component/lifecycle.mjs +29 -13
- package/dist/dev/runtime/register/component/lifecycle.mjs.map +1 -1
- package/dist/dev/runtime/register/component/registerDefinition.mjs +69 -32
- package/dist/dev/runtime/register/component/registerDefinition.mjs.map +1 -1
- package/dist/dev/vue-demi.mjs +1 -1
- package/dist/index.mjs +1 -1
- package/dist/internal-runtime.mjs +1 -1
- package/dist/package.mjs +1 -1
- package/dist/router/createRouter.mjs +1 -1
- package/dist/router/initialNavigation.mjs +1 -0
- package/dist/router/navigationTarget.mjs +1 -1
- package/dist/router/types.d.mts +10 -1
- package/dist/router/useRoute.mjs +1 -1
- package/dist/router.d.mts +2 -2
- package/dist/routerInternal/snapshots.mjs +1 -1
- package/dist/runtime/register/component/lifecycle.mjs +1 -1
- package/dist/runtime/register/component/registerDefinition.mjs +1 -1
- package/dist/vue-demi.mjs +1 -1
- package/package.json +5 -5
package/dist/dev/index.mjs
CHANGED
|
@@ -24,11 +24,11 @@ import { resolveRuntimePageLayoutName, setPageLayout, syncRuntimePageLayoutState
|
|
|
24
24
|
import { runSetupFunction } from "./runtime/register/setup.mjs";
|
|
25
25
|
import { mountRuntimeInstance, setRuntimeSetDataVisibility, teardownRuntimeInstance } from "./runtime/register/runtimeInstance.mjs";
|
|
26
26
|
import { registerApp } from "./runtime/register/app.mjs";
|
|
27
|
+
import { hasInjectionContext, inject, injectGlobal, provide, provideGlobal } from "./runtime/provide.mjs";
|
|
27
28
|
import { registerPageLayoutBridge, registerRuntimeLayoutHosts, resolveLayoutBridge, resolveLayoutHost, unregisterPageLayoutBridge, unregisterRuntimeLayoutHosts, useLayoutBridge, useLayoutHosts, waitForLayoutHost } from "./runtime/layoutBridge.mjs";
|
|
28
29
|
import { registerComponent } from "./runtime/register/component.mjs";
|
|
29
30
|
import { createApp } from "./runtime/app.mjs";
|
|
30
31
|
import { useCssModule } from "./runtime/css.mjs";
|
|
31
|
-
import { hasInjectionContext, inject, injectGlobal, provide, provideGlobal } from "./runtime/provide.mjs";
|
|
32
32
|
import { createWevuComponent, createWevuScopedSlotComponent, defineComponent } from "./runtime/define.mjs";
|
|
33
33
|
import { useDisposables } from "./runtime/disposables.mjs";
|
|
34
34
|
import { useElementIntersectionObserver } from "./runtime/elementIntersectionObserver.mjs";
|
|
@@ -10,12 +10,12 @@ import { resolveRuntimePageLayoutName, setPageLayout, syncRuntimePageLayoutState
|
|
|
10
10
|
import { runSetupFunction } from "./runtime/register/setup.mjs";
|
|
11
11
|
import { mountRuntimeInstance, setRuntimeSetDataVisibility, teardownRuntimeInstance } from "./runtime/register/runtimeInstance.mjs";
|
|
12
12
|
import { registerApp } from "./runtime/register/app.mjs";
|
|
13
|
+
import { hasInjectionContext, inject, injectGlobal, provide, provideGlobal } from "./runtime/provide.mjs";
|
|
13
14
|
import { Fragment, createTextVNode, createVNode, isVNode, mergeProps, normalizeJsxIsland, resolveComponent, resolveDirective, transformOn, vModelCheckbox, vModelRadio, vModelSelect, vModelText, vShow, withDirectives } from "./runtime/jsxIsland.mjs";
|
|
14
15
|
import { resolveLayoutBridge, resolveLayoutHost, useLayoutBridge, useLayoutHosts, waitForLayoutHost } from "./runtime/layoutBridge.mjs";
|
|
15
16
|
import { registerComponent } from "./runtime/register/component.mjs";
|
|
16
17
|
import { createApp } from "./runtime/app.mjs";
|
|
17
18
|
import { useCssModule, useCssVars } from "./runtime/css.mjs";
|
|
18
|
-
import { hasInjectionContext, inject, injectGlobal, provide, provideGlobal } from "./runtime/provide.mjs";
|
|
19
19
|
import { createIsolatedWevuComponentDefinition, createWevuComponent, createWevuComponentDefinition, createWevuScopedSlotComponent, defineComponent, getWevuComponentLifecycleDefinition } from "./runtime/define.mjs";
|
|
20
20
|
import { useDisposables } from "./runtime/disposables.mjs";
|
|
21
21
|
import { useElementIntersectionObserver } from "./runtime/elementIntersectionObserver.mjs";
|
package/dist/dev/package.mjs
CHANGED
|
@@ -1,15 +1,18 @@
|
|
|
1
1
|
import { getMiniProgramGlobalObject } from "../runtime/platform.mjs";
|
|
2
|
-
import {
|
|
2
|
+
import { setActiveRouter } from "./instance.mjs";
|
|
3
|
+
import { DEFAULT_INITIAL_NAVIGATION_TIMEOUT, registerInitialNavigationRunner } from "./initialNavigation.mjs";
|
|
4
|
+
import { installRouteStateSyncOnNativeRouter, notifyRouteStateSync } from "./routeSync.mjs";
|
|
3
5
|
import { resolvePath } from "../routerInternal/path.mjs";
|
|
4
6
|
import { parseQuery, stringifyQuery } from "../routerInternal/query.mjs";
|
|
7
|
+
import { resolveCurrentRoute } from "../routerInternal/location.mjs";
|
|
5
8
|
import { resolveNamedRouteLocation } from "../routerInternal/params.mjs";
|
|
6
9
|
import { mergeMatchedRouteMeta, resolveMatchedRouteRecord } from "../routerInternal/matching.mjs";
|
|
7
10
|
import { warnDuplicateRouteEntries } from "../routerInternal/recordsWarnings.mjs";
|
|
8
11
|
import { createNamedRouteLookup, resolveRouteOptionEntries } from "../routerInternal/records.mjs";
|
|
9
12
|
import { cloneRouteMeta, cloneRouteParams, createRouterOptionsSnapshot, normalizeRouteRecordMatched, snapshotRouteLocation } from "../routerInternal/snapshots.mjs";
|
|
10
13
|
import { createNavigationResultController } from "./navigationResult.mjs";
|
|
11
|
-
import { runBackNavigationGuards } from "./backNavigation.mjs";
|
|
12
|
-
import {
|
|
14
|
+
import { resolveBackNavigationTarget, runBackNavigationGuards } from "./backNavigation.mjs";
|
|
15
|
+
import { navigateWithTarget } from "./navigationTarget.mjs";
|
|
13
16
|
import { createNavigationApi } from "./navigationApi.mjs";
|
|
14
17
|
import { resolveRouteLocation } from "./resolve.mjs";
|
|
15
18
|
import { createRouteRegistry } from "./routeRegistry.mjs";
|
|
@@ -20,7 +23,7 @@ import { createRouteStateController, useNativeRouter } from "./useRoute.mjs";
|
|
|
20
23
|
* @description 创建高阶路由导航器(对齐 Vue Router 的 createRouter 心智)
|
|
21
24
|
*/
|
|
22
25
|
function createRouter(options = {}) {
|
|
23
|
-
var _options$maxRedirects, _options$paramsMode, _options$rejectOnErro, _options$parseQuery, _options$stringifyQue, _options$tabBarEntrie;
|
|
26
|
+
var _options$maxRedirects, _options$initialNavig, _options$paramsMode, _options$rejectOnErro, _options$parseQuery, _options$stringifyQue, _options$tabBarEntrie;
|
|
24
27
|
const nativeRouter = useNativeRouter();
|
|
25
28
|
installRouteStateSyncOnNativeRouter(getMiniProgramGlobalObject());
|
|
26
29
|
const beforeEachGuards = /* @__PURE__ */ new Set();
|
|
@@ -28,6 +31,8 @@ function createRouter(options = {}) {
|
|
|
28
31
|
const afterEachHooks = /* @__PURE__ */ new Set();
|
|
29
32
|
const errorHandlers = /* @__PURE__ */ new Set();
|
|
30
33
|
const maxRedirects = (_options$maxRedirects = options.maxRedirects) !== null && _options$maxRedirects !== void 0 ? _options$maxRedirects : 10;
|
|
34
|
+
const initialNavigationMode = options.initialNavigationMode === "blocking" ? "blocking" : "eager";
|
|
35
|
+
const initialNavigationTimeout = Number.isFinite(options.initialNavigationTimeout) && ((_options$initialNavig = options.initialNavigationTimeout) !== null && _options$initialNavig !== void 0 ? _options$initialNavig : 0) > 0 ? Math.max(1, Math.trunc(options.initialNavigationTimeout)) : DEFAULT_INITIAL_NAVIGATION_TIMEOUT;
|
|
31
36
|
const paramsMode = (_options$paramsMode = options.paramsMode) !== null && _options$paramsMode !== void 0 ? _options$paramsMode : "loose";
|
|
32
37
|
const rejectOnError = (_options$rejectOnErro = options.rejectOnError) !== null && _options$rejectOnErro !== void 0 ? _options$rejectOnErro : true;
|
|
33
38
|
const routeResolveCodec = {
|
|
@@ -42,7 +47,10 @@ function createRouter(options = {}) {
|
|
|
42
47
|
const tabBarPathSet = new Set(normalizedTabBarEntries);
|
|
43
48
|
const routeRegistry = createRouteRegistry(namedRouteLookup);
|
|
44
49
|
let managedNavigationCount = 0;
|
|
45
|
-
|
|
50
|
+
let activeManagedRoutePath;
|
|
51
|
+
let pendingManagedRouteSyncPath;
|
|
52
|
+
let pendingExternalRouteSyncPath;
|
|
53
|
+
const routerOptions = createRouterOptionsSnapshot(normalizedTabBarEntries, routeRegistry.getRoutes(), paramsMode, maxRedirects, initialNavigationMode, initialNavigationTimeout, routeResolveCodec, rejectOnError);
|
|
46
54
|
function enrichRouteRecordState(routeLocation) {
|
|
47
55
|
const resolved = { ...routeLocation };
|
|
48
56
|
resolved.href = resolved.fullPath;
|
|
@@ -70,7 +78,15 @@ function createRouter(options = {}) {
|
|
|
70
78
|
return payload.source === "page" || payload.source === "native" && payload.method === "navigateBack";
|
|
71
79
|
}
|
|
72
80
|
function beforeRouteStateSync(nextRoute, payload) {
|
|
73
|
-
if (managedNavigationCount > 0 || !isExternalBackSync(payload)
|
|
81
|
+
if (managedNavigationCount > 0 || !isExternalBackSync(payload)) return;
|
|
82
|
+
if (pendingExternalRouteSyncPath !== void 0) return;
|
|
83
|
+
if (pendingManagedRouteSyncPath !== void 0) {
|
|
84
|
+
const expectedPath = pendingManagedRouteSyncPath;
|
|
85
|
+
pendingManagedRouteSyncPath = void 0;
|
|
86
|
+
if (nextRoute.fullPath === expectedPath) return;
|
|
87
|
+
}
|
|
88
|
+
if (nextRoute.fullPath === route.fullPath) return;
|
|
89
|
+
pendingExternalRouteSyncPath = nextRoute.fullPath;
|
|
74
90
|
const from = snapshotRouteLocation(route);
|
|
75
91
|
runBackNavigationGuards({
|
|
76
92
|
target: nextRoute,
|
|
@@ -81,6 +97,8 @@ function createRouter(options = {}) {
|
|
|
81
97
|
resolveWithCodec
|
|
82
98
|
}).then((result) => {
|
|
83
99
|
return emitObservedNavigationAfterEach === null || emitObservedNavigationAfterEach === void 0 ? void 0 : emitObservedNavigationAfterEach(result);
|
|
100
|
+
}).finally(() => {
|
|
101
|
+
pendingExternalRouteSyncPath = void 0;
|
|
84
102
|
});
|
|
85
103
|
}
|
|
86
104
|
route = createRouteStateController({
|
|
@@ -109,14 +127,57 @@ function createRouter(options = {}) {
|
|
|
109
127
|
resolveWithCodec,
|
|
110
128
|
settleNavigationResult: navigationResultController.settleNavigationResult
|
|
111
129
|
});
|
|
112
|
-
async function runManagedNavigation(navigation) {
|
|
130
|
+
async function runManagedNavigation(navigation, targetPath) {
|
|
131
|
+
const previousRoutePath = route.fullPath;
|
|
132
|
+
if (targetPath) activeManagedRoutePath = targetPath;
|
|
113
133
|
managedNavigationCount += 1;
|
|
114
134
|
try {
|
|
115
|
-
|
|
135
|
+
const result = await navigation();
|
|
136
|
+
if (route.fullPath !== previousRoutePath) pendingManagedRouteSyncPath = route.fullPath;
|
|
137
|
+
return result;
|
|
116
138
|
} finally {
|
|
117
139
|
managedNavigationCount -= 1;
|
|
140
|
+
if (managedNavigationCount <= 0) activeManagedRoutePath = void 0;
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
function resolveManagedRoutePath(to) {
|
|
144
|
+
try {
|
|
145
|
+
return resolveWithCodec(to, route.path).fullPath;
|
|
146
|
+
} catch (_unused) {
|
|
147
|
+
return;
|
|
118
148
|
}
|
|
119
149
|
}
|
|
150
|
+
async function runInitialNavigation(page, query, isActive = () => true) {
|
|
151
|
+
return runManagedNavigation(async () => {
|
|
152
|
+
const from = snapshotRouteLocation(route);
|
|
153
|
+
const target = enrichRouteRecordState(resolveCurrentRoute(query, page));
|
|
154
|
+
if (!target.path) return;
|
|
155
|
+
if (activeManagedRoutePath === target.fullPath) {
|
|
156
|
+
notifyRouteStateSync({
|
|
157
|
+
route: target,
|
|
158
|
+
source: "router"
|
|
159
|
+
});
|
|
160
|
+
return;
|
|
161
|
+
}
|
|
162
|
+
const result = await navigateWithTarget({
|
|
163
|
+
mode: "push",
|
|
164
|
+
target,
|
|
165
|
+
from,
|
|
166
|
+
nativeRouter,
|
|
167
|
+
routeResolveCodec,
|
|
168
|
+
namedRouteLookup,
|
|
169
|
+
beforeEachGuards,
|
|
170
|
+
beforeResolveGuards,
|
|
171
|
+
maxRedirects,
|
|
172
|
+
tabBarPathSet,
|
|
173
|
+
resolveWithCodec,
|
|
174
|
+
executeNative: false,
|
|
175
|
+
allowSameLocation: true
|
|
176
|
+
});
|
|
177
|
+
if (!isActive()) return;
|
|
178
|
+
return navigationResultController.settleNavigationResult(result);
|
|
179
|
+
});
|
|
180
|
+
}
|
|
120
181
|
function beforeEach(guard) {
|
|
121
182
|
beforeEachGuards.add(guard);
|
|
122
183
|
return () => {
|
|
@@ -155,10 +216,16 @@ function createRouter(options = {}) {
|
|
|
155
216
|
isReady() {
|
|
156
217
|
return readyPromise;
|
|
157
218
|
},
|
|
158
|
-
push: (to) => runManagedNavigation(() => navigationApi.push(to)),
|
|
159
|
-
replace: (to) => runManagedNavigation(() => navigationApi.replace(to)),
|
|
160
|
-
back: (delta) =>
|
|
161
|
-
|
|
219
|
+
push: (to) => runManagedNavigation(() => navigationApi.push(to), resolveManagedRoutePath(to)),
|
|
220
|
+
replace: (to) => runManagedNavigation(() => navigationApi.replace(to), resolveManagedRoutePath(to)),
|
|
221
|
+
back: (delta) => {
|
|
222
|
+
var _resolveBackNavigatio;
|
|
223
|
+
return runManagedNavigation(() => navigationApi.back(delta), (_resolveBackNavigatio = resolveBackNavigationTarget(delta !== null && delta !== void 0 ? delta : 1, route, resolveWithCodec)) === null || _resolveBackNavigatio === void 0 ? void 0 : _resolveBackNavigatio.fullPath);
|
|
224
|
+
},
|
|
225
|
+
go: (delta) => {
|
|
226
|
+
var _resolveBackNavigatio2;
|
|
227
|
+
return runManagedNavigation(() => navigationApi.go(delta), delta < 0 ? (_resolveBackNavigatio2 = resolveBackNavigationTarget(Math.abs(delta), route, resolveWithCodec)) === null || _resolveBackNavigatio2 === void 0 ? void 0 : _resolveBackNavigatio2.fullPath : void 0);
|
|
228
|
+
},
|
|
162
229
|
forward: () => runManagedNavigation(() => navigationApi.forward()),
|
|
163
230
|
hasRoute: routeRegistry.hasRoute,
|
|
164
231
|
getRoutes: routeRegistry.getRoutes,
|
|
@@ -171,6 +238,7 @@ function createRouter(options = {}) {
|
|
|
171
238
|
onError
|
|
172
239
|
};
|
|
173
240
|
setActiveRouter(router);
|
|
241
|
+
registerInitialNavigationRunner(router, runInitialNavigation, initialNavigationTimeout, initialNavigationMode);
|
|
174
242
|
return router;
|
|
175
243
|
}
|
|
176
244
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"createRouter.mjs","names":[],"sources":["../../../src/router/createRouter.ts"],"sourcesContent":["import type { RouteResolveCodec } from '../routerInternal/shared'\nimport type { NavigationRunResult } from './navigationResult'\nimport type { RouteStateSyncPayload } from './routeSync'\nimport type {\n NavigationAfterEach,\n NavigationErrorHandler,\n NavigationGuard,\n RouteLocationNormalizedLoaded,\n RouteLocationRaw,\n RouterNavigation,\n UseRouterOptions,\n} from './types'\nimport {\n cloneRouteMeta,\n cloneRouteParams,\n createNamedRouteLookup,\n createRouterOptionsSnapshot,\n mergeMatchedRouteMeta,\n normalizeRouteRecordMatched,\n parseQuery,\n resolveMatchedRouteRecord,\n resolveNamedRouteLocation,\n resolvePath,\n resolveRouteOptionEntries,\n snapshotRouteLocation,\n stringifyQuery,\n warnDuplicateRouteEntries,\n} from '../routerInternal/shared'\nimport { getMiniProgramGlobalObject } from '../runtime/platform'\nimport { runBackNavigationGuards } from './backNavigation'\nimport { setActiveRouter } from './instance'\nimport { createNavigationApi } from './navigationApi'\nimport { createNavigationResultController } from './navigationResult'\nimport { resolveRouteLocation } from './resolve'\nimport { createRouteRegistry } from './routeRegistry'\nimport { installRouteStateSyncOnNativeRouter } from './routeSync'\nimport { createRouteStateController, useNativeRouter } from './useRoute'\n\n/**\n * @description 创建高阶路由导航器(对齐 Vue Router 的 createRouter 心智)\n */\nexport function createRouter(options: UseRouterOptions = {}): RouterNavigation {\n const nativeRouter = useNativeRouter()\n installRouteStateSyncOnNativeRouter(getMiniProgramGlobalObject())\n const beforeEachGuards = new Set<NavigationGuard>()\n const beforeResolveGuards = new Set<NavigationGuard>()\n const afterEachHooks = new Set<NavigationAfterEach>()\n const errorHandlers = new Set<NavigationErrorHandler>()\n const maxRedirects = options.maxRedirects ?? 10\n const paramsMode = options.paramsMode ?? 'loose'\n const rejectOnError = options.rejectOnError ?? true\n const routeResolveCodec: RouteResolveCodec = {\n parseQuery: options.parseQuery ?? parseQuery,\n stringifyQuery: options.stringifyQuery ?? stringifyQuery,\n }\n const readyPromise = Promise.resolve()\n const routeEntries = resolveRouteOptionEntries(options)\n warnDuplicateRouteEntries(routeEntries)\n const namedRouteLookup = createNamedRouteLookup(routeEntries)\n const normalizedTabBarEntries = (options.tabBarEntries ?? [])\n .map(path => resolvePath(path, ''))\n .filter(Boolean)\n const tabBarPathSet = new Set(normalizedTabBarEntries)\n const routeRegistry = createRouteRegistry(namedRouteLookup)\n let managedNavigationCount = 0\n const routerOptions = createRouterOptionsSnapshot(\n normalizedTabBarEntries,\n routeRegistry.getRoutes(),\n paramsMode,\n maxRedirects,\n routeResolveCodec,\n rejectOnError,\n )\n\n function enrichRouteRecordState(routeLocation: RouteLocationNormalizedLoaded): RouteLocationNormalizedLoaded {\n const resolved = { ...routeLocation }\n resolved.href = resolved.fullPath\n const matchedResult = resolveMatchedRouteRecord(resolved, namedRouteLookup)\n if (matchedResult) {\n const matchedRecord = matchedResult.record\n if (resolved.name === undefined) {\n resolved.name = matchedRecord.name\n }\n const mergedRouteMeta = mergeMatchedRouteMeta(matchedResult.matchedRecords)\n if (mergedRouteMeta !== undefined) {\n resolved.meta = cloneRouteMeta(mergedRouteMeta)\n }\n if (matchedResult.params && Object.keys(resolved.params).length === 0) {\n resolved.params = cloneRouteParams(matchedResult.params)\n }\n resolved.matched = matchedResult.matchedRecords.map((record, index, records) => {\n const leafMatchedPath = index === records.length - 1\n ? matchedResult.matchedPath\n : undefined\n return normalizeRouteRecordMatched(record, leafMatchedPath)\n })\n }\n else {\n resolved.matched = []\n }\n return resolved\n }\n\n function resolveWithCodec(to: RouteLocationRaw, currentPath: string): RouteLocationNormalizedLoaded {\n const rawTo = typeof to === 'string'\n ? to\n : resolveNamedRouteLocation(to, namedRouteLookup, paramsMode)\n return enrichRouteRecordState(resolveRouteLocation(rawTo, currentPath, routeResolveCodec))\n }\n\n let route: Readonly<RouteLocationNormalizedLoaded>\n let emitObservedNavigationAfterEach: ((result: NavigationRunResult) => Promise<void>) | undefined\n\n function isExternalBackSync(payload: RouteStateSyncPayload): boolean {\n return payload.source === 'page'\n || (payload.source === 'native' && payload.method === 'navigateBack')\n }\n\n function beforeRouteStateSync(\n nextRoute: RouteLocationNormalizedLoaded,\n payload: RouteStateSyncPayload,\n ) {\n if (\n managedNavigationCount > 0\n || !isExternalBackSync(payload)\n || nextRoute.fullPath === route.fullPath\n ) {\n return\n }\n\n const from = snapshotRouteLocation(route)\n void runBackNavigationGuards({\n target: nextRoute,\n from,\n nativeRouter,\n beforeEachGuards,\n beforeResolveGuards,\n resolveWithCodec,\n }).then((result) => {\n return emitObservedNavigationAfterEach?.(result)\n })\n }\n\n const routeController = createRouteStateController({\n beforeRouteStateSync,\n resolveRoute: enrichRouteRecordState,\n })\n route = routeController.route\n\n function resolve(to: RouteLocationRaw): RouteLocationNormalizedLoaded {\n return resolveWithCodec(to, route.path)\n }\n\n const navigationResultController = createNavigationResultController({\n afterEachHooks,\n errorHandlers,\n nativeRouter,\n rejectOnError,\n })\n emitObservedNavigationAfterEach = navigationResultController.emitNavigationAfterEach\n\n const navigationApi = createNavigationApi({\n nativeRouter,\n route,\n routeResolveCodec,\n namedRouteLookup,\n beforeEachGuards,\n beforeResolveGuards,\n maxRedirects,\n tabBarPathSet,\n resolveWithCodec,\n settleNavigationResult: navigationResultController.settleNavigationResult,\n })\n\n async function runManagedNavigation<T>(navigation: () => Promise<T>): Promise<T> {\n managedNavigationCount += 1\n try {\n return await navigation()\n }\n finally {\n managedNavigationCount -= 1\n }\n }\n\n function beforeEach(guard: NavigationGuard): () => void {\n beforeEachGuards.add(guard)\n return () => {\n beforeEachGuards.delete(guard)\n }\n }\n\n function beforeResolve(guard: NavigationGuard): () => void {\n beforeResolveGuards.add(guard)\n return () => {\n beforeResolveGuards.delete(guard)\n }\n }\n\n function afterEach(hook: NavigationAfterEach): () => void {\n afterEachHooks.add(hook)\n return () => {\n afterEachHooks.delete(hook)\n }\n }\n\n function onError(handler: NavigationErrorHandler): () => void {\n errorHandlers.add(handler)\n return () => {\n errorHandlers.delete(handler)\n }\n }\n\n const router: RouterNavigation = {\n nativeRouter,\n options: routerOptions,\n currentRoute: route,\n install(app?: unknown): void {\n setActiveRouter(router)\n const globalProperties = (app as { config?: { globalProperties?: Record<string, unknown> } } | undefined)?.config?.globalProperties\n if (globalProperties) {\n globalProperties.$router = router\n }\n },\n resolve,\n isReady(): Promise<void> {\n return readyPromise\n },\n push: to => runManagedNavigation(() => navigationApi.push(to)),\n replace: to => runManagedNavigation(() => navigationApi.replace(to)),\n back: delta => runManagedNavigation(() => navigationApi.back(delta)),\n go: delta => runManagedNavigation(() => navigationApi.go(delta)),\n forward: () => runManagedNavigation(() => navigationApi.forward()),\n hasRoute: routeRegistry.hasRoute,\n getRoutes: routeRegistry.getRoutes,\n addRoute: routeRegistry.addRoute,\n removeRoute: routeRegistry.removeRoute,\n clearRoutes: routeRegistry.clearRoutes,\n beforeEach,\n beforeResolve,\n afterEach,\n onError,\n }\n\n setActiveRouter(router)\n return router\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"createRouter.mjs","names":[],"sources":["../../../src/router/createRouter.ts"],"sourcesContent":["import type { RouteResolveCodec } from '../routerInternal/shared'\nimport type { NavigationRunResult } from './navigationResult'\nimport type { RouteStateSyncPayload } from './routeSync'\nimport type {\n InitialNavigationMode,\n LocationQueryRaw,\n NavigationAfterEach,\n NavigationErrorHandler,\n NavigationGuard,\n RouteLocationNormalizedLoaded,\n RouteLocationRaw,\n RouterNavigation,\n UseRouterOptions,\n} from './types'\nimport {\n cloneRouteMeta,\n cloneRouteParams,\n createNamedRouteLookup,\n createRouterOptionsSnapshot,\n mergeMatchedRouteMeta,\n normalizeRouteRecordMatched,\n parseQuery,\n resolveCurrentRoute,\n resolveMatchedRouteRecord,\n resolveNamedRouteLocation,\n resolvePath,\n resolveRouteOptionEntries,\n snapshotRouteLocation,\n stringifyQuery,\n warnDuplicateRouteEntries,\n} from '../routerInternal/shared'\nimport { getMiniProgramGlobalObject } from '../runtime/platform'\nimport { resolveBackNavigationTarget, runBackNavigationGuards } from './backNavigation'\nimport { DEFAULT_INITIAL_NAVIGATION_TIMEOUT, registerInitialNavigationRunner } from './initialNavigation'\nimport { setActiveRouter } from './instance'\nimport { createNavigationApi } from './navigationApi'\nimport { createNavigationResultController } from './navigationResult'\nimport { navigateWithTarget } from './navigationTarget'\nimport { resolveRouteLocation } from './resolve'\nimport { createRouteRegistry } from './routeRegistry'\nimport { installRouteStateSyncOnNativeRouter, notifyRouteStateSync } from './routeSync'\nimport { createRouteStateController, useNativeRouter } from './useRoute'\n\n/**\n * @description 创建高阶路由导航器(对齐 Vue Router 的 createRouter 心智)\n */\nexport function createRouter(options: UseRouterOptions = {}): RouterNavigation {\n const nativeRouter = useNativeRouter()\n installRouteStateSyncOnNativeRouter(getMiniProgramGlobalObject())\n const beforeEachGuards = new Set<NavigationGuard>()\n const beforeResolveGuards = new Set<NavigationGuard>()\n const afterEachHooks = new Set<NavigationAfterEach>()\n const errorHandlers = new Set<NavigationErrorHandler>()\n const maxRedirects = options.maxRedirects ?? 10\n const initialNavigationMode: InitialNavigationMode = options.initialNavigationMode === 'blocking' ? 'blocking' : 'eager'\n const initialNavigationTimeout = Number.isFinite(options.initialNavigationTimeout) && (options.initialNavigationTimeout ?? 0) > 0\n ? Math.max(1, Math.trunc(options.initialNavigationTimeout!))\n : DEFAULT_INITIAL_NAVIGATION_TIMEOUT\n const paramsMode = options.paramsMode ?? 'loose'\n const rejectOnError = options.rejectOnError ?? true\n const routeResolveCodec: RouteResolveCodec = {\n parseQuery: options.parseQuery ?? parseQuery,\n stringifyQuery: options.stringifyQuery ?? stringifyQuery,\n }\n const readyPromise = Promise.resolve()\n const routeEntries = resolveRouteOptionEntries(options)\n warnDuplicateRouteEntries(routeEntries)\n const namedRouteLookup = createNamedRouteLookup(routeEntries)\n const normalizedTabBarEntries = (options.tabBarEntries ?? [])\n .map(path => resolvePath(path, ''))\n .filter(Boolean)\n const tabBarPathSet = new Set(normalizedTabBarEntries)\n const routeRegistry = createRouteRegistry(namedRouteLookup)\n let managedNavigationCount = 0\n let activeManagedRoutePath: string | undefined\n let pendingManagedRouteSyncPath: string | undefined\n let pendingExternalRouteSyncPath: string | undefined\n const routerOptions = createRouterOptionsSnapshot(\n normalizedTabBarEntries,\n routeRegistry.getRoutes(),\n paramsMode,\n maxRedirects,\n initialNavigationMode,\n initialNavigationTimeout,\n routeResolveCodec,\n rejectOnError,\n )\n\n function enrichRouteRecordState(routeLocation: RouteLocationNormalizedLoaded): RouteLocationNormalizedLoaded {\n const resolved = { ...routeLocation }\n resolved.href = resolved.fullPath\n const matchedResult = resolveMatchedRouteRecord(resolved, namedRouteLookup)\n if (matchedResult) {\n const matchedRecord = matchedResult.record\n if (resolved.name === undefined) {\n resolved.name = matchedRecord.name\n }\n const mergedRouteMeta = mergeMatchedRouteMeta(matchedResult.matchedRecords)\n if (mergedRouteMeta !== undefined) {\n resolved.meta = cloneRouteMeta(mergedRouteMeta)\n }\n if (matchedResult.params && Object.keys(resolved.params).length === 0) {\n resolved.params = cloneRouteParams(matchedResult.params)\n }\n resolved.matched = matchedResult.matchedRecords.map((record, index, records) => {\n const leafMatchedPath = index === records.length - 1\n ? matchedResult.matchedPath\n : undefined\n return normalizeRouteRecordMatched(record, leafMatchedPath)\n })\n }\n else {\n resolved.matched = []\n }\n return resolved\n }\n\n function resolveWithCodec(to: RouteLocationRaw, currentPath: string): RouteLocationNormalizedLoaded {\n const rawTo = typeof to === 'string'\n ? to\n : resolveNamedRouteLocation(to, namedRouteLookup, paramsMode)\n return enrichRouteRecordState(resolveRouteLocation(rawTo, currentPath, routeResolveCodec))\n }\n\n let route: Readonly<RouteLocationNormalizedLoaded>\n let emitObservedNavigationAfterEach: ((result: NavigationRunResult) => Promise<void>) | undefined\n\n function isExternalBackSync(payload: RouteStateSyncPayload): boolean {\n return payload.source === 'page'\n || (payload.source === 'native' && payload.method === 'navigateBack')\n }\n\n function beforeRouteStateSync(\n nextRoute: RouteLocationNormalizedLoaded,\n payload: RouteStateSyncPayload,\n ) {\n if (managedNavigationCount > 0 || !isExternalBackSync(payload)) {\n return\n }\n\n if (pendingExternalRouteSyncPath !== undefined) {\n return\n }\n\n if (pendingManagedRouteSyncPath !== undefined) {\n const expectedPath = pendingManagedRouteSyncPath\n pendingManagedRouteSyncPath = undefined\n if (nextRoute.fullPath === expectedPath) {\n return\n }\n }\n\n if (nextRoute.fullPath === route.fullPath) {\n return\n }\n\n pendingExternalRouteSyncPath = nextRoute.fullPath\n const from = snapshotRouteLocation(route)\n void runBackNavigationGuards({\n target: nextRoute,\n from,\n nativeRouter,\n beforeEachGuards,\n beforeResolveGuards,\n resolveWithCodec,\n }).then((result) => {\n return emitObservedNavigationAfterEach?.(result)\n }).finally(() => {\n pendingExternalRouteSyncPath = undefined\n })\n }\n\n const routeController = createRouteStateController({\n beforeRouteStateSync,\n resolveRoute: enrichRouteRecordState,\n })\n route = routeController.route\n\n function resolve(to: RouteLocationRaw): RouteLocationNormalizedLoaded {\n return resolveWithCodec(to, route.path)\n }\n\n const navigationResultController = createNavigationResultController({\n afterEachHooks,\n errorHandlers,\n nativeRouter,\n rejectOnError,\n })\n emitObservedNavigationAfterEach = navigationResultController.emitNavigationAfterEach\n\n const navigationApi = createNavigationApi({\n nativeRouter,\n route,\n routeResolveCodec,\n namedRouteLookup,\n beforeEachGuards,\n beforeResolveGuards,\n maxRedirects,\n tabBarPathSet,\n resolveWithCodec,\n settleNavigationResult: navigationResultController.settleNavigationResult,\n })\n\n async function runManagedNavigation<T>(navigation: () => Promise<T>, targetPath?: string): Promise<T> {\n const previousRoutePath = route.fullPath\n if (targetPath) {\n activeManagedRoutePath = targetPath\n }\n managedNavigationCount += 1\n try {\n const result = await navigation()\n if (route.fullPath !== previousRoutePath) {\n pendingManagedRouteSyncPath = route.fullPath\n }\n return result\n }\n finally {\n managedNavigationCount -= 1\n if (managedNavigationCount <= 0) {\n activeManagedRoutePath = undefined\n }\n }\n }\n\n function resolveManagedRoutePath(to: RouteLocationRaw): string | undefined {\n try {\n return resolveWithCodec(to, route.path).fullPath\n }\n catch {\n return undefined\n }\n }\n\n async function runInitialNavigation(\n page: Parameters<typeof resolveCurrentRoute>[1],\n query?: LocationQueryRaw,\n isActive: () => boolean = () => true,\n ) {\n return runManagedNavigation(async () => {\n const from = snapshotRouteLocation(route)\n const target = enrichRouteRecordState(resolveCurrentRoute(query, page))\n if (!target.path) {\n return undefined\n }\n if (activeManagedRoutePath === target.fullPath) {\n notifyRouteStateSync({\n route: target,\n source: 'router',\n })\n return undefined\n }\n const result = await navigateWithTarget({\n mode: 'push',\n target,\n from,\n nativeRouter,\n routeResolveCodec,\n namedRouteLookup,\n beforeEachGuards,\n beforeResolveGuards,\n maxRedirects,\n tabBarPathSet,\n resolveWithCodec,\n executeNative: false,\n allowSameLocation: true,\n })\n if (!isActive()) {\n return undefined\n }\n return navigationResultController.settleNavigationResult(result)\n })\n }\n\n function beforeEach(guard: NavigationGuard): () => void {\n beforeEachGuards.add(guard)\n return () => {\n beforeEachGuards.delete(guard)\n }\n }\n\n function beforeResolve(guard: NavigationGuard): () => void {\n beforeResolveGuards.add(guard)\n return () => {\n beforeResolveGuards.delete(guard)\n }\n }\n\n function afterEach(hook: NavigationAfterEach): () => void {\n afterEachHooks.add(hook)\n return () => {\n afterEachHooks.delete(hook)\n }\n }\n\n function onError(handler: NavigationErrorHandler): () => void {\n errorHandlers.add(handler)\n return () => {\n errorHandlers.delete(handler)\n }\n }\n\n const router: RouterNavigation = {\n nativeRouter,\n options: routerOptions,\n currentRoute: route,\n install(app?: unknown): void {\n setActiveRouter(router)\n const globalProperties = (app as { config?: { globalProperties?: Record<string, unknown> } } | undefined)?.config?.globalProperties\n if (globalProperties) {\n globalProperties.$router = router\n }\n },\n resolve,\n isReady(): Promise<void> {\n return readyPromise\n },\n push: to => runManagedNavigation(() => navigationApi.push(to), resolveManagedRoutePath(to)),\n replace: to => runManagedNavigation(() => navigationApi.replace(to), resolveManagedRoutePath(to)),\n back: delta => runManagedNavigation(\n () => navigationApi.back(delta),\n resolveBackNavigationTarget(delta ?? 1, route, resolveWithCodec)?.fullPath,\n ),\n go: delta => runManagedNavigation(\n () => navigationApi.go(delta),\n delta < 0\n ? resolveBackNavigationTarget(Math.abs(delta), route, resolveWithCodec)?.fullPath\n : undefined,\n ),\n forward: () => runManagedNavigation(() => navigationApi.forward()),\n hasRoute: routeRegistry.hasRoute,\n getRoutes: routeRegistry.getRoutes,\n addRoute: routeRegistry.addRoute,\n removeRoute: routeRegistry.removeRoute,\n clearRoutes: routeRegistry.clearRoutes,\n beforeEach,\n beforeResolve,\n afterEach,\n onError,\n }\n\n setActiveRouter(router)\n registerInitialNavigationRunner(router, runInitialNavigation, initialNavigationTimeout, initialNavigationMode)\n return router\n}\n"],"mappings":"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"}
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
import { getActiveRouter } from "./instance.mjs";
|
|
2
|
+
import { WEVU_INITIAL_NAVIGATION_TIMEOUT_MARKER } from "@weapp-core/constants";
|
|
3
|
+
|
|
4
|
+
//#region src/router/initialNavigation.ts
|
|
5
|
+
const DEFAULT_INITIAL_NAVIGATION_TIMEOUT = 1e4;
|
|
6
|
+
const initialNavigationRunners = /* @__PURE__ */ new WeakMap();
|
|
7
|
+
const initialNavigationControllers = /* @__PURE__ */ new WeakMap();
|
|
8
|
+
function normalizeTimeout(timeoutMs) {
|
|
9
|
+
return Number.isFinite(timeoutMs) && timeoutMs > 0 ? Math.max(1, Math.trunc(timeoutMs)) : DEFAULT_INITIAL_NAVIGATION_TIMEOUT;
|
|
10
|
+
}
|
|
11
|
+
function snapshotPage(instance) {
|
|
12
|
+
return {
|
|
13
|
+
route: typeof instance.route === "string" ? instance.route : void 0,
|
|
14
|
+
__route__: typeof instance.__route__ === "string" ? instance.__route__ : void 0,
|
|
15
|
+
options: instance.options && typeof instance.options === "object" ? { ...instance.options } : void 0
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
function snapshotQuery(query) {
|
|
19
|
+
if (!query || typeof query !== "object") return;
|
|
20
|
+
return Object.fromEntries(Object.entries(query).map(([key, value]) => [key, Array.isArray(value) ? [...value] : value]));
|
|
21
|
+
}
|
|
22
|
+
function registerInitialNavigationRunner(router, runner, timeoutMs = DEFAULT_INITIAL_NAVIGATION_TIMEOUT, mode = "blocking") {
|
|
23
|
+
initialNavigationRunners.set(router, {
|
|
24
|
+
runner,
|
|
25
|
+
mode,
|
|
26
|
+
timeoutMs: normalizeTimeout(timeoutMs)
|
|
27
|
+
});
|
|
28
|
+
}
|
|
29
|
+
function getInitialNavigationTimeout() {
|
|
30
|
+
var _initialNavigationRun2, _initialNavigationRun3;
|
|
31
|
+
const router = getActiveRouter();
|
|
32
|
+
return router ? (_initialNavigationRun2 = (_initialNavigationRun3 = initialNavigationRunners.get(router)) === null || _initialNavigationRun3 === void 0 ? void 0 : _initialNavigationRun3.timeoutMs) !== null && _initialNavigationRun2 !== void 0 ? _initialNavigationRun2 : DEFAULT_INITIAL_NAVIGATION_TIMEOUT : DEFAULT_INITIAL_NAVIGATION_TIMEOUT;
|
|
33
|
+
}
|
|
34
|
+
function isNavigationFailureResult(result) {
|
|
35
|
+
return Boolean(result && typeof result === "object" && result.__wevuNavigationFailure);
|
|
36
|
+
}
|
|
37
|
+
function ensureInitialNavigation(instance, query, options = {}) {
|
|
38
|
+
const existing = initialNavigationControllers.get(instance);
|
|
39
|
+
if (existing) {
|
|
40
|
+
if (options.onComplete && existing.blocking) existing.subscribe(options.onComplete);
|
|
41
|
+
if (options.start !== false) existing.start(query);
|
|
42
|
+
return existing.blocking ? existing.promise : void 0;
|
|
43
|
+
}
|
|
44
|
+
const router = getActiveRouter();
|
|
45
|
+
const registration = router ? initialNavigationRunners.get(router) : void 0;
|
|
46
|
+
let pendingRunner = registration === null || registration === void 0 ? void 0 : registration.runner;
|
|
47
|
+
if (!pendingRunner) return;
|
|
48
|
+
const blocking = (registration === null || registration === void 0 ? void 0 : registration.mode) === "blocking";
|
|
49
|
+
let page = snapshotPage(instance);
|
|
50
|
+
let initialQuery = snapshotQuery(query);
|
|
51
|
+
let currentStatus = "idle";
|
|
52
|
+
let timeoutHandle;
|
|
53
|
+
const timeoutMs = getInitialNavigationTimeout();
|
|
54
|
+
let resolveNavigation;
|
|
55
|
+
const completionCallbacks = /* @__PURE__ */ new Set();
|
|
56
|
+
const promise = new Promise((resolve) => {
|
|
57
|
+
resolveNavigation = resolve;
|
|
58
|
+
});
|
|
59
|
+
const settle = (status, shouldMount) => {
|
|
60
|
+
if (currentStatus !== "idle" && currentStatus !== "running") return;
|
|
61
|
+
currentStatus = status;
|
|
62
|
+
if (timeoutHandle !== void 0) {
|
|
63
|
+
clearTimeout(timeoutHandle);
|
|
64
|
+
timeoutHandle = void 0;
|
|
65
|
+
}
|
|
66
|
+
const callbacks = [...completionCallbacks];
|
|
67
|
+
completionCallbacks.clear();
|
|
68
|
+
pendingRunner = void 0;
|
|
69
|
+
page = void 0;
|
|
70
|
+
initialQuery = void 0;
|
|
71
|
+
resolveNavigation(shouldMount);
|
|
72
|
+
queueMicrotask(() => {
|
|
73
|
+
if (currentStatus !== "allowed" && currentStatus !== "timed-out") return;
|
|
74
|
+
for (const entry of callbacks) if (entry.active) {
|
|
75
|
+
entry.callback(shouldMount);
|
|
76
|
+
entry.active = false;
|
|
77
|
+
}
|
|
78
|
+
});
|
|
79
|
+
};
|
|
80
|
+
const controller = {
|
|
81
|
+
promise,
|
|
82
|
+
blocking,
|
|
83
|
+
status: () => currentStatus,
|
|
84
|
+
subscribe(callback) {
|
|
85
|
+
const entry = {
|
|
86
|
+
callback,
|
|
87
|
+
active: true
|
|
88
|
+
};
|
|
89
|
+
if (currentStatus !== "idle" && currentStatus !== "running") queueMicrotask(() => {
|
|
90
|
+
if (entry.active && (currentStatus === "allowed" || currentStatus === "timed-out")) {
|
|
91
|
+
callback(currentStatus === "allowed" || currentStatus === "timed-out");
|
|
92
|
+
entry.active = false;
|
|
93
|
+
}
|
|
94
|
+
});
|
|
95
|
+
else completionCallbacks.add(entry);
|
|
96
|
+
return () => {
|
|
97
|
+
entry.active = false;
|
|
98
|
+
completionCallbacks.delete(entry);
|
|
99
|
+
};
|
|
100
|
+
},
|
|
101
|
+
start(startQuery) {
|
|
102
|
+
if (currentStatus !== "idle") return;
|
|
103
|
+
currentStatus = "running";
|
|
104
|
+
if (blocking) timeoutHandle = setTimeout(() => {
|
|
105
|
+
var _ref, _page$route;
|
|
106
|
+
if (currentStatus !== "running") return;
|
|
107
|
+
console.warn(`${WEVU_INITIAL_NAVIGATION_TIMEOUT_MARKER} initial navigation exceeded ${timeoutMs}ms; mounting page`, (_ref = (_page$route = page === null || page === void 0 ? void 0 : page.route) !== null && _page$route !== void 0 ? _page$route : page === null || page === void 0 ? void 0 : page.__route__) !== null && _ref !== void 0 ? _ref : "");
|
|
108
|
+
settle("timed-out", true);
|
|
109
|
+
}, timeoutMs);
|
|
110
|
+
const runnerPage = page;
|
|
111
|
+
const runnerQuery = snapshotQuery(startQuery !== null && startQuery !== void 0 ? startQuery : initialQuery);
|
|
112
|
+
const runner = pendingRunner;
|
|
113
|
+
pendingRunner = void 0;
|
|
114
|
+
if (!runner || !runnerPage) {
|
|
115
|
+
settle("aborted", false);
|
|
116
|
+
return;
|
|
117
|
+
}
|
|
118
|
+
runner(runnerPage, runnerQuery, () => currentStatus === "running").then((result) => {
|
|
119
|
+
const failed = isNavigationFailureResult(result);
|
|
120
|
+
settle(failed ? "aborted" : "allowed", !failed);
|
|
121
|
+
}, () => {
|
|
122
|
+
settle("aborted", false);
|
|
123
|
+
});
|
|
124
|
+
},
|
|
125
|
+
cancel() {
|
|
126
|
+
settle("cancelled", false);
|
|
127
|
+
}
|
|
128
|
+
};
|
|
129
|
+
initialNavigationControllers.set(instance, controller);
|
|
130
|
+
if (options.onComplete && blocking) controller.subscribe(options.onComplete);
|
|
131
|
+
if (options.start !== false) controller.start(query);
|
|
132
|
+
return blocking ? promise : void 0;
|
|
133
|
+
}
|
|
134
|
+
function cancelInitialNavigation(instance) {
|
|
135
|
+
var _initialNavigationCon3;
|
|
136
|
+
(_initialNavigationCon3 = initialNavigationControllers.get(instance)) === null || _initialNavigationCon3 === void 0 || _initialNavigationCon3.cancel();
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
//#endregion
|
|
140
|
+
export { DEFAULT_INITIAL_NAVIGATION_TIMEOUT, cancelInitialNavigation, ensureInitialNavigation, getInitialNavigationTimeout, registerInitialNavigationRunner };
|
|
141
|
+
//# sourceMappingURL=initialNavigation.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"initialNavigation.mjs","names":[],"sources":["../../../src/router/initialNavigation.ts"],"sourcesContent":["import type { MiniProgramPageLike } from '../routerInternal/shared'\nimport type { InitialNavigationMode, LocationQueryRaw, NavigationFailure } from './types'\nimport { WEVU_INITIAL_NAVIGATION_TIMEOUT_MARKER } from '@weapp-core/constants'\nimport { getActiveRouter } from './instance'\n\nexport const DEFAULT_INITIAL_NAVIGATION_TIMEOUT = 10_000\n\nexport type InitialNavigationStatus = 'idle' | 'running' | 'allowed' | 'aborted' | 'timed-out' | 'cancelled'\n\ninterface InitialNavigationRunnerRegistration {\n runner: InitialNavigationRunner\n mode: InitialNavigationMode\n timeoutMs: number\n}\n\nexport type InitialNavigationRunner = (\n page: MiniProgramPageLike,\n query?: LocationQueryRaw,\n isActive?: () => boolean,\n) => Promise<void | NavigationFailure>\n\ninterface InitialNavigationController {\n readonly promise: Promise<boolean>\n readonly blocking: boolean\n readonly status: () => InitialNavigationStatus\n subscribe: (callback: (shouldMount: boolean) => void) => () => void\n start: (query?: LocationQueryRaw) => void\n cancel: () => void\n}\n\nconst initialNavigationRunners = new WeakMap<object, InitialNavigationRunnerRegistration>()\nconst initialNavigationControllers = new WeakMap<object, InitialNavigationController>()\n\nfunction normalizeTimeout(timeoutMs: number) {\n return Number.isFinite(timeoutMs) && timeoutMs > 0\n ? Math.max(1, Math.trunc(timeoutMs))\n : DEFAULT_INITIAL_NAVIGATION_TIMEOUT\n}\n\nfunction snapshotPage(instance: MiniProgramPageLike): MiniProgramPageLike {\n return {\n route: typeof instance.route === 'string' ? instance.route : undefined,\n __route__: typeof instance.__route__ === 'string' ? instance.__route__ : undefined,\n options: instance.options && typeof instance.options === 'object'\n ? { ...instance.options }\n : undefined,\n }\n}\n\nfunction snapshotQuery(query: LocationQueryRaw | undefined): LocationQueryRaw | undefined {\n if (!query || typeof query !== 'object') {\n return undefined\n }\n return Object.fromEntries(Object.entries(query).map(([key, value]) => [\n key,\n Array.isArray(value) ? [...value] : value,\n ]))\n}\n\nexport function registerInitialNavigationRunner(\n router: object,\n runner: InitialNavigationRunner,\n timeoutMs = DEFAULT_INITIAL_NAVIGATION_TIMEOUT,\n mode: InitialNavigationMode = 'blocking',\n) {\n initialNavigationRunners.set(router, {\n runner,\n mode,\n timeoutMs: normalizeTimeout(timeoutMs),\n })\n}\n\nexport function getInitialNavigationRunner(): InitialNavigationRunner | undefined {\n const router = getActiveRouter()\n return router ? initialNavigationRunners.get(router)?.runner : undefined\n}\n\nexport function getInitialNavigationTimeout() {\n const router = getActiveRouter()\n return router ? initialNavigationRunners.get(router)?.timeoutMs ?? DEFAULT_INITIAL_NAVIGATION_TIMEOUT : DEFAULT_INITIAL_NAVIGATION_TIMEOUT\n}\n\nexport function getInitialNavigationMode(): InitialNavigationMode {\n const router = getActiveRouter()\n return router ? initialNavigationRunners.get(router)?.mode ?? 'eager' : 'eager'\n}\n\nfunction isNavigationFailureResult(result: void | NavigationFailure): result is NavigationFailure {\n return Boolean(result && typeof result === 'object' && (result as NavigationFailure).__wevuNavigationFailure)\n}\n\nexport function getInitialNavigationPromise(instance: MiniProgramPageLike) {\n return initialNavigationControllers.get(instance as object)?.promise\n}\n\nexport function getInitialNavigationStatus(instance: MiniProgramPageLike) {\n return initialNavigationControllers.get(instance as object)?.status()\n}\n\nexport function ensureInitialNavigation(\n instance: MiniProgramPageLike,\n query?: LocationQueryRaw,\n options: { start?: boolean, onComplete?: (shouldMount: boolean) => void } = {},\n) {\n const existing = initialNavigationControllers.get(instance as object)\n if (existing) {\n if (options.onComplete && existing.blocking) {\n existing.subscribe(options.onComplete)\n }\n if (options.start !== false) {\n existing.start(query)\n }\n return existing.blocking ? existing.promise : undefined\n }\n\n const router = getActiveRouter()\n const registration = router ? initialNavigationRunners.get(router) : undefined\n let pendingRunner = registration?.runner\n if (!pendingRunner) {\n return undefined\n }\n const blocking = registration?.mode === 'blocking'\n\n let page: MiniProgramPageLike | undefined = snapshotPage(instance)\n let initialQuery = snapshotQuery(query)\n let currentStatus: InitialNavigationStatus = 'idle'\n let timeoutHandle: ReturnType<typeof setTimeout> | undefined\n const timeoutMs = getInitialNavigationTimeout()\n let resolveNavigation!: (shouldMount: boolean) => void\n const completionCallbacks = new Set<{ callback: (shouldMount: boolean) => void, active: boolean }>()\n const promise = new Promise<boolean>((resolve) => {\n resolveNavigation = resolve\n })\n\n const settle = (status: Exclude<InitialNavigationStatus, 'idle' | 'running'>, shouldMount: boolean) => {\n if (currentStatus !== 'idle' && currentStatus !== 'running') {\n return\n }\n currentStatus = status\n if (timeoutHandle !== undefined) {\n clearTimeout(timeoutHandle)\n timeoutHandle = undefined\n }\n const callbacks = [...completionCallbacks]\n completionCallbacks.clear()\n pendingRunner = undefined\n page = undefined\n initialQuery = undefined\n resolveNavigation(shouldMount)\n queueMicrotask(() => {\n if (currentStatus !== 'allowed' && currentStatus !== 'timed-out') {\n return\n }\n for (const entry of callbacks) {\n if (entry.active) {\n entry.callback(shouldMount)\n entry.active = false\n }\n }\n })\n }\n\n const controller: InitialNavigationController = {\n promise,\n blocking,\n status: () => currentStatus,\n subscribe(callback) {\n const entry = { callback, active: true }\n if (currentStatus !== 'idle' && currentStatus !== 'running') {\n queueMicrotask(() => {\n if (entry.active && (currentStatus === 'allowed' || currentStatus === 'timed-out')) {\n callback(currentStatus === 'allowed' || currentStatus === 'timed-out')\n entry.active = false\n }\n })\n }\n else {\n completionCallbacks.add(entry)\n }\n return () => {\n entry.active = false\n completionCallbacks.delete(entry)\n }\n },\n start(startQuery?: LocationQueryRaw) {\n if (currentStatus !== 'idle') {\n return\n }\n currentStatus = 'running'\n if (blocking) {\n timeoutHandle = setTimeout(() => {\n if (currentStatus !== 'running') {\n return\n }\n // 超时是可恢复的运行时诊断,保留稳定 marker 供宿主和 E2E 观测。\n // eslint-disable-next-line no-console\n console.warn(`${WEVU_INITIAL_NAVIGATION_TIMEOUT_MARKER} initial navigation exceeded ${timeoutMs}ms; mounting page`, page?.route ?? page?.__route__ ?? '')\n settle('timed-out', true)\n }, timeoutMs)\n }\n const runnerPage = page\n const runnerQuery = snapshotQuery(startQuery ?? initialQuery)\n const runner = pendingRunner\n pendingRunner = undefined\n if (!runner || !runnerPage) {\n settle('aborted', false)\n return\n }\n void runner(runnerPage, runnerQuery, () => currentStatus === 'running').then((result) => {\n const failed = isNavigationFailureResult(result)\n settle(failed ? 'aborted' : 'allowed', !failed)\n }, () => {\n settle('aborted', false)\n })\n },\n cancel() {\n settle('cancelled', false)\n },\n }\n\n initialNavigationControllers.set(instance as object, controller)\n if (options.onComplete && blocking) {\n controller.subscribe(options.onComplete)\n }\n if (options.start !== false) {\n controller.start(query)\n }\n return blocking ? promise : undefined\n}\n\nexport function cancelInitialNavigation(instance: MiniProgramPageLike) {\n initialNavigationControllers.get(instance as object)?.cancel()\n}\n"],"mappings":"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"}
|
|
@@ -8,7 +8,7 @@ import { applyRedirectedFrom, createDuplicatedFailure, createHashOnlyNavigationF
|
|
|
8
8
|
|
|
9
9
|
//#region src/router/navigationTarget.ts
|
|
10
10
|
async function navigateWithTarget(options) {
|
|
11
|
-
const { mode, target, from, nativeRouter, routeResolveCodec, namedRouteLookup, beforeEachGuards, beforeResolveGuards, maxRedirects, tabBarPathSet, resolveWithCodec } = options;
|
|
11
|
+
const { mode, target, from, nativeRouter, routeResolveCodec, namedRouteLookup, beforeEachGuards, beforeResolveGuards, maxRedirects, tabBarPathSet, resolveWithCodec, executeNative = true, allowSameLocation = false } = options;
|
|
12
12
|
let currentTarget = target;
|
|
13
13
|
let currentMode = mode;
|
|
14
14
|
let redirectCount = 0;
|
|
@@ -16,7 +16,7 @@ async function navigateWithTarget(options) {
|
|
|
16
16
|
var _matchedRouteResult$m;
|
|
17
17
|
const tabBarTarget = tabBarPathSet.has(currentTarget.path);
|
|
18
18
|
if (createNativeRouteUrl(currentTarget, routeResolveCodec.stringifyQuery) === createNativeRouteUrl(from, routeResolveCodec.stringifyQuery) && currentTarget.hash !== from.hash) return createNavigationRunResult(currentMode, from, currentTarget, createHashOnlyNavigationFailure(currentTarget, from));
|
|
19
|
-
if (tabBarTarget ? currentTarget.path === from.path : currentTarget.fullPath === from.fullPath) return createNavigationRunResult(currentMode, from, currentTarget, createDuplicatedFailure(currentTarget, from));
|
|
19
|
+
if (!allowSameLocation && (tabBarTarget ? currentTarget.path === from.path : currentTarget.fullPath === from.fullPath)) return createNavigationRunResult(currentMode, from, currentTarget, createDuplicatedFailure(currentTarget, from));
|
|
20
20
|
if (tabBarTarget && hasLocationQuery(currentTarget.query)) return createNavigationRunResult(currentMode, from, currentTarget, createTabBarQueryFailure(currentTarget, from));
|
|
21
21
|
const beforeEachResult = await runNavigationGuards(beforeEachGuards, {
|
|
22
22
|
mode: currentMode,
|
|
@@ -105,6 +105,7 @@ async function navigateWithTarget(options) {
|
|
|
105
105
|
continue;
|
|
106
106
|
}
|
|
107
107
|
}
|
|
108
|
+
if (!executeNative) return createNavigationRunResult(currentMode, from, currentTarget);
|
|
108
109
|
if (tabBarTarget) {
|
|
109
110
|
const result = await executeNavigationMethod(nativeRouter.switchTab, { url: createAbsoluteRoutePath(currentTarget.path) }, currentTarget, from);
|
|
110
111
|
if (isNavigationFailure(result)) return createNavigationRunResult(currentMode, from, currentTarget, result);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"navigationTarget.mjs","names":[],"sources":["../../../src/router/navigationTarget.ts"],"sourcesContent":["import type {\n NamedRouteLookup,\n RouteResolveCodec,\n} from '../routerInternal/shared'\nimport type { NavigationRunResult } from './navigationResult'\nimport type {\n NavigationGuard,\n NavigationMode,\n RouteLocationNormalizedLoaded,\n RouteLocationRaw,\n} from './types'\nimport {\n createAbsoluteRoutePath,\n createNativeRouteUrl,\n hasLocationQuery,\n resolveMatchedRouteRecord,\n} from '../routerInternal/shared'\nimport {\n createNavigationFailure,\n executeNavigationMethod,\n isNavigationFailure,\n runNavigationGuards,\n} from './navigationCore'\nimport { createNavigationRunResult } from './navigationResult'\nimport {\n applyRedirectedFrom,\n createDuplicatedFailure,\n createHashOnlyNavigationFailure,\n createTabBarQueryFailure,\n createTooManyRedirectsFailure,\n resolveRouteRecordRedirect,\n} from './navigationTargetHelpers'\nimport { NavigationFailureType } from './types'\n\ninterface NavigateWithTargetOptions {\n mode: Exclude<NavigationMode, 'back'>\n target: RouteLocationNormalizedLoaded\n from: RouteLocationNormalizedLoaded\n nativeRouter: Record<string, any>\n routeResolveCodec: RouteResolveCodec\n namedRouteLookup: NamedRouteLookup\n beforeEachGuards: ReadonlySet<NavigationGuard>\n beforeResolveGuards: ReadonlySet<NavigationGuard>\n maxRedirects: number\n tabBarPathSet: ReadonlySet<string>\n resolveWithCodec: (to: RouteLocationRaw, currentPath: string) => RouteLocationNormalizedLoaded\n}\n\nexport async function navigateWithTarget(options: NavigateWithTargetOptions): Promise<NavigationRunResult> {\n const {\n mode,\n target,\n from,\n nativeRouter,\n routeResolveCodec,\n namedRouteLookup,\n beforeEachGuards,\n beforeResolveGuards,\n maxRedirects,\n tabBarPathSet,\n resolveWithCodec,\n } = options\n let currentTarget = target\n let currentMode: Exclude<NavigationMode, 'back'> = mode\n let redirectCount = 0\n\n while (true) {\n const tabBarTarget = tabBarPathSet.has(currentTarget.path)\n const sameNativeLocation = createNativeRouteUrl(currentTarget, routeResolveCodec.stringifyQuery)\n === createNativeRouteUrl(from, routeResolveCodec.stringifyQuery)\n if (sameNativeLocation && currentTarget.hash !== from.hash) {\n return createNavigationRunResult(currentMode, from, currentTarget, createHashOnlyNavigationFailure(currentTarget, from))\n }\n\n const duplicated = tabBarTarget\n ? currentTarget.path === from.path\n : currentTarget.fullPath === from.fullPath\n if (duplicated) {\n return createNavigationRunResult(currentMode, from, currentTarget, createDuplicatedFailure(currentTarget, from))\n }\n\n if (tabBarTarget && hasLocationQuery(currentTarget.query)) {\n return createNavigationRunResult(currentMode, from, currentTarget, createTabBarQueryFailure(currentTarget, from))\n }\n\n const beforeEachResult = await runNavigationGuards(beforeEachGuards, {\n mode: currentMode,\n to: currentTarget,\n from,\n nativeRouter: nativeRouter as any,\n }, resolveWithCodec)\n\n if (beforeEachResult.status === 'failure') {\n return createNavigationRunResult(currentMode, from, currentTarget, beforeEachResult.failure)\n }\n if (beforeEachResult.status === 'redirect') {\n const redirectedTarget = beforeEachResult.target\n const redirectedMode = beforeEachResult.replace === true\n ? 'replace'\n : beforeEachResult.replace === false\n ? 'push'\n : currentMode\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n continue\n }\n }\n\n const matchedRouteResult = resolveMatchedRouteRecord(currentTarget, namedRouteLookup)\n const matchedRouteRecords = matchedRouteResult?.matchedRecords ?? []\n let redirectedByRouteRecord = false\n for (const matchedRouteRecord of matchedRouteRecords) {\n if (matchedRouteRecord.redirect === undefined) {\n continue\n }\n let redirectedByRecord: { target: RouteLocationNormalizedLoaded, replace?: boolean }\n try {\n redirectedByRecord = await resolveRouteRecordRedirect(\n matchedRouteRecord.redirect,\n currentTarget,\n from,\n resolveWithCodec,\n )\n }\n catch (error) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createNavigationFailure(NavigationFailureType.aborted, currentTarget, from, error),\n )\n }\n\n const redirectedMode = redirectedByRecord.replace === false ? 'push' : 'replace'\n const redirectedTarget = redirectedByRecord.target\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n redirectedByRouteRecord = true\n break\n }\n }\n if (redirectedByRouteRecord) {\n continue\n }\n\n let redirectedByBeforeEnter = false\n for (const matchedRouteRecord of matchedRouteRecords) {\n if (matchedRouteRecord.beforeEnterGuards.length === 0) {\n continue\n }\n const beforeEnterResult = await runNavigationGuards(new Set(matchedRouteRecord.beforeEnterGuards), {\n mode: currentMode,\n to: currentTarget,\n from,\n nativeRouter: nativeRouter as any,\n }, resolveWithCodec)\n\n if (beforeEnterResult.status === 'failure') {\n return createNavigationRunResult(currentMode, from, currentTarget, beforeEnterResult.failure)\n }\n if (beforeEnterResult.status === 'redirect') {\n const redirectedTarget = beforeEnterResult.target\n const redirectedMode = beforeEnterResult.replace === true\n ? 'replace'\n : beforeEnterResult.replace === false\n ? 'push'\n : currentMode\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n redirectedByBeforeEnter = true\n break\n }\n }\n }\n if (redirectedByBeforeEnter) {\n continue\n }\n\n const beforeResolveResult = await runNavigationGuards(beforeResolveGuards, {\n mode: currentMode,\n to: currentTarget,\n from,\n nativeRouter: nativeRouter as any,\n }, resolveWithCodec)\n\n if (beforeResolveResult.status === 'failure') {\n return createNavigationRunResult(currentMode, from, currentTarget, beforeResolveResult.failure)\n }\n if (beforeResolveResult.status === 'redirect') {\n const redirectedTarget = beforeResolveResult.target\n const redirectedMode = beforeResolveResult.replace === true\n ? 'replace'\n : beforeResolveResult.replace === false\n ? 'push'\n : currentMode\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n continue\n }\n }\n\n if (tabBarTarget) {\n const result = await executeNavigationMethod(\n nativeRouter.switchTab as (options: Record<string, any>) => unknown,\n { url: createAbsoluteRoutePath(currentTarget.path) },\n currentTarget,\n from,\n )\n if (isNavigationFailure(result)) {\n return createNavigationRunResult(currentMode, from, currentTarget, result)\n }\n return createNavigationRunResult(currentMode, from, currentTarget)\n }\n\n const nativeMethod = currentMode === 'push'\n ? nativeRouter.navigateTo\n : nativeRouter.redirectTo\n const result = await executeNavigationMethod(\n nativeMethod as (options: Record<string, any>) => unknown,\n { url: createNativeRouteUrl(currentTarget, routeResolveCodec.stringifyQuery) },\n currentTarget,\n from,\n )\n if (isNavigationFailure(result)) {\n return createNavigationRunResult(currentMode, from, currentTarget, result)\n }\n return createNavigationRunResult(currentMode, from, currentTarget)\n }\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"navigationTarget.mjs","names":[],"sources":["../../../src/router/navigationTarget.ts"],"sourcesContent":["import type {\n NamedRouteLookup,\n RouteResolveCodec,\n} from '../routerInternal/shared'\nimport type { NavigationRunResult } from './navigationResult'\nimport type {\n NavigationGuard,\n NavigationMode,\n RouteLocationNormalizedLoaded,\n RouteLocationRaw,\n} from './types'\nimport {\n createAbsoluteRoutePath,\n createNativeRouteUrl,\n hasLocationQuery,\n resolveMatchedRouteRecord,\n} from '../routerInternal/shared'\nimport {\n createNavigationFailure,\n executeNavigationMethod,\n isNavigationFailure,\n runNavigationGuards,\n} from './navigationCore'\nimport { createNavigationRunResult } from './navigationResult'\nimport {\n applyRedirectedFrom,\n createDuplicatedFailure,\n createHashOnlyNavigationFailure,\n createTabBarQueryFailure,\n createTooManyRedirectsFailure,\n resolveRouteRecordRedirect,\n} from './navigationTargetHelpers'\nimport { NavigationFailureType } from './types'\n\ninterface NavigateWithTargetOptions {\n mode: Exclude<NavigationMode, 'back'>\n target: RouteLocationNormalizedLoaded\n from: RouteLocationNormalizedLoaded\n nativeRouter: Record<string, any>\n routeResolveCodec: RouteResolveCodec\n namedRouteLookup: NamedRouteLookup\n beforeEachGuards: ReadonlySet<NavigationGuard>\n beforeResolveGuards: ReadonlySet<NavigationGuard>\n maxRedirects: number\n tabBarPathSet: ReadonlySet<string>\n resolveWithCodec: (to: RouteLocationRaw, currentPath: string) => RouteLocationNormalizedLoaded\n executeNative?: boolean\n allowSameLocation?: boolean\n}\n\nexport async function navigateWithTarget(options: NavigateWithTargetOptions): Promise<NavigationRunResult> {\n const {\n mode,\n target,\n from,\n nativeRouter,\n routeResolveCodec,\n namedRouteLookup,\n beforeEachGuards,\n beforeResolveGuards,\n maxRedirects,\n tabBarPathSet,\n resolveWithCodec,\n executeNative = true,\n allowSameLocation = false,\n } = options\n let currentTarget = target\n let currentMode: Exclude<NavigationMode, 'back'> = mode\n let redirectCount = 0\n\n while (true) {\n const tabBarTarget = tabBarPathSet.has(currentTarget.path)\n const sameNativeLocation = createNativeRouteUrl(currentTarget, routeResolveCodec.stringifyQuery)\n === createNativeRouteUrl(from, routeResolveCodec.stringifyQuery)\n if (sameNativeLocation && currentTarget.hash !== from.hash) {\n return createNavigationRunResult(currentMode, from, currentTarget, createHashOnlyNavigationFailure(currentTarget, from))\n }\n\n const duplicated = !allowSameLocation && (tabBarTarget\n ? currentTarget.path === from.path\n : currentTarget.fullPath === from.fullPath)\n if (duplicated) {\n return createNavigationRunResult(currentMode, from, currentTarget, createDuplicatedFailure(currentTarget, from))\n }\n\n if (tabBarTarget && hasLocationQuery(currentTarget.query)) {\n return createNavigationRunResult(currentMode, from, currentTarget, createTabBarQueryFailure(currentTarget, from))\n }\n\n const beforeEachResult = await runNavigationGuards(beforeEachGuards, {\n mode: currentMode,\n to: currentTarget,\n from,\n nativeRouter: nativeRouter as any,\n }, resolveWithCodec)\n\n if (beforeEachResult.status === 'failure') {\n return createNavigationRunResult(currentMode, from, currentTarget, beforeEachResult.failure)\n }\n if (beforeEachResult.status === 'redirect') {\n const redirectedTarget = beforeEachResult.target\n const redirectedMode = beforeEachResult.replace === true\n ? 'replace'\n : beforeEachResult.replace === false\n ? 'push'\n : currentMode\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n continue\n }\n }\n\n const matchedRouteResult = resolveMatchedRouteRecord(currentTarget, namedRouteLookup)\n const matchedRouteRecords = matchedRouteResult?.matchedRecords ?? []\n let redirectedByRouteRecord = false\n for (const matchedRouteRecord of matchedRouteRecords) {\n if (matchedRouteRecord.redirect === undefined) {\n continue\n }\n let redirectedByRecord: { target: RouteLocationNormalizedLoaded, replace?: boolean }\n try {\n redirectedByRecord = await resolveRouteRecordRedirect(\n matchedRouteRecord.redirect,\n currentTarget,\n from,\n resolveWithCodec,\n )\n }\n catch (error) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createNavigationFailure(NavigationFailureType.aborted, currentTarget, from, error),\n )\n }\n\n const redirectedMode = redirectedByRecord.replace === false ? 'push' : 'replace'\n const redirectedTarget = redirectedByRecord.target\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n redirectedByRouteRecord = true\n break\n }\n }\n if (redirectedByRouteRecord) {\n continue\n }\n\n let redirectedByBeforeEnter = false\n for (const matchedRouteRecord of matchedRouteRecords) {\n if (matchedRouteRecord.beforeEnterGuards.length === 0) {\n continue\n }\n const beforeEnterResult = await runNavigationGuards(new Set(matchedRouteRecord.beforeEnterGuards), {\n mode: currentMode,\n to: currentTarget,\n from,\n nativeRouter: nativeRouter as any,\n }, resolveWithCodec)\n\n if (beforeEnterResult.status === 'failure') {\n return createNavigationRunResult(currentMode, from, currentTarget, beforeEnterResult.failure)\n }\n if (beforeEnterResult.status === 'redirect') {\n const redirectedTarget = beforeEnterResult.target\n const redirectedMode = beforeEnterResult.replace === true\n ? 'replace'\n : beforeEnterResult.replace === false\n ? 'push'\n : currentMode\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n redirectedByBeforeEnter = true\n break\n }\n }\n }\n if (redirectedByBeforeEnter) {\n continue\n }\n\n const beforeResolveResult = await runNavigationGuards(beforeResolveGuards, {\n mode: currentMode,\n to: currentTarget,\n from,\n nativeRouter: nativeRouter as any,\n }, resolveWithCodec)\n\n if (beforeResolveResult.status === 'failure') {\n return createNavigationRunResult(currentMode, from, currentTarget, beforeResolveResult.failure)\n }\n if (beforeResolveResult.status === 'redirect') {\n const redirectedTarget = beforeResolveResult.target\n const redirectedMode = beforeResolveResult.replace === true\n ? 'replace'\n : beforeResolveResult.replace === false\n ? 'push'\n : currentMode\n if (redirectedTarget.fullPath !== currentTarget.fullPath || redirectedMode !== currentMode) {\n applyRedirectedFrom(redirectedTarget, currentTarget)\n currentTarget = redirectedTarget\n currentMode = redirectedMode\n redirectCount += 1\n if (redirectCount > maxRedirects) {\n return createNavigationRunResult(\n currentMode,\n from,\n currentTarget,\n createTooManyRedirectsFailure(currentTarget, from, maxRedirects),\n )\n }\n continue\n }\n }\n\n if (!executeNative) {\n return createNavigationRunResult(currentMode, from, currentTarget)\n }\n\n if (tabBarTarget) {\n const result = await executeNavigationMethod(\n nativeRouter.switchTab as (options: Record<string, any>) => unknown,\n { url: createAbsoluteRoutePath(currentTarget.path) },\n currentTarget,\n from,\n )\n if (isNavigationFailure(result)) {\n return createNavigationRunResult(currentMode, from, currentTarget, result)\n }\n return createNavigationRunResult(currentMode, from, currentTarget)\n }\n\n const nativeMethod = currentMode === 'push'\n ? nativeRouter.navigateTo\n : nativeRouter.redirectTo\n const result = await executeNavigationMethod(\n nativeMethod as (options: Record<string, any>) => unknown,\n { url: createNativeRouteUrl(currentTarget, routeResolveCodec.stringifyQuery) },\n currentTarget,\n from,\n )\n if (isNavigationFailure(result)) {\n return createNavigationRunResult(currentMode, from, currentTarget, result)\n }\n return createNavigationRunResult(currentMode, from, currentTarget)\n }\n}\n"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.mjs","names":[],"sources":["../../../src/router/types.ts"],"sourcesContent":["import type {\n SetupContextRouter,\n TypedRouterTabBarUrl,\n} from '../runtime/types/props'\n\nexport type LocationQueryValue = string | null\nexport type LocationQueryValueRaw = LocationQueryValue | number | boolean | undefined\nexport type LocationQuery = Record<string, LocationQueryValue | LocationQueryValue[]>\nexport type LocationQueryRaw = Record<string, LocationQueryValueRaw | LocationQueryValueRaw[]>\nexport type RouteParamValue = string\nexport type RouteParamValueRaw = RouteParamValue | number | boolean | null | undefined\nexport type RouteParams = Record<string, RouteParamValue | RouteParamValue[]>\nexport type RouteParamsRaw = Record<string, RouteParamValueRaw | RouteParamValueRaw[]>\nexport type RouteParamsMode = 'loose' | 'strict'\nexport type RouteQueryParser = (search: string) => LocationQueryRaw | LocationQuery\nexport type RouteQueryStringifier = (query: LocationQueryRaw | LocationQuery) => string\nexport type RouteMeta = Record<string, unknown>\nexport interface NamedRouteRecord {\n name: string\n path: string\n}\nexport interface RouteRecordInput {\n name?: string\n path: string\n meta?: RouteMeta\n alias?: string | readonly string[]\n children?: readonly RouteRecordInput[]\n beforeEnter?: NavigationGuard | readonly NavigationGuard[]\n redirect?: RouteRecordRedirect\n}\nexport type NamedRoutes = Readonly<Record<string, string>> | readonly RouteRecordRaw[]\n\nexport type RouteLocationRaw = string | {\n path?: string\n fullPath?: string\n query?: LocationQueryRaw\n hash?: string\n name?: string\n params?: RouteParamsRaw\n}\n\nexport interface RouteLocationNormalizedLoaded {\n path: string\n fullPath: string\n query: LocationQuery\n hash: string\n name?: string\n meta?: RouteMeta\n href?: string\n matched?: readonly RouteRecordMatched[]\n redirectedFrom?: RouteLocationRedirectedFrom\n params: RouteParams\n}\n\nexport const NavigationFailureType = {\n unknown: 1,\n aborted: 4,\n cancelled: 8,\n duplicated: 16,\n} as const\n\nexport type NavigationFailureTypeValue = (typeof NavigationFailureType)[keyof typeof NavigationFailureType]\n\nexport interface NavigationFailure extends Error {\n readonly __wevuNavigationFailure: true\n readonly type: NavigationFailureTypeValue\n readonly to?: RouteLocationNormalizedLoaded\n readonly from?: RouteLocationNormalizedLoaded\n readonly cause?: unknown\n}\n\nexport type NavigationMode = 'push' | 'replace' | 'back'\nexport interface NavigationRedirect {\n to: RouteLocationRaw\n replace?: boolean\n}\nexport type RouteRecordRedirect = RouteLocationRaw | NavigationRedirect | ((\n to: RouteLocationNormalizedLoaded,\n from: RouteLocationNormalizedLoaded,\n) => RouteLocationRaw | NavigationRedirect | Promise<RouteLocationRaw | NavigationRedirect>)\nexport interface RouteRecordRaw extends Omit<RouteRecordInput, 'name' | 'children'>, NamedRouteRecord {\n children?: readonly RouteRecordRaw[]\n}\n\nexport interface RouteRecordMatched {\n name: string\n path: string\n aliasPath?: string\n meta?: RouteMeta\n}\n\nexport interface RouteLocationRedirectedFrom {\n path: string\n fullPath: string\n query: LocationQuery\n hash: string\n name?: string\n meta?: RouteMeta\n href?: string\n matched?: readonly RouteRecordMatched[]\n params: RouteParams\n}\n\nexport type NavigationGuardResult = void | boolean | NavigationFailure | RouteLocationRaw | NavigationRedirect\nexport type NavigationGuard = (\n to: RouteLocationNormalizedLoaded | undefined,\n from: RouteLocationNormalizedLoaded,\n context?: NavigationGuardContext,\n) => NavigationGuardResult | Promise<NavigationGuardResult>\nexport type NavigationAfterEach = (\n to: RouteLocationNormalizedLoaded | undefined,\n from: RouteLocationNormalizedLoaded,\n failure?: NavigationFailure,\n context?: NavigationAfterEachContext,\n) => void | Promise<void>\n\nexport interface NavigationGuardContext {\n readonly mode: NavigationMode\n readonly to?: RouteLocationNormalizedLoaded\n readonly from: RouteLocationNormalizedLoaded\n readonly nativeRouter: SetupContextRouter\n}\n\nexport interface NavigationAfterEachContext {\n readonly mode: NavigationMode\n readonly to?: RouteLocationNormalizedLoaded\n readonly from: RouteLocationNormalizedLoaded\n readonly nativeRouter: SetupContextRouter\n readonly failure?: NavigationFailure\n}\n\nexport interface NavigationErrorContext {\n readonly mode: NavigationMode\n readonly to?: RouteLocationNormalizedLoaded\n readonly from: RouteLocationNormalizedLoaded\n readonly nativeRouter: SetupContextRouter\n readonly failure: NavigationFailure\n}\n\nexport type NavigationErrorHandler = (\n error: unknown,\n context: NavigationErrorContext,\n) => void | Promise<void>\n\nexport interface UseRouterOptions {\n tabBarEntries?: readonly (TypedRouterTabBarUrl | string)[]\n /**\n * Vue Router 对齐入口:推荐使用 `routes`\n */\n routes?: readonly RouteRecordInput[]\n /**\n * 兼容入口:支持对象 map 或路由记录数组\n */\n namedRoutes?: NamedRoutes\n paramsMode?: RouteParamsMode\n maxRedirects?: number\n parseQuery?: RouteQueryParser\n stringifyQuery?: RouteQueryStringifier\n /**\n * 异常型导航失败时是否以 Promise reject 抛出失败对象。\n *\n * - `true`:更贴近 Vue Router 心智(默认)\n * - `false`:始终以返回值形式携带失败对象\n */\n rejectOnError?: boolean\n}\n\nexport interface RouterNavigation {\n readonly nativeRouter: SetupContextRouter\n readonly options: Readonly<UseRouterOptions>\n readonly currentRoute: Readonly<RouteLocationNormalizedLoaded>\n install: (app?: unknown) => void\n resolve: (to: RouteLocationRaw) => RouteLocationNormalizedLoaded\n isReady: () => Promise<void>\n push: (to: RouteLocationRaw) => Promise<void | NavigationFailure>\n replace: (to: RouteLocationRaw) => Promise<void | NavigationFailure>\n back: (delta?: number) => Promise<void | NavigationFailure>\n go: (delta: number) => Promise<void | NavigationFailure>\n forward: () => Promise<void | NavigationFailure>\n hasRoute: (name: string) => boolean\n getRoutes: () => readonly RouteRecordRaw[]\n addRoute: AddRoute\n removeRoute: (name: string) => void\n clearRoutes: () => void\n beforeEach: (guard: NavigationGuard) => () => void\n beforeResolve: (guard: NavigationGuard) => () => void\n afterEach: (hook: NavigationAfterEach) => () => void\n onError: (handler: NavigationErrorHandler) => () => void\n}\n\nexport interface AddRoute {\n (route: RouteRecordRaw): () => void\n (parentName: string, route: RouteRecordRaw): () => void\n}\n"],"mappings":";AAsDA,MAAa,wBAAwB;CACnC,SAAS;CACT,SAAS;CACT,WAAW;CACX,YAAY;AACd"}
|
|
1
|
+
{"version":3,"file":"types.mjs","names":[],"sources":["../../../src/router/types.ts"],"sourcesContent":["import type {\n SetupContextRouter,\n TypedRouterTabBarUrl,\n} from '../runtime/types/props'\n\nexport type LocationQueryValue = string | null\nexport type LocationQueryValueRaw = LocationQueryValue | number | boolean | undefined\nexport type LocationQuery = Record<string, LocationQueryValue | LocationQueryValue[]>\nexport type LocationQueryRaw = Record<string, LocationQueryValueRaw | LocationQueryValueRaw[]>\nexport type RouteParamValue = string\nexport type RouteParamValueRaw = RouteParamValue | number | boolean | null | undefined\nexport type RouteParams = Record<string, RouteParamValue | RouteParamValue[]>\nexport type RouteParamsRaw = Record<string, RouteParamValueRaw | RouteParamValueRaw[]>\nexport type RouteParamsMode = 'loose' | 'strict'\nexport type RouteQueryParser = (search: string) => LocationQueryRaw | LocationQuery\nexport type RouteQueryStringifier = (query: LocationQueryRaw | LocationQuery) => string\nexport type RouteMeta = Record<string, unknown>\nexport interface NamedRouteRecord {\n name: string\n path: string\n}\nexport interface RouteRecordInput {\n name?: string\n path: string\n meta?: RouteMeta\n alias?: string | readonly string[]\n children?: readonly RouteRecordInput[]\n beforeEnter?: NavigationGuard | readonly NavigationGuard[]\n redirect?: RouteRecordRedirect\n}\nexport type NamedRoutes = Readonly<Record<string, string>> | readonly RouteRecordRaw[]\n\nexport type RouteLocationRaw = string | {\n path?: string\n fullPath?: string\n query?: LocationQueryRaw\n hash?: string\n name?: string\n params?: RouteParamsRaw\n}\n\nexport interface RouteLocationNormalizedLoaded {\n path: string\n fullPath: string\n query: LocationQuery\n hash: string\n name?: string\n meta?: RouteMeta\n href?: string\n matched?: readonly RouteRecordMatched[]\n redirectedFrom?: RouteLocationRedirectedFrom\n params: RouteParams\n}\n\nexport const NavigationFailureType = {\n unknown: 1,\n aborted: 4,\n cancelled: 8,\n duplicated: 16,\n} as const\n\nexport type NavigationFailureTypeValue = (typeof NavigationFailureType)[keyof typeof NavigationFailureType]\n\nexport interface NavigationFailure extends Error {\n readonly __wevuNavigationFailure: true\n readonly type: NavigationFailureTypeValue\n readonly to?: RouteLocationNormalizedLoaded\n readonly from?: RouteLocationNormalizedLoaded\n readonly cause?: unknown\n}\n\nexport type NavigationMode = 'push' | 'replace' | 'back'\nexport type InitialNavigationMode = 'eager' | 'blocking'\nexport interface NavigationRedirect {\n to: RouteLocationRaw\n replace?: boolean\n}\nexport type RouteRecordRedirect = RouteLocationRaw | NavigationRedirect | ((\n to: RouteLocationNormalizedLoaded,\n from: RouteLocationNormalizedLoaded,\n) => RouteLocationRaw | NavigationRedirect | Promise<RouteLocationRaw | NavigationRedirect>)\nexport interface RouteRecordRaw extends Omit<RouteRecordInput, 'name' | 'children'>, NamedRouteRecord {\n children?: readonly RouteRecordRaw[]\n}\n\nexport interface RouteRecordMatched {\n name: string\n path: string\n aliasPath?: string\n meta?: RouteMeta\n}\n\nexport interface RouteLocationRedirectedFrom {\n path: string\n fullPath: string\n query: LocationQuery\n hash: string\n name?: string\n meta?: RouteMeta\n href?: string\n matched?: readonly RouteRecordMatched[]\n params: RouteParams\n}\n\nexport type NavigationGuardResult = void | boolean | NavigationFailure | RouteLocationRaw | NavigationRedirect\nexport type NavigationGuard = (\n to: RouteLocationNormalizedLoaded | undefined,\n from: RouteLocationNormalizedLoaded,\n context?: NavigationGuardContext,\n) => NavigationGuardResult | Promise<NavigationGuardResult>\nexport type NavigationAfterEach = (\n to: RouteLocationNormalizedLoaded | undefined,\n from: RouteLocationNormalizedLoaded,\n failure?: NavigationFailure,\n context?: NavigationAfterEachContext,\n) => void | Promise<void>\n\nexport interface NavigationGuardContext {\n readonly mode: NavigationMode\n readonly to?: RouteLocationNormalizedLoaded\n readonly from: RouteLocationNormalizedLoaded\n readonly nativeRouter: SetupContextRouter\n}\n\nexport interface NavigationAfterEachContext {\n readonly mode: NavigationMode\n readonly to?: RouteLocationNormalizedLoaded\n readonly from: RouteLocationNormalizedLoaded\n readonly nativeRouter: SetupContextRouter\n readonly failure?: NavigationFailure\n}\n\nexport interface NavigationErrorContext {\n readonly mode: NavigationMode\n readonly to?: RouteLocationNormalizedLoaded\n readonly from: RouteLocationNormalizedLoaded\n readonly nativeRouter: SetupContextRouter\n readonly failure: NavigationFailure\n}\n\nexport type NavigationErrorHandler = (\n error: unknown,\n context: NavigationErrorContext,\n) => void | Promise<void>\n\nexport interface UseRouterOptions {\n tabBarEntries?: readonly (TypedRouterTabBarUrl | string)[]\n /**\n * Vue Router 对齐入口:推荐使用 `routes`\n */\n routes?: readonly RouteRecordInput[]\n /**\n * 兼容入口:支持对象 map 或路由记录数组\n */\n namedRoutes?: NamedRoutes\n paramsMode?: RouteParamsMode\n maxRedirects?: number\n /**\n * 首屏导航守卫模式。默认立即挂载页面,只有明确配置 `blocking` 时才等待守卫完成。\n */\n initialNavigationMode?: InitialNavigationMode\n /**\n * blocking 首屏导航守卫的最大等待时间(毫秒),超时后放行页面挂载。\n */\n initialNavigationTimeout?: number\n parseQuery?: RouteQueryParser\n stringifyQuery?: RouteQueryStringifier\n /**\n * 异常型导航失败时是否以 Promise reject 抛出失败对象。\n *\n * - `true`:更贴近 Vue Router 心智(默认)\n * - `false`:始终以返回值形式携带失败对象\n */\n rejectOnError?: boolean\n}\n\nexport interface RouterNavigation {\n readonly nativeRouter: SetupContextRouter\n readonly options: Readonly<UseRouterOptions>\n readonly currentRoute: Readonly<RouteLocationNormalizedLoaded>\n install: (app?: unknown) => void\n resolve: (to: RouteLocationRaw) => RouteLocationNormalizedLoaded\n isReady: () => Promise<void>\n push: (to: RouteLocationRaw) => Promise<void | NavigationFailure>\n replace: (to: RouteLocationRaw) => Promise<void | NavigationFailure>\n back: (delta?: number) => Promise<void | NavigationFailure>\n go: (delta: number) => Promise<void | NavigationFailure>\n forward: () => Promise<void | NavigationFailure>\n hasRoute: (name: string) => boolean\n getRoutes: () => readonly RouteRecordRaw[]\n addRoute: AddRoute\n removeRoute: (name: string) => void\n clearRoutes: () => void\n beforeEach: (guard: NavigationGuard) => () => void\n beforeResolve: (guard: NavigationGuard) => () => void\n afterEach: (hook: NavigationAfterEach) => () => void\n onError: (handler: NavigationErrorHandler) => () => void\n}\n\nexport interface AddRoute {\n (route: RouteRecordRaw): () => void\n (parentName: string, route: RouteRecordRaw): () => void\n}\n"],"mappings":";AAsDA,MAAa,wBAAwB;CACnC,SAAS;CACT,SAAS;CACT,WAAW;CACX,YAAY;AACd"}
|
|
@@ -1,15 +1,26 @@
|
|
|
1
1
|
import { reactive } from "../reactivity/reactive.mjs";
|
|
2
2
|
import { readonly } from "../reactivity/readonly.mjs";
|
|
3
|
+
import { getCurrentMiniProgramPages } from "../runtime/platform.mjs";
|
|
3
4
|
import { getCurrentSetupContext } from "../runtime/hooks/base.mjs";
|
|
4
5
|
import { onLoad, onReady, onRouteDone, onShow, onUnload } from "../runtime/hooks/register.mjs";
|
|
6
|
+
import { getActiveRouter } from "./instance.mjs";
|
|
5
7
|
import { registerRouteStateSyncHandler } from "./routeSync.mjs";
|
|
6
8
|
import { resolveCurrentRoute, resolvePageRoute } from "../routerInternal/location.mjs";
|
|
7
9
|
import { cloneLocationQuery, cloneRouteLocationRedirectedFrom, cloneRouteMeta, cloneRouteParams, cloneRouteRecordMatchedList } from "../routerInternal/snapshots.mjs";
|
|
8
10
|
import { useNativePageRouter as useNativePageRouter$1, useNativeRouter as useNativeRouter$1 } from "../runtime/vueCompat/router.mjs";
|
|
9
|
-
import { getActiveRouter } from "./instance.mjs";
|
|
10
11
|
import { resolveRouteLocation } from "./resolve.mjs";
|
|
11
12
|
|
|
12
13
|
//#region src/router/useRoute.ts
|
|
14
|
+
function isPageLikeInstance(instance) {
|
|
15
|
+
return typeof instance.route === "string" || typeof instance.__route__ === "string";
|
|
16
|
+
}
|
|
17
|
+
function shouldSyncRouteStateForInstance(instance, isPageController, payload) {
|
|
18
|
+
if ((payload === null || payload === void 0 ? void 0 : payload.source) === "router") return true;
|
|
19
|
+
if (!isPageController) return true;
|
|
20
|
+
if (payload === null || payload === void 0 ? void 0 : payload.page) return payload.page === instance;
|
|
21
|
+
const pages = getCurrentMiniProgramPages();
|
|
22
|
+
return pages[pages.length - 1] === instance;
|
|
23
|
+
}
|
|
13
24
|
function applyRouteState(routeState, nextRoute) {
|
|
14
25
|
routeState.path = nextRoute.path;
|
|
15
26
|
routeState.fullPath = nextRoute.fullPath;
|
|
@@ -37,6 +48,7 @@ function createRouteStateController(options = {}) {
|
|
|
37
48
|
return (_getActiveRouter$reso = (_getActiveRouter = getActiveRouter()) === null || _getActiveRouter === void 0 ? void 0 : _getActiveRouter.resolve(route)) !== null && _getActiveRouter$reso !== void 0 ? _getActiveRouter$reso : route;
|
|
38
49
|
});
|
|
39
50
|
const currentRoute = resolveRoute(resolveCurrentRoute(void 0, fallbackPage));
|
|
51
|
+
const isPageController = isPageLikeInstance(fallbackPage) || getCurrentMiniProgramPages().includes(fallbackPage);
|
|
40
52
|
const routeState = reactive({
|
|
41
53
|
path: currentRoute.path,
|
|
42
54
|
fullPath: currentRoute.fullPath,
|
|
@@ -66,6 +78,7 @@ function createRouteStateController(options = {}) {
|
|
|
66
78
|
syncRoute();
|
|
67
79
|
});
|
|
68
80
|
const unregisterRouteStateSync = registerRouteStateSyncHandler((payload) => {
|
|
81
|
+
if (!shouldSyncRouteStateForInstance(fallbackPage, isPageController, payload)) return;
|
|
69
82
|
if (payload === null || payload === void 0 ? void 0 : payload.route) {
|
|
70
83
|
syncRoute(void 0, payload.route, payload);
|
|
71
84
|
return;
|