@angular/router 14.1.0-next.0 → 14.1.0-next.3
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/esm2020/src/apply_redirects.mjs +30 -56
- package/esm2020/src/components/empty_outlet.mjs +3 -3
- package/esm2020/src/directives/router_link.mjs +6 -6
- package/esm2020/src/directives/router_link_active.mjs +3 -3
- package/esm2020/src/directives/router_outlet.mjs +8 -5
- package/esm2020/src/index.mjs +1 -1
- package/esm2020/src/models.mjs +1 -1
- package/esm2020/src/operators/check_guards.mjs +48 -4
- package/esm2020/src/operators/recognize.mjs +3 -3
- package/esm2020/src/page_title_strategy.mjs +3 -3
- package/esm2020/src/private_export.mjs +2 -2
- package/esm2020/src/recognize.mjs +133 -110
- package/esm2020/src/router.mjs +8 -37
- package/esm2020/src/router_config_loader.mjs +3 -3
- package/esm2020/src/router_module.mjs +151 -136
- package/esm2020/src/router_preloader.mjs +16 -4
- package/esm2020/src/router_scroller.mjs +6 -5
- package/esm2020/src/utils/config_matching.mjs +16 -2
- package/esm2020/src/utils/type_guards.mjs +4 -1
- package/esm2020/src/version.mjs +1 -1
- package/esm2020/testing/src/router_testing_module.mjs +8 -8
- package/fesm2015/router.mjs +840 -778
- package/fesm2015/router.mjs.map +1 -1
- package/fesm2015/testing.mjs +8 -8
- package/fesm2015/testing.mjs.map +1 -1
- package/fesm2015/upgrade.mjs +1 -1
- package/fesm2020/router.mjs +835 -779
- package/fesm2020/router.mjs.map +1 -1
- package/fesm2020/testing.mjs +8 -8
- package/fesm2020/testing.mjs.map +1 -1
- package/fesm2020/upgrade.mjs +1 -1
- package/index.d.ts +117 -1
- package/package.json +4 -4
- package/testing/index.d.ts +2 -2
- package/upgrade/index.d.ts +1 -1
package/fesm2020/router.mjs
CHANGED
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* @license Angular v14.1.0-next.
|
|
2
|
+
* @license Angular v14.1.0-next.3
|
|
3
3
|
* (c) 2010-2022 Google LLC. https://angular.io/
|
|
4
4
|
* License: MIT
|
|
5
5
|
*/
|
|
6
6
|
|
|
7
7
|
import * as i0 from '@angular/core';
|
|
8
|
-
import { ɵisObservable, ɵisPromise, EventEmitter, Directive, Attribute, Output, Component, createEnvironmentInjector, ɵisStandalone, ComponentFactoryResolver, InjectionToken, InjectFlags, NgModuleFactory, Injectable, NgModuleRef, ɵConsole, NgZone, ɵcoerceToBoolean, Input, HostListener, HostBinding, Optional, ContentChildren, Injector, Compiler, NgProbeToken, ANALYZE_FOR_ENTRY_COMPONENTS, SkipSelf,
|
|
9
|
-
import { from, of, BehaviorSubject, combineLatest,
|
|
8
|
+
import { ɵisObservable, ɵisPromise, EventEmitter, Directive, Attribute, Output, Component, createEnvironmentInjector, ɵisStandalone, ComponentFactoryResolver, InjectionToken, InjectFlags, NgModuleFactory, Injectable, NgModuleRef, ɵConsole, NgZone, ɵcoerceToBoolean, Input, HostListener, HostBinding, Optional, ContentChildren, Injector, Compiler, NgProbeToken, ANALYZE_FOR_ENTRY_COMPONENTS, SkipSelf, inject, APP_INITIALIZER, APP_BOOTSTRAP_LISTENER, NgModule, Inject, ApplicationRef, ENVIRONMENT_INITIALIZER, Version } from '@angular/core';
|
|
9
|
+
import { from, of, BehaviorSubject, combineLatest, concat, defer, pipe, throwError, EmptyError, Observable, EMPTY, ConnectableObservable, Subject } from 'rxjs';
|
|
10
10
|
import * as i3 from '@angular/common';
|
|
11
|
-
import { Location, LocationStrategy,
|
|
12
|
-
import { map, switchMap, take, startWith, scan, filter,
|
|
11
|
+
import { Location, LocationStrategy, HashLocationStrategy, PathLocationStrategy, ViewportScroller, LOCATION_INITIALIZED } from '@angular/common';
|
|
12
|
+
import { map, switchMap, take, startWith, scan, filter, mergeMap, first, concatMap, tap, catchError, last as last$1, takeWhile, defaultIfEmpty, takeLast, mapTo, finalize, refCount, mergeAll } from 'rxjs/operators';
|
|
13
13
|
import * as i1 from '@angular/platform-browser';
|
|
14
14
|
|
|
15
15
|
/**
|
|
@@ -2391,7 +2391,10 @@ class RouterOutlet {
|
|
|
2391
2391
|
}
|
|
2392
2392
|
/** @nodoc */
|
|
2393
2393
|
ngOnDestroy() {
|
|
2394
|
-
this.
|
|
2394
|
+
// Ensure that the registered outlet is this one before removing it on the context.
|
|
2395
|
+
if (this.parentContexts.getContext(this.name)?.outlet === this) {
|
|
2396
|
+
this.parentContexts.onChildOutletDestroyed(this.name);
|
|
2397
|
+
}
|
|
2395
2398
|
}
|
|
2396
2399
|
/** @nodoc */
|
|
2397
2400
|
ngOnInit() {
|
|
@@ -2489,9 +2492,9 @@ class RouterOutlet {
|
|
|
2489
2492
|
this.activateEvents.emit(this.activated.instance);
|
|
2490
2493
|
}
|
|
2491
2494
|
}
|
|
2492
|
-
RouterOutlet.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
2493
|
-
RouterOutlet.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.
|
|
2494
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
2495
|
+
RouterOutlet.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterOutlet, deps: [{ token: ChildrenOutletContexts }, { token: i0.ViewContainerRef }, { token: 'name', attribute: true }, { token: i0.ChangeDetectorRef }, { token: i0.EnvironmentInjector }], target: i0.ɵɵFactoryTarget.Directive });
|
|
2496
|
+
RouterOutlet.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.3", type: RouterOutlet, selector: "router-outlet", outputs: { activateEvents: "activate", deactivateEvents: "deactivate", attachEvents: "attach", detachEvents: "detach" }, exportAs: ["outlet"], ngImport: i0 });
|
|
2497
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterOutlet, decorators: [{
|
|
2495
2498
|
type: Directive,
|
|
2496
2499
|
args: [{ selector: 'router-outlet', exportAs: 'outlet' }]
|
|
2497
2500
|
}], ctorParameters: function () { return [{ type: ChildrenOutletContexts }, { type: i0.ViewContainerRef }, { type: undefined, decorators: [{
|
|
@@ -2548,9 +2551,9 @@ function isComponentFactoryResolver(item) {
|
|
|
2548
2551
|
*/
|
|
2549
2552
|
class ɵEmptyOutletComponent {
|
|
2550
2553
|
}
|
|
2551
|
-
ɵEmptyOutletComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
2552
|
-
ɵEmptyOutletComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.1.0-next.
|
|
2553
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
2554
|
+
ɵEmptyOutletComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: ɵEmptyOutletComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
2555
|
+
ɵEmptyOutletComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.1.0-next.3", type: ɵEmptyOutletComponent, selector: "ng-component", ngImport: i0, template: `<router-outlet></router-outlet>`, isInline: true, dependencies: [{ kind: "directive", type: RouterOutlet, selector: "router-outlet", outputs: ["activate", "deactivate", "attach", "detach"], exportAs: ["outlet"] }] });
|
|
2556
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: ɵEmptyOutletComponent, decorators: [{
|
|
2554
2557
|
type: Component,
|
|
2555
2558
|
args: [{ template: `<router-outlet></router-outlet>` }]
|
|
2556
2559
|
}] });
|
|
@@ -2920,6 +2923,146 @@ class ActivateRoutes {
|
|
|
2920
2923
|
}
|
|
2921
2924
|
}
|
|
2922
2925
|
|
|
2926
|
+
/**
|
|
2927
|
+
* @license
|
|
2928
|
+
* Copyright Google LLC All Rights Reserved.
|
|
2929
|
+
*
|
|
2930
|
+
* Use of this source code is governed by an MIT-style license that can be
|
|
2931
|
+
* found in the LICENSE file at https://angular.io/license
|
|
2932
|
+
*/
|
|
2933
|
+
class CanActivate {
|
|
2934
|
+
constructor(path) {
|
|
2935
|
+
this.path = path;
|
|
2936
|
+
this.route = this.path[this.path.length - 1];
|
|
2937
|
+
}
|
|
2938
|
+
}
|
|
2939
|
+
class CanDeactivate {
|
|
2940
|
+
constructor(component, route) {
|
|
2941
|
+
this.component = component;
|
|
2942
|
+
this.route = route;
|
|
2943
|
+
}
|
|
2944
|
+
}
|
|
2945
|
+
function getAllRouteGuards(future, curr, parentContexts) {
|
|
2946
|
+
const futureRoot = future._root;
|
|
2947
|
+
const currRoot = curr ? curr._root : null;
|
|
2948
|
+
return getChildRouteGuards(futureRoot, currRoot, parentContexts, [futureRoot.value]);
|
|
2949
|
+
}
|
|
2950
|
+
function getCanActivateChild(p) {
|
|
2951
|
+
const canActivateChild = p.routeConfig ? p.routeConfig.canActivateChild : null;
|
|
2952
|
+
if (!canActivateChild || canActivateChild.length === 0)
|
|
2953
|
+
return null;
|
|
2954
|
+
return { node: p, guards: canActivateChild };
|
|
2955
|
+
}
|
|
2956
|
+
function getToken(token, snapshot, fallbackInjector) {
|
|
2957
|
+
const routeInjector = getClosestRouteInjector(snapshot);
|
|
2958
|
+
const injector = routeInjector ?? fallbackInjector;
|
|
2959
|
+
return injector.get(token);
|
|
2960
|
+
}
|
|
2961
|
+
function getChildRouteGuards(futureNode, currNode, contexts, futurePath, checks = {
|
|
2962
|
+
canDeactivateChecks: [],
|
|
2963
|
+
canActivateChecks: []
|
|
2964
|
+
}) {
|
|
2965
|
+
const prevChildren = nodeChildrenAsMap(currNode);
|
|
2966
|
+
// Process the children of the future route
|
|
2967
|
+
futureNode.children.forEach(c => {
|
|
2968
|
+
getRouteGuards(c, prevChildren[c.value.outlet], contexts, futurePath.concat([c.value]), checks);
|
|
2969
|
+
delete prevChildren[c.value.outlet];
|
|
2970
|
+
});
|
|
2971
|
+
// Process any children left from the current route (not active for the future route)
|
|
2972
|
+
forEach(prevChildren, (v, k) => deactivateRouteAndItsChildren(v, contexts.getContext(k), checks));
|
|
2973
|
+
return checks;
|
|
2974
|
+
}
|
|
2975
|
+
function getRouteGuards(futureNode, currNode, parentContexts, futurePath, checks = {
|
|
2976
|
+
canDeactivateChecks: [],
|
|
2977
|
+
canActivateChecks: []
|
|
2978
|
+
}) {
|
|
2979
|
+
const future = futureNode.value;
|
|
2980
|
+
const curr = currNode ? currNode.value : null;
|
|
2981
|
+
const context = parentContexts ? parentContexts.getContext(futureNode.value.outlet) : null;
|
|
2982
|
+
// reusing the node
|
|
2983
|
+
if (curr && future.routeConfig === curr.routeConfig) {
|
|
2984
|
+
const shouldRun = shouldRunGuardsAndResolvers(curr, future, future.routeConfig.runGuardsAndResolvers);
|
|
2985
|
+
if (shouldRun) {
|
|
2986
|
+
checks.canActivateChecks.push(new CanActivate(futurePath));
|
|
2987
|
+
}
|
|
2988
|
+
else {
|
|
2989
|
+
// we need to set the data
|
|
2990
|
+
future.data = curr.data;
|
|
2991
|
+
future._resolvedData = curr._resolvedData;
|
|
2992
|
+
}
|
|
2993
|
+
// If we have a component, we need to go through an outlet.
|
|
2994
|
+
if (future.component) {
|
|
2995
|
+
getChildRouteGuards(futureNode, currNode, context ? context.children : null, futurePath, checks);
|
|
2996
|
+
// if we have a componentless route, we recurse but keep the same outlet map.
|
|
2997
|
+
}
|
|
2998
|
+
else {
|
|
2999
|
+
getChildRouteGuards(futureNode, currNode, parentContexts, futurePath, checks);
|
|
3000
|
+
}
|
|
3001
|
+
if (shouldRun && context && context.outlet && context.outlet.isActivated) {
|
|
3002
|
+
checks.canDeactivateChecks.push(new CanDeactivate(context.outlet.component, curr));
|
|
3003
|
+
}
|
|
3004
|
+
}
|
|
3005
|
+
else {
|
|
3006
|
+
if (curr) {
|
|
3007
|
+
deactivateRouteAndItsChildren(currNode, context, checks);
|
|
3008
|
+
}
|
|
3009
|
+
checks.canActivateChecks.push(new CanActivate(futurePath));
|
|
3010
|
+
// If we have a component, we need to go through an outlet.
|
|
3011
|
+
if (future.component) {
|
|
3012
|
+
getChildRouteGuards(futureNode, null, context ? context.children : null, futurePath, checks);
|
|
3013
|
+
// if we have a componentless route, we recurse but keep the same outlet map.
|
|
3014
|
+
}
|
|
3015
|
+
else {
|
|
3016
|
+
getChildRouteGuards(futureNode, null, parentContexts, futurePath, checks);
|
|
3017
|
+
}
|
|
3018
|
+
}
|
|
3019
|
+
return checks;
|
|
3020
|
+
}
|
|
3021
|
+
function shouldRunGuardsAndResolvers(curr, future, mode) {
|
|
3022
|
+
if (typeof mode === 'function') {
|
|
3023
|
+
return mode(curr, future);
|
|
3024
|
+
}
|
|
3025
|
+
switch (mode) {
|
|
3026
|
+
case 'pathParamsChange':
|
|
3027
|
+
return !equalPath(curr.url, future.url);
|
|
3028
|
+
case 'pathParamsOrQueryParamsChange':
|
|
3029
|
+
return !equalPath(curr.url, future.url) ||
|
|
3030
|
+
!shallowEqual(curr.queryParams, future.queryParams);
|
|
3031
|
+
case 'always':
|
|
3032
|
+
return true;
|
|
3033
|
+
case 'paramsOrQueryParamsChange':
|
|
3034
|
+
return !equalParamsAndUrlSegments(curr, future) ||
|
|
3035
|
+
!shallowEqual(curr.queryParams, future.queryParams);
|
|
3036
|
+
case 'paramsChange':
|
|
3037
|
+
default:
|
|
3038
|
+
return !equalParamsAndUrlSegments(curr, future);
|
|
3039
|
+
}
|
|
3040
|
+
}
|
|
3041
|
+
function deactivateRouteAndItsChildren(route, context, checks) {
|
|
3042
|
+
const children = nodeChildrenAsMap(route);
|
|
3043
|
+
const r = route.value;
|
|
3044
|
+
forEach(children, (node, childName) => {
|
|
3045
|
+
if (!r.component) {
|
|
3046
|
+
deactivateRouteAndItsChildren(node, context, checks);
|
|
3047
|
+
}
|
|
3048
|
+
else if (context) {
|
|
3049
|
+
deactivateRouteAndItsChildren(node, context.children.getContext(childName), checks);
|
|
3050
|
+
}
|
|
3051
|
+
else {
|
|
3052
|
+
deactivateRouteAndItsChildren(node, null, checks);
|
|
3053
|
+
}
|
|
3054
|
+
});
|
|
3055
|
+
if (!r.component) {
|
|
3056
|
+
checks.canDeactivateChecks.push(new CanDeactivate(null, r));
|
|
3057
|
+
}
|
|
3058
|
+
else if (context && context.outlet && context.outlet.isActivated) {
|
|
3059
|
+
checks.canDeactivateChecks.push(new CanDeactivate(context.outlet.component, r));
|
|
3060
|
+
}
|
|
3061
|
+
else {
|
|
3062
|
+
checks.canDeactivateChecks.push(new CanDeactivate(null, r));
|
|
3063
|
+
}
|
|
3064
|
+
}
|
|
3065
|
+
|
|
2923
3066
|
/**
|
|
2924
3067
|
* @license
|
|
2925
3068
|
* Copyright Google LLC All Rights Reserved.
|
|
@@ -2961,6 +3104,9 @@ function isCanActivateChild(guard) {
|
|
|
2961
3104
|
function isCanDeactivate(guard) {
|
|
2962
3105
|
return guard && isFunction(guard.canDeactivate);
|
|
2963
3106
|
}
|
|
3107
|
+
function isCanMatch(guard) {
|
|
3108
|
+
return guard && isFunction(guard.canMatch);
|
|
3109
|
+
}
|
|
2964
3110
|
|
|
2965
3111
|
/**
|
|
2966
3112
|
* @license
|
|
@@ -3008,92 +3154,277 @@ function prioritizedGuardValue() {
|
|
|
3008
3154
|
* Use of this source code is governed by an MIT-style license that can be
|
|
3009
3155
|
* found in the LICENSE file at https://angular.io/license
|
|
3010
3156
|
*/
|
|
3011
|
-
|
|
3012
|
-
|
|
3013
|
-
|
|
3014
|
-
|
|
3015
|
-
|
|
3016
|
-
positionalParamSegments: {}
|
|
3017
|
-
};
|
|
3018
|
-
function match(segmentGroup, route, segments) {
|
|
3019
|
-
if (route.path === '') {
|
|
3020
|
-
if (route.pathMatch === 'full' && (segmentGroup.hasChildren() || segments.length > 0)) {
|
|
3021
|
-
return { ...noMatch$1 };
|
|
3157
|
+
function checkGuards(moduleInjector, forwardEvent) {
|
|
3158
|
+
return mergeMap(t => {
|
|
3159
|
+
const { targetSnapshot, currentSnapshot, guards: { canActivateChecks, canDeactivateChecks } } = t;
|
|
3160
|
+
if (canDeactivateChecks.length === 0 && canActivateChecks.length === 0) {
|
|
3161
|
+
return of({ ...t, guardsResult: true });
|
|
3022
3162
|
}
|
|
3023
|
-
return
|
|
3024
|
-
|
|
3025
|
-
|
|
3026
|
-
|
|
3027
|
-
|
|
3028
|
-
|
|
3029
|
-
};
|
|
3030
|
-
}
|
|
3031
|
-
const matcher = route.matcher || defaultUrlMatcher;
|
|
3032
|
-
const res = matcher(segments, segmentGroup, route);
|
|
3033
|
-
if (!res)
|
|
3034
|
-
return { ...noMatch$1 };
|
|
3035
|
-
const posParams = {};
|
|
3036
|
-
forEach(res.posParams, (v, k) => {
|
|
3037
|
-
posParams[k] = v.path;
|
|
3163
|
+
return runCanDeactivateChecks(canDeactivateChecks, targetSnapshot, currentSnapshot, moduleInjector)
|
|
3164
|
+
.pipe(mergeMap(canDeactivate => {
|
|
3165
|
+
return canDeactivate && isBoolean(canDeactivate) ?
|
|
3166
|
+
runCanActivateChecks(targetSnapshot, canActivateChecks, moduleInjector, forwardEvent) :
|
|
3167
|
+
of(canDeactivate);
|
|
3168
|
+
}), map(guardsResult => ({ ...t, guardsResult })));
|
|
3038
3169
|
});
|
|
3039
|
-
const parameters = res.consumed.length > 0 ?
|
|
3040
|
-
{ ...posParams, ...res.consumed[res.consumed.length - 1].parameters } :
|
|
3041
|
-
posParams;
|
|
3042
|
-
return {
|
|
3043
|
-
matched: true,
|
|
3044
|
-
consumedSegments: res.consumed,
|
|
3045
|
-
remainingSegments: segments.slice(res.consumed.length),
|
|
3046
|
-
// TODO(atscott): investigate combining parameters and positionalParamSegments
|
|
3047
|
-
parameters,
|
|
3048
|
-
positionalParamSegments: res.posParams ?? {}
|
|
3049
|
-
};
|
|
3050
3170
|
}
|
|
3051
|
-
function
|
|
3052
|
-
|
|
3053
|
-
|
|
3054
|
-
|
|
3055
|
-
s._sourceSegment = segmentGroup;
|
|
3056
|
-
s._segmentIndexShift = consumedSegments.length;
|
|
3057
|
-
return { segmentGroup: s, slicedSegments: [] };
|
|
3058
|
-
}
|
|
3059
|
-
if (slicedSegments.length === 0 &&
|
|
3060
|
-
containsEmptyPathMatches(segmentGroup, slicedSegments, config)) {
|
|
3061
|
-
const s = new UrlSegmentGroup(segmentGroup.segments, addEmptyPathsToChildrenIfNeeded(segmentGroup, consumedSegments, slicedSegments, config, segmentGroup.children, relativeLinkResolution));
|
|
3062
|
-
s._sourceSegment = segmentGroup;
|
|
3063
|
-
s._segmentIndexShift = consumedSegments.length;
|
|
3064
|
-
return { segmentGroup: s, slicedSegments };
|
|
3065
|
-
}
|
|
3066
|
-
const s = new UrlSegmentGroup(segmentGroup.segments, segmentGroup.children);
|
|
3067
|
-
s._sourceSegment = segmentGroup;
|
|
3068
|
-
s._segmentIndexShift = consumedSegments.length;
|
|
3069
|
-
return { segmentGroup: s, slicedSegments };
|
|
3171
|
+
function runCanDeactivateChecks(checks, futureRSS, currRSS, moduleInjector) {
|
|
3172
|
+
return from(checks).pipe(mergeMap(check => runCanDeactivate(check.component, check.route, currRSS, futureRSS, moduleInjector)), first(result => {
|
|
3173
|
+
return result !== true;
|
|
3174
|
+
}, true));
|
|
3070
3175
|
}
|
|
3071
|
-
function
|
|
3072
|
-
|
|
3073
|
-
|
|
3074
|
-
|
|
3075
|
-
|
|
3076
|
-
|
|
3077
|
-
|
|
3078
|
-
|
|
3079
|
-
|
|
3080
|
-
|
|
3081
|
-
|
|
3082
|
-
|
|
3083
|
-
|
|
3084
|
-
|
|
3085
|
-
|
|
3086
|
-
|
|
3087
|
-
|
|
3176
|
+
function runCanActivateChecks(futureSnapshot, checks, moduleInjector, forwardEvent) {
|
|
3177
|
+
return from(checks).pipe(concatMap((check) => {
|
|
3178
|
+
return concat(fireChildActivationStart(check.route.parent, forwardEvent), fireActivationStart(check.route, forwardEvent), runCanActivateChild(futureSnapshot, check.path, moduleInjector), runCanActivate(futureSnapshot, check.route, moduleInjector));
|
|
3179
|
+
}), first(result => {
|
|
3180
|
+
return result !== true;
|
|
3181
|
+
}, true));
|
|
3182
|
+
}
|
|
3183
|
+
/**
|
|
3184
|
+
* This should fire off `ActivationStart` events for each route being activated at this
|
|
3185
|
+
* level.
|
|
3186
|
+
* In other words, if you're activating `a` and `b` below, `path` will contain the
|
|
3187
|
+
* `ActivatedRouteSnapshot`s for both and we will fire `ActivationStart` for both. Always
|
|
3188
|
+
* return
|
|
3189
|
+
* `true` so checks continue to run.
|
|
3190
|
+
*/
|
|
3191
|
+
function fireActivationStart(snapshot, forwardEvent) {
|
|
3192
|
+
if (snapshot !== null && forwardEvent) {
|
|
3193
|
+
forwardEvent(new ActivationStart(snapshot));
|
|
3088
3194
|
}
|
|
3089
|
-
return
|
|
3195
|
+
return of(true);
|
|
3090
3196
|
}
|
|
3091
|
-
|
|
3092
|
-
|
|
3093
|
-
|
|
3094
|
-
|
|
3095
|
-
|
|
3096
|
-
|
|
3197
|
+
/**
|
|
3198
|
+
* This should fire off `ChildActivationStart` events for each route being activated at this
|
|
3199
|
+
* level.
|
|
3200
|
+
* In other words, if you're activating `a` and `b` below, `path` will contain the
|
|
3201
|
+
* `ActivatedRouteSnapshot`s for both and we will fire `ChildActivationStart` for both. Always
|
|
3202
|
+
* return
|
|
3203
|
+
* `true` so checks continue to run.
|
|
3204
|
+
*/
|
|
3205
|
+
function fireChildActivationStart(snapshot, forwardEvent) {
|
|
3206
|
+
if (snapshot !== null && forwardEvent) {
|
|
3207
|
+
forwardEvent(new ChildActivationStart(snapshot));
|
|
3208
|
+
}
|
|
3209
|
+
return of(true);
|
|
3210
|
+
}
|
|
3211
|
+
function runCanActivate(futureRSS, futureARS, moduleInjector) {
|
|
3212
|
+
const canActivate = futureARS.routeConfig ? futureARS.routeConfig.canActivate : null;
|
|
3213
|
+
if (!canActivate || canActivate.length === 0)
|
|
3214
|
+
return of(true);
|
|
3215
|
+
const canActivateObservables = canActivate.map((c) => {
|
|
3216
|
+
return defer(() => {
|
|
3217
|
+
const guard = getToken(c, futureARS, moduleInjector);
|
|
3218
|
+
let observable;
|
|
3219
|
+
if (isCanActivate(guard)) {
|
|
3220
|
+
observable = wrapIntoObservable(guard.canActivate(futureARS, futureRSS));
|
|
3221
|
+
}
|
|
3222
|
+
else if (isFunction(guard)) {
|
|
3223
|
+
observable = wrapIntoObservable(guard(futureARS, futureRSS));
|
|
3224
|
+
}
|
|
3225
|
+
else {
|
|
3226
|
+
throw new Error('Invalid CanActivate guard');
|
|
3227
|
+
}
|
|
3228
|
+
return observable.pipe(first());
|
|
3229
|
+
});
|
|
3230
|
+
});
|
|
3231
|
+
return of(canActivateObservables).pipe(prioritizedGuardValue());
|
|
3232
|
+
}
|
|
3233
|
+
function runCanActivateChild(futureRSS, path, moduleInjector) {
|
|
3234
|
+
const futureARS = path[path.length - 1];
|
|
3235
|
+
const canActivateChildGuards = path.slice(0, path.length - 1)
|
|
3236
|
+
.reverse()
|
|
3237
|
+
.map(p => getCanActivateChild(p))
|
|
3238
|
+
.filter(_ => _ !== null);
|
|
3239
|
+
const canActivateChildGuardsMapped = canActivateChildGuards.map((d) => {
|
|
3240
|
+
return defer(() => {
|
|
3241
|
+
const guardsMapped = d.guards.map((c) => {
|
|
3242
|
+
const guard = getToken(c, d.node, moduleInjector);
|
|
3243
|
+
let observable;
|
|
3244
|
+
if (isCanActivateChild(guard)) {
|
|
3245
|
+
observable = wrapIntoObservable(guard.canActivateChild(futureARS, futureRSS));
|
|
3246
|
+
}
|
|
3247
|
+
else if (isFunction(guard)) {
|
|
3248
|
+
observable = wrapIntoObservable(guard(futureARS, futureRSS));
|
|
3249
|
+
}
|
|
3250
|
+
else {
|
|
3251
|
+
throw new Error('Invalid CanActivateChild guard');
|
|
3252
|
+
}
|
|
3253
|
+
return observable.pipe(first());
|
|
3254
|
+
});
|
|
3255
|
+
return of(guardsMapped).pipe(prioritizedGuardValue());
|
|
3256
|
+
});
|
|
3257
|
+
});
|
|
3258
|
+
return of(canActivateChildGuardsMapped).pipe(prioritizedGuardValue());
|
|
3259
|
+
}
|
|
3260
|
+
function runCanDeactivate(component, currARS, currRSS, futureRSS, moduleInjector) {
|
|
3261
|
+
const canDeactivate = currARS && currARS.routeConfig ? currARS.routeConfig.canDeactivate : null;
|
|
3262
|
+
if (!canDeactivate || canDeactivate.length === 0)
|
|
3263
|
+
return of(true);
|
|
3264
|
+
const canDeactivateObservables = canDeactivate.map((c) => {
|
|
3265
|
+
const guard = getToken(c, currARS, moduleInjector);
|
|
3266
|
+
let observable;
|
|
3267
|
+
if (isCanDeactivate(guard)) {
|
|
3268
|
+
observable = wrapIntoObservable(guard.canDeactivate(component, currARS, currRSS, futureRSS));
|
|
3269
|
+
}
|
|
3270
|
+
else if (isFunction(guard)) {
|
|
3271
|
+
observable = wrapIntoObservable(guard(component, currARS, currRSS, futureRSS));
|
|
3272
|
+
}
|
|
3273
|
+
else {
|
|
3274
|
+
throw new Error('Invalid CanDeactivate guard');
|
|
3275
|
+
}
|
|
3276
|
+
return observable.pipe(first());
|
|
3277
|
+
});
|
|
3278
|
+
return of(canDeactivateObservables).pipe(prioritizedGuardValue());
|
|
3279
|
+
}
|
|
3280
|
+
function runCanLoadGuards(injector, route, segments, urlSerializer) {
|
|
3281
|
+
const canLoad = route.canLoad;
|
|
3282
|
+
if (canLoad === undefined || canLoad.length === 0) {
|
|
3283
|
+
return of(true);
|
|
3284
|
+
}
|
|
3285
|
+
const canLoadObservables = canLoad.map((injectionToken) => {
|
|
3286
|
+
const guard = injector.get(injectionToken);
|
|
3287
|
+
let guardVal;
|
|
3288
|
+
if (isCanLoad(guard)) {
|
|
3289
|
+
guardVal = guard.canLoad(route, segments);
|
|
3290
|
+
}
|
|
3291
|
+
else if (isFunction(guard)) {
|
|
3292
|
+
guardVal = guard(route, segments);
|
|
3293
|
+
}
|
|
3294
|
+
else {
|
|
3295
|
+
throw new Error('Invalid CanLoad guard');
|
|
3296
|
+
}
|
|
3297
|
+
return wrapIntoObservable(guardVal);
|
|
3298
|
+
});
|
|
3299
|
+
return of(canLoadObservables)
|
|
3300
|
+
.pipe(prioritizedGuardValue(), redirectIfUrlTree(urlSerializer));
|
|
3301
|
+
}
|
|
3302
|
+
function redirectIfUrlTree(urlSerializer) {
|
|
3303
|
+
return pipe(tap((result) => {
|
|
3304
|
+
if (!isUrlTree(result))
|
|
3305
|
+
return;
|
|
3306
|
+
const error = navigationCancelingError(`Redirecting to "${urlSerializer.serialize(result)}"`);
|
|
3307
|
+
error.url = result;
|
|
3308
|
+
throw error;
|
|
3309
|
+
}), map(result => result === true));
|
|
3310
|
+
}
|
|
3311
|
+
function runCanMatchGuards(injector, route, segments, urlSerializer) {
|
|
3312
|
+
const canMatch = route.canMatch;
|
|
3313
|
+
if (!canMatch || canMatch.length === 0)
|
|
3314
|
+
return of(true);
|
|
3315
|
+
const canMatchObservables = canMatch.map(injectionToken => {
|
|
3316
|
+
const guard = injector.get(injectionToken);
|
|
3317
|
+
const guardVal = isCanMatch(guard) ? guard.canMatch(route, segments) : guard(route, segments);
|
|
3318
|
+
return wrapIntoObservable(guardVal);
|
|
3319
|
+
});
|
|
3320
|
+
return of(canMatchObservables)
|
|
3321
|
+
.pipe(prioritizedGuardValue(), redirectIfUrlTree(urlSerializer));
|
|
3322
|
+
}
|
|
3323
|
+
|
|
3324
|
+
/**
|
|
3325
|
+
* @license
|
|
3326
|
+
* Copyright Google LLC All Rights Reserved.
|
|
3327
|
+
*
|
|
3328
|
+
* Use of this source code is governed by an MIT-style license that can be
|
|
3329
|
+
* found in the LICENSE file at https://angular.io/license
|
|
3330
|
+
*/
|
|
3331
|
+
const noMatch$1 = {
|
|
3332
|
+
matched: false,
|
|
3333
|
+
consumedSegments: [],
|
|
3334
|
+
remainingSegments: [],
|
|
3335
|
+
parameters: {},
|
|
3336
|
+
positionalParamSegments: {}
|
|
3337
|
+
};
|
|
3338
|
+
function matchWithChecks(segmentGroup, route, segments, injector, urlSerializer) {
|
|
3339
|
+
const result = match(segmentGroup, route, segments);
|
|
3340
|
+
if (!result.matched) {
|
|
3341
|
+
return of(result);
|
|
3342
|
+
}
|
|
3343
|
+
// Only create the Route's `EnvironmentInjector` if it matches the attempted
|
|
3344
|
+
// navigation
|
|
3345
|
+
injector = getOrCreateRouteInjectorIfNeeded(route, injector);
|
|
3346
|
+
return runCanMatchGuards(injector, route, segments, urlSerializer)
|
|
3347
|
+
.pipe(map((v) => v === true ? result : { ...noMatch$1 }));
|
|
3348
|
+
}
|
|
3349
|
+
function match(segmentGroup, route, segments) {
|
|
3350
|
+
if (route.path === '') {
|
|
3351
|
+
if (route.pathMatch === 'full' && (segmentGroup.hasChildren() || segments.length > 0)) {
|
|
3352
|
+
return { ...noMatch$1 };
|
|
3353
|
+
}
|
|
3354
|
+
return {
|
|
3355
|
+
matched: true,
|
|
3356
|
+
consumedSegments: [],
|
|
3357
|
+
remainingSegments: segments,
|
|
3358
|
+
parameters: {},
|
|
3359
|
+
positionalParamSegments: {}
|
|
3360
|
+
};
|
|
3361
|
+
}
|
|
3362
|
+
const matcher = route.matcher || defaultUrlMatcher;
|
|
3363
|
+
const res = matcher(segments, segmentGroup, route);
|
|
3364
|
+
if (!res)
|
|
3365
|
+
return { ...noMatch$1 };
|
|
3366
|
+
const posParams = {};
|
|
3367
|
+
forEach(res.posParams, (v, k) => {
|
|
3368
|
+
posParams[k] = v.path;
|
|
3369
|
+
});
|
|
3370
|
+
const parameters = res.consumed.length > 0 ?
|
|
3371
|
+
{ ...posParams, ...res.consumed[res.consumed.length - 1].parameters } :
|
|
3372
|
+
posParams;
|
|
3373
|
+
return {
|
|
3374
|
+
matched: true,
|
|
3375
|
+
consumedSegments: res.consumed,
|
|
3376
|
+
remainingSegments: segments.slice(res.consumed.length),
|
|
3377
|
+
// TODO(atscott): investigate combining parameters and positionalParamSegments
|
|
3378
|
+
parameters,
|
|
3379
|
+
positionalParamSegments: res.posParams ?? {}
|
|
3380
|
+
};
|
|
3381
|
+
}
|
|
3382
|
+
function split(segmentGroup, consumedSegments, slicedSegments, config, relativeLinkResolution = 'corrected') {
|
|
3383
|
+
if (slicedSegments.length > 0 &&
|
|
3384
|
+
containsEmptyPathMatchesWithNamedOutlets(segmentGroup, slicedSegments, config)) {
|
|
3385
|
+
const s = new UrlSegmentGroup(consumedSegments, createChildrenForEmptyPaths(segmentGroup, consumedSegments, config, new UrlSegmentGroup(slicedSegments, segmentGroup.children)));
|
|
3386
|
+
s._sourceSegment = segmentGroup;
|
|
3387
|
+
s._segmentIndexShift = consumedSegments.length;
|
|
3388
|
+
return { segmentGroup: s, slicedSegments: [] };
|
|
3389
|
+
}
|
|
3390
|
+
if (slicedSegments.length === 0 &&
|
|
3391
|
+
containsEmptyPathMatches(segmentGroup, slicedSegments, config)) {
|
|
3392
|
+
const s = new UrlSegmentGroup(segmentGroup.segments, addEmptyPathsToChildrenIfNeeded(segmentGroup, consumedSegments, slicedSegments, config, segmentGroup.children, relativeLinkResolution));
|
|
3393
|
+
s._sourceSegment = segmentGroup;
|
|
3394
|
+
s._segmentIndexShift = consumedSegments.length;
|
|
3395
|
+
return { segmentGroup: s, slicedSegments };
|
|
3396
|
+
}
|
|
3397
|
+
const s = new UrlSegmentGroup(segmentGroup.segments, segmentGroup.children);
|
|
3398
|
+
s._sourceSegment = segmentGroup;
|
|
3399
|
+
s._segmentIndexShift = consumedSegments.length;
|
|
3400
|
+
return { segmentGroup: s, slicedSegments };
|
|
3401
|
+
}
|
|
3402
|
+
function addEmptyPathsToChildrenIfNeeded(segmentGroup, consumedSegments, slicedSegments, routes, children, relativeLinkResolution) {
|
|
3403
|
+
const res = {};
|
|
3404
|
+
for (const r of routes) {
|
|
3405
|
+
if (emptyPathMatch(segmentGroup, slicedSegments, r) && !children[getOutlet(r)]) {
|
|
3406
|
+
const s = new UrlSegmentGroup([], {});
|
|
3407
|
+
s._sourceSegment = segmentGroup;
|
|
3408
|
+
if (relativeLinkResolution === 'legacy') {
|
|
3409
|
+
s._segmentIndexShift = segmentGroup.segments.length;
|
|
3410
|
+
if (typeof ngDevMode === 'undefined' || !!ngDevMode) {
|
|
3411
|
+
s._segmentIndexShiftCorrected = consumedSegments.length;
|
|
3412
|
+
}
|
|
3413
|
+
}
|
|
3414
|
+
else {
|
|
3415
|
+
s._segmentIndexShift = consumedSegments.length;
|
|
3416
|
+
}
|
|
3417
|
+
res[getOutlet(r)] = s;
|
|
3418
|
+
}
|
|
3419
|
+
}
|
|
3420
|
+
return { ...children, ...res };
|
|
3421
|
+
}
|
|
3422
|
+
function createChildrenForEmptyPaths(segmentGroup, consumedSegments, routes, primarySegment) {
|
|
3423
|
+
const res = {};
|
|
3424
|
+
res[PRIMARY_OUTLET] = primarySegment;
|
|
3425
|
+
primarySegment._sourceSegment = segmentGroup;
|
|
3426
|
+
primarySegment._segmentIndexShift = consumedSegments.length;
|
|
3427
|
+
for (const r of routes) {
|
|
3097
3428
|
if (r.path === '' && getOutlet(r) !== PRIMARY_OUTLET) {
|
|
3098
3429
|
const s = new UrlSegmentGroup([], {});
|
|
3099
3430
|
s._sourceSegment = segmentGroup;
|
|
@@ -3346,28 +3677,30 @@ class ApplyRedirects {
|
|
|
3346
3677
|
}
|
|
3347
3678
|
return of(new UrlSegmentGroup(segments, {}));
|
|
3348
3679
|
}
|
|
3349
|
-
|
|
3350
|
-
|
|
3351
|
-
|
|
3352
|
-
|
|
3353
|
-
|
|
3354
|
-
|
|
3355
|
-
|
|
3356
|
-
|
|
3357
|
-
|
|
3358
|
-
|
|
3359
|
-
|
|
3360
|
-
|
|
3361
|
-
|
|
3362
|
-
|
|
3363
|
-
|
|
3364
|
-
|
|
3365
|
-
|
|
3366
|
-
|
|
3367
|
-
|
|
3368
|
-
|
|
3369
|
-
|
|
3370
|
-
|
|
3680
|
+
return matchWithChecks(rawSegmentGroup, route, segments, injector, this.urlSerializer)
|
|
3681
|
+
.pipe(switchMap(({ matched, consumedSegments, remainingSegments }) => {
|
|
3682
|
+
if (!matched)
|
|
3683
|
+
return noMatch(rawSegmentGroup);
|
|
3684
|
+
// If the route has an injector created from providers, we should start using that.
|
|
3685
|
+
injector = route._injector ?? injector;
|
|
3686
|
+
const childConfig$ = this.getChildConfig(injector, route, segments);
|
|
3687
|
+
return childConfig$.pipe(mergeMap((routerConfig) => {
|
|
3688
|
+
const childInjector = routerConfig.injector ?? injector;
|
|
3689
|
+
const childConfig = routerConfig.routes;
|
|
3690
|
+
const { segmentGroup: splitSegmentGroup, slicedSegments } = split(rawSegmentGroup, consumedSegments, remainingSegments, childConfig);
|
|
3691
|
+
// See comment on the other call to `split` about why this is necessary.
|
|
3692
|
+
const segmentGroup = new UrlSegmentGroup(splitSegmentGroup.segments, splitSegmentGroup.children);
|
|
3693
|
+
if (slicedSegments.length === 0 && segmentGroup.hasChildren()) {
|
|
3694
|
+
const expanded$ = this.expandChildren(childInjector, childConfig, segmentGroup);
|
|
3695
|
+
return expanded$.pipe(map((children) => new UrlSegmentGroup(consumedSegments, children)));
|
|
3696
|
+
}
|
|
3697
|
+
if (childConfig.length === 0 && slicedSegments.length === 0) {
|
|
3698
|
+
return of(new UrlSegmentGroup(consumedSegments, {}));
|
|
3699
|
+
}
|
|
3700
|
+
const matchedOnOutlet = getOutlet(route) === outlet;
|
|
3701
|
+
const expanded$ = this.expandSegment(childInjector, segmentGroup, childConfig, slicedSegments, matchedOnOutlet ? PRIMARY_OUTLET : outlet, true);
|
|
3702
|
+
return expanded$.pipe(map((cs) => new UrlSegmentGroup(consumedSegments.concat(cs.segments), cs.children)));
|
|
3703
|
+
}));
|
|
3371
3704
|
}));
|
|
3372
3705
|
}
|
|
3373
3706
|
getChildConfig(injector, route, segments) {
|
|
@@ -3380,7 +3713,7 @@ class ApplyRedirects {
|
|
|
3380
3713
|
if (route._loadedRoutes !== undefined) {
|
|
3381
3714
|
return of({ routes: route._loadedRoutes, injector: route._loadedInjector });
|
|
3382
3715
|
}
|
|
3383
|
-
return
|
|
3716
|
+
return runCanLoadGuards(injector, route, segments, this.urlSerializer)
|
|
3384
3717
|
.pipe(mergeMap((shouldLoadResult) => {
|
|
3385
3718
|
if (shouldLoadResult) {
|
|
3386
3719
|
return this.configLoader.loadChildren(injector, route)
|
|
@@ -3394,33 +3727,6 @@ class ApplyRedirects {
|
|
|
3394
3727
|
}
|
|
3395
3728
|
return of({ routes: [], injector });
|
|
3396
3729
|
}
|
|
3397
|
-
runCanLoadGuards(injector, route, segments) {
|
|
3398
|
-
const canLoad = route.canLoad;
|
|
3399
|
-
if (!canLoad || canLoad.length === 0)
|
|
3400
|
-
return of(true);
|
|
3401
|
-
const canLoadObservables = canLoad.map((injectionToken) => {
|
|
3402
|
-
const guard = injector.get(injectionToken);
|
|
3403
|
-
let guardVal;
|
|
3404
|
-
if (isCanLoad(guard)) {
|
|
3405
|
-
guardVal = guard.canLoad(route, segments);
|
|
3406
|
-
}
|
|
3407
|
-
else if (isFunction(guard)) {
|
|
3408
|
-
guardVal = guard(route, segments);
|
|
3409
|
-
}
|
|
3410
|
-
else {
|
|
3411
|
-
throw new Error('Invalid CanLoad guard');
|
|
3412
|
-
}
|
|
3413
|
-
return wrapIntoObservable(guardVal);
|
|
3414
|
-
});
|
|
3415
|
-
return of(canLoadObservables)
|
|
3416
|
-
.pipe(prioritizedGuardValue(), tap((result) => {
|
|
3417
|
-
if (!isUrlTree(result))
|
|
3418
|
-
return;
|
|
3419
|
-
const error = navigationCancelingError(`Redirecting to "${this.urlSerializer.serialize(result)}"`);
|
|
3420
|
-
error.url = result;
|
|
3421
|
-
throw error;
|
|
3422
|
-
}), map(result => result === true));
|
|
3423
|
-
}
|
|
3424
3730
|
lineralizeSegments(route, urlTree) {
|
|
3425
3731
|
let res = [];
|
|
3426
3732
|
let c = urlTree.root;
|
|
@@ -3430,344 +3736,61 @@ class ApplyRedirects {
|
|
|
3430
3736
|
return of(res);
|
|
3431
3737
|
}
|
|
3432
3738
|
if (c.numberOfChildren > 1 || !c.children[PRIMARY_OUTLET]) {
|
|
3433
|
-
return namedOutletsRedirect(route.redirectTo);
|
|
3434
|
-
}
|
|
3435
|
-
c = c.children[PRIMARY_OUTLET];
|
|
3436
|
-
}
|
|
3437
|
-
}
|
|
3438
|
-
applyRedirectCommands(segments, redirectTo, posParams) {
|
|
3439
|
-
return this.applyRedirectCreatreUrlTree(redirectTo, this.urlSerializer.parse(redirectTo), segments, posParams);
|
|
3440
|
-
}
|
|
3441
|
-
applyRedirectCreatreUrlTree(redirectTo, urlTree, segments, posParams) {
|
|
3442
|
-
const newRoot = this.createSegmentGroup(redirectTo, urlTree.root, segments, posParams);
|
|
3443
|
-
return new UrlTree(newRoot, this.createQueryParams(urlTree.queryParams, this.urlTree.queryParams), urlTree.fragment);
|
|
3444
|
-
}
|
|
3445
|
-
createQueryParams(redirectToParams, actualParams) {
|
|
3446
|
-
const res = {};
|
|
3447
|
-
forEach(redirectToParams, (v, k) => {
|
|
3448
|
-
const copySourceValue = typeof v === 'string' && v.startsWith(':');
|
|
3449
|
-
if (copySourceValue) {
|
|
3450
|
-
const sourceName = v.substring(1);
|
|
3451
|
-
res[k] = actualParams[sourceName];
|
|
3452
|
-
}
|
|
3453
|
-
else {
|
|
3454
|
-
res[k] = v;
|
|
3455
|
-
}
|
|
3456
|
-
});
|
|
3457
|
-
return res;
|
|
3458
|
-
}
|
|
3459
|
-
createSegmentGroup(redirectTo, group, segments, posParams) {
|
|
3460
|
-
const updatedSegments = this.createSegments(redirectTo, group.segments, segments, posParams);
|
|
3461
|
-
let children = {};
|
|
3462
|
-
forEach(group.children, (child, name) => {
|
|
3463
|
-
children[name] = this.createSegmentGroup(redirectTo, child, segments, posParams);
|
|
3464
|
-
});
|
|
3465
|
-
return new UrlSegmentGroup(updatedSegments, children);
|
|
3466
|
-
}
|
|
3467
|
-
createSegments(redirectTo, redirectToSegments, actualSegments, posParams) {
|
|
3468
|
-
return redirectToSegments.map(s => s.path.startsWith(':') ? this.findPosParam(redirectTo, s, posParams) :
|
|
3469
|
-
this.findOrReturn(s, actualSegments));
|
|
3470
|
-
}
|
|
3471
|
-
findPosParam(redirectTo, redirectToUrlSegment, posParams) {
|
|
3472
|
-
const pos = posParams[redirectToUrlSegment.path.substring(1)];
|
|
3473
|
-
if (!pos)
|
|
3474
|
-
throw new Error(`Cannot redirect to '${redirectTo}'. Cannot find '${redirectToUrlSegment.path}'.`);
|
|
3475
|
-
return pos;
|
|
3476
|
-
}
|
|
3477
|
-
findOrReturn(redirectToUrlSegment, actualSegments) {
|
|
3478
|
-
let idx = 0;
|
|
3479
|
-
for (const s of actualSegments) {
|
|
3480
|
-
if (s.path === redirectToUrlSegment.path) {
|
|
3481
|
-
actualSegments.splice(idx);
|
|
3482
|
-
return s;
|
|
3483
|
-
}
|
|
3484
|
-
idx++;
|
|
3485
|
-
}
|
|
3486
|
-
return redirectToUrlSegment;
|
|
3487
|
-
}
|
|
3488
|
-
}
|
|
3489
|
-
|
|
3490
|
-
/**
|
|
3491
|
-
* @license
|
|
3492
|
-
* Copyright Google LLC All Rights Reserved.
|
|
3493
|
-
*
|
|
3494
|
-
* Use of this source code is governed by an MIT-style license that can be
|
|
3495
|
-
* found in the LICENSE file at https://angular.io/license
|
|
3496
|
-
*/
|
|
3497
|
-
function applyRedirects(environmentInjector, configLoader, urlSerializer, config) {
|
|
3498
|
-
return switchMap(t => applyRedirects$1(environmentInjector, configLoader, urlSerializer, t.extractedUrl, config)
|
|
3499
|
-
.pipe(map(urlAfterRedirects => ({ ...t, urlAfterRedirects }))));
|
|
3500
|
-
}
|
|
3501
|
-
|
|
3502
|
-
/**
|
|
3503
|
-
* @license
|
|
3504
|
-
* Copyright Google LLC All Rights Reserved.
|
|
3505
|
-
*
|
|
3506
|
-
* Use of this source code is governed by an MIT-style license that can be
|
|
3507
|
-
* found in the LICENSE file at https://angular.io/license
|
|
3508
|
-
*/
|
|
3509
|
-
class CanActivate {
|
|
3510
|
-
constructor(path) {
|
|
3511
|
-
this.path = path;
|
|
3512
|
-
this.route = this.path[this.path.length - 1];
|
|
3513
|
-
}
|
|
3514
|
-
}
|
|
3515
|
-
class CanDeactivate {
|
|
3516
|
-
constructor(component, route) {
|
|
3517
|
-
this.component = component;
|
|
3518
|
-
this.route = route;
|
|
3519
|
-
}
|
|
3520
|
-
}
|
|
3521
|
-
function getAllRouteGuards(future, curr, parentContexts) {
|
|
3522
|
-
const futureRoot = future._root;
|
|
3523
|
-
const currRoot = curr ? curr._root : null;
|
|
3524
|
-
return getChildRouteGuards(futureRoot, currRoot, parentContexts, [futureRoot.value]);
|
|
3525
|
-
}
|
|
3526
|
-
function getCanActivateChild(p) {
|
|
3527
|
-
const canActivateChild = p.routeConfig ? p.routeConfig.canActivateChild : null;
|
|
3528
|
-
if (!canActivateChild || canActivateChild.length === 0)
|
|
3529
|
-
return null;
|
|
3530
|
-
return { node: p, guards: canActivateChild };
|
|
3531
|
-
}
|
|
3532
|
-
function getToken(token, snapshot, fallbackInjector) {
|
|
3533
|
-
const routeInjector = getClosestRouteInjector(snapshot);
|
|
3534
|
-
const injector = routeInjector ?? fallbackInjector;
|
|
3535
|
-
return injector.get(token);
|
|
3536
|
-
}
|
|
3537
|
-
function getChildRouteGuards(futureNode, currNode, contexts, futurePath, checks = {
|
|
3538
|
-
canDeactivateChecks: [],
|
|
3539
|
-
canActivateChecks: []
|
|
3540
|
-
}) {
|
|
3541
|
-
const prevChildren = nodeChildrenAsMap(currNode);
|
|
3542
|
-
// Process the children of the future route
|
|
3543
|
-
futureNode.children.forEach(c => {
|
|
3544
|
-
getRouteGuards(c, prevChildren[c.value.outlet], contexts, futurePath.concat([c.value]), checks);
|
|
3545
|
-
delete prevChildren[c.value.outlet];
|
|
3546
|
-
});
|
|
3547
|
-
// Process any children left from the current route (not active for the future route)
|
|
3548
|
-
forEach(prevChildren, (v, k) => deactivateRouteAndItsChildren(v, contexts.getContext(k), checks));
|
|
3549
|
-
return checks;
|
|
3550
|
-
}
|
|
3551
|
-
function getRouteGuards(futureNode, currNode, parentContexts, futurePath, checks = {
|
|
3552
|
-
canDeactivateChecks: [],
|
|
3553
|
-
canActivateChecks: []
|
|
3554
|
-
}) {
|
|
3555
|
-
const future = futureNode.value;
|
|
3556
|
-
const curr = currNode ? currNode.value : null;
|
|
3557
|
-
const context = parentContexts ? parentContexts.getContext(futureNode.value.outlet) : null;
|
|
3558
|
-
// reusing the node
|
|
3559
|
-
if (curr && future.routeConfig === curr.routeConfig) {
|
|
3560
|
-
const shouldRun = shouldRunGuardsAndResolvers(curr, future, future.routeConfig.runGuardsAndResolvers);
|
|
3561
|
-
if (shouldRun) {
|
|
3562
|
-
checks.canActivateChecks.push(new CanActivate(futurePath));
|
|
3563
|
-
}
|
|
3564
|
-
else {
|
|
3565
|
-
// we need to set the data
|
|
3566
|
-
future.data = curr.data;
|
|
3567
|
-
future._resolvedData = curr._resolvedData;
|
|
3568
|
-
}
|
|
3569
|
-
// If we have a component, we need to go through an outlet.
|
|
3570
|
-
if (future.component) {
|
|
3571
|
-
getChildRouteGuards(futureNode, currNode, context ? context.children : null, futurePath, checks);
|
|
3572
|
-
// if we have a componentless route, we recurse but keep the same outlet map.
|
|
3573
|
-
}
|
|
3574
|
-
else {
|
|
3575
|
-
getChildRouteGuards(futureNode, currNode, parentContexts, futurePath, checks);
|
|
3576
|
-
}
|
|
3577
|
-
if (shouldRun && context && context.outlet && context.outlet.isActivated) {
|
|
3578
|
-
checks.canDeactivateChecks.push(new CanDeactivate(context.outlet.component, curr));
|
|
3579
|
-
}
|
|
3580
|
-
}
|
|
3581
|
-
else {
|
|
3582
|
-
if (curr) {
|
|
3583
|
-
deactivateRouteAndItsChildren(currNode, context, checks);
|
|
3584
|
-
}
|
|
3585
|
-
checks.canActivateChecks.push(new CanActivate(futurePath));
|
|
3586
|
-
// If we have a component, we need to go through an outlet.
|
|
3587
|
-
if (future.component) {
|
|
3588
|
-
getChildRouteGuards(futureNode, null, context ? context.children : null, futurePath, checks);
|
|
3589
|
-
// if we have a componentless route, we recurse but keep the same outlet map.
|
|
3590
|
-
}
|
|
3591
|
-
else {
|
|
3592
|
-
getChildRouteGuards(futureNode, null, parentContexts, futurePath, checks);
|
|
3593
|
-
}
|
|
3594
|
-
}
|
|
3595
|
-
return checks;
|
|
3596
|
-
}
|
|
3597
|
-
function shouldRunGuardsAndResolvers(curr, future, mode) {
|
|
3598
|
-
if (typeof mode === 'function') {
|
|
3599
|
-
return mode(curr, future);
|
|
3600
|
-
}
|
|
3601
|
-
switch (mode) {
|
|
3602
|
-
case 'pathParamsChange':
|
|
3603
|
-
return !equalPath(curr.url, future.url);
|
|
3604
|
-
case 'pathParamsOrQueryParamsChange':
|
|
3605
|
-
return !equalPath(curr.url, future.url) ||
|
|
3606
|
-
!shallowEqual(curr.queryParams, future.queryParams);
|
|
3607
|
-
case 'always':
|
|
3608
|
-
return true;
|
|
3609
|
-
case 'paramsOrQueryParamsChange':
|
|
3610
|
-
return !equalParamsAndUrlSegments(curr, future) ||
|
|
3611
|
-
!shallowEqual(curr.queryParams, future.queryParams);
|
|
3612
|
-
case 'paramsChange':
|
|
3613
|
-
default:
|
|
3614
|
-
return !equalParamsAndUrlSegments(curr, future);
|
|
3615
|
-
}
|
|
3616
|
-
}
|
|
3617
|
-
function deactivateRouteAndItsChildren(route, context, checks) {
|
|
3618
|
-
const children = nodeChildrenAsMap(route);
|
|
3619
|
-
const r = route.value;
|
|
3620
|
-
forEach(children, (node, childName) => {
|
|
3621
|
-
if (!r.component) {
|
|
3622
|
-
deactivateRouteAndItsChildren(node, context, checks);
|
|
3623
|
-
}
|
|
3624
|
-
else if (context) {
|
|
3625
|
-
deactivateRouteAndItsChildren(node, context.children.getContext(childName), checks);
|
|
3626
|
-
}
|
|
3627
|
-
else {
|
|
3628
|
-
deactivateRouteAndItsChildren(node, null, checks);
|
|
3629
|
-
}
|
|
3630
|
-
});
|
|
3631
|
-
if (!r.component) {
|
|
3632
|
-
checks.canDeactivateChecks.push(new CanDeactivate(null, r));
|
|
3633
|
-
}
|
|
3634
|
-
else if (context && context.outlet && context.outlet.isActivated) {
|
|
3635
|
-
checks.canDeactivateChecks.push(new CanDeactivate(context.outlet.component, r));
|
|
3636
|
-
}
|
|
3637
|
-
else {
|
|
3638
|
-
checks.canDeactivateChecks.push(new CanDeactivate(null, r));
|
|
3639
|
-
}
|
|
3640
|
-
}
|
|
3641
|
-
|
|
3642
|
-
/**
|
|
3643
|
-
* @license
|
|
3644
|
-
* Copyright Google LLC All Rights Reserved.
|
|
3645
|
-
*
|
|
3646
|
-
* Use of this source code is governed by an MIT-style license that can be
|
|
3647
|
-
* found in the LICENSE file at https://angular.io/license
|
|
3648
|
-
*/
|
|
3649
|
-
function checkGuards(moduleInjector, forwardEvent) {
|
|
3650
|
-
return mergeMap(t => {
|
|
3651
|
-
const { targetSnapshot, currentSnapshot, guards: { canActivateChecks, canDeactivateChecks } } = t;
|
|
3652
|
-
if (canDeactivateChecks.length === 0 && canActivateChecks.length === 0) {
|
|
3653
|
-
return of({ ...t, guardsResult: true });
|
|
3654
|
-
}
|
|
3655
|
-
return runCanDeactivateChecks(canDeactivateChecks, targetSnapshot, currentSnapshot, moduleInjector)
|
|
3656
|
-
.pipe(mergeMap(canDeactivate => {
|
|
3657
|
-
return canDeactivate && isBoolean(canDeactivate) ?
|
|
3658
|
-
runCanActivateChecks(targetSnapshot, canActivateChecks, moduleInjector, forwardEvent) :
|
|
3659
|
-
of(canDeactivate);
|
|
3660
|
-
}), map(guardsResult => ({ ...t, guardsResult })));
|
|
3661
|
-
});
|
|
3662
|
-
}
|
|
3663
|
-
function runCanDeactivateChecks(checks, futureRSS, currRSS, moduleInjector) {
|
|
3664
|
-
return from(checks).pipe(mergeMap(check => runCanDeactivate(check.component, check.route, currRSS, futureRSS, moduleInjector)), first(result => {
|
|
3665
|
-
return result !== true;
|
|
3666
|
-
}, true));
|
|
3667
|
-
}
|
|
3668
|
-
function runCanActivateChecks(futureSnapshot, checks, moduleInjector, forwardEvent) {
|
|
3669
|
-
return from(checks).pipe(concatMap((check) => {
|
|
3670
|
-
return concat(fireChildActivationStart(check.route.parent, forwardEvent), fireActivationStart(check.route, forwardEvent), runCanActivateChild(futureSnapshot, check.path, moduleInjector), runCanActivate(futureSnapshot, check.route, moduleInjector));
|
|
3671
|
-
}), first(result => {
|
|
3672
|
-
return result !== true;
|
|
3673
|
-
}, true));
|
|
3674
|
-
}
|
|
3675
|
-
/**
|
|
3676
|
-
* This should fire off `ActivationStart` events for each route being activated at this
|
|
3677
|
-
* level.
|
|
3678
|
-
* In other words, if you're activating `a` and `b` below, `path` will contain the
|
|
3679
|
-
* `ActivatedRouteSnapshot`s for both and we will fire `ActivationStart` for both. Always
|
|
3680
|
-
* return
|
|
3681
|
-
* `true` so checks continue to run.
|
|
3682
|
-
*/
|
|
3683
|
-
function fireActivationStart(snapshot, forwardEvent) {
|
|
3684
|
-
if (snapshot !== null && forwardEvent) {
|
|
3685
|
-
forwardEvent(new ActivationStart(snapshot));
|
|
3686
|
-
}
|
|
3687
|
-
return of(true);
|
|
3688
|
-
}
|
|
3689
|
-
/**
|
|
3690
|
-
* This should fire off `ChildActivationStart` events for each route being activated at this
|
|
3691
|
-
* level.
|
|
3692
|
-
* In other words, if you're activating `a` and `b` below, `path` will contain the
|
|
3693
|
-
* `ActivatedRouteSnapshot`s for both and we will fire `ChildActivationStart` for both. Always
|
|
3694
|
-
* return
|
|
3695
|
-
* `true` so checks continue to run.
|
|
3696
|
-
*/
|
|
3697
|
-
function fireChildActivationStart(snapshot, forwardEvent) {
|
|
3698
|
-
if (snapshot !== null && forwardEvent) {
|
|
3699
|
-
forwardEvent(new ChildActivationStart(snapshot));
|
|
3700
|
-
}
|
|
3701
|
-
return of(true);
|
|
3702
|
-
}
|
|
3703
|
-
function runCanActivate(futureRSS, futureARS, moduleInjector) {
|
|
3704
|
-
const canActivate = futureARS.routeConfig ? futureARS.routeConfig.canActivate : null;
|
|
3705
|
-
if (!canActivate || canActivate.length === 0)
|
|
3706
|
-
return of(true);
|
|
3707
|
-
const canActivateObservables = canActivate.map((c) => {
|
|
3708
|
-
return defer(() => {
|
|
3709
|
-
const guard = getToken(c, futureARS, moduleInjector);
|
|
3710
|
-
let observable;
|
|
3711
|
-
if (isCanActivate(guard)) {
|
|
3712
|
-
observable = wrapIntoObservable(guard.canActivate(futureARS, futureRSS));
|
|
3739
|
+
return namedOutletsRedirect(route.redirectTo);
|
|
3713
3740
|
}
|
|
3714
|
-
|
|
3715
|
-
|
|
3741
|
+
c = c.children[PRIMARY_OUTLET];
|
|
3742
|
+
}
|
|
3743
|
+
}
|
|
3744
|
+
applyRedirectCommands(segments, redirectTo, posParams) {
|
|
3745
|
+
return this.applyRedirectCreatreUrlTree(redirectTo, this.urlSerializer.parse(redirectTo), segments, posParams);
|
|
3746
|
+
}
|
|
3747
|
+
applyRedirectCreatreUrlTree(redirectTo, urlTree, segments, posParams) {
|
|
3748
|
+
const newRoot = this.createSegmentGroup(redirectTo, urlTree.root, segments, posParams);
|
|
3749
|
+
return new UrlTree(newRoot, this.createQueryParams(urlTree.queryParams, this.urlTree.queryParams), urlTree.fragment);
|
|
3750
|
+
}
|
|
3751
|
+
createQueryParams(redirectToParams, actualParams) {
|
|
3752
|
+
const res = {};
|
|
3753
|
+
forEach(redirectToParams, (v, k) => {
|
|
3754
|
+
const copySourceValue = typeof v === 'string' && v.startsWith(':');
|
|
3755
|
+
if (copySourceValue) {
|
|
3756
|
+
const sourceName = v.substring(1);
|
|
3757
|
+
res[k] = actualParams[sourceName];
|
|
3716
3758
|
}
|
|
3717
3759
|
else {
|
|
3718
|
-
|
|
3760
|
+
res[k] = v;
|
|
3719
3761
|
}
|
|
3720
|
-
return observable.pipe(first());
|
|
3721
3762
|
});
|
|
3722
|
-
|
|
3723
|
-
|
|
3724
|
-
|
|
3725
|
-
|
|
3726
|
-
|
|
3727
|
-
|
|
3728
|
-
|
|
3729
|
-
.map(p => getCanActivateChild(p))
|
|
3730
|
-
.filter(_ => _ !== null);
|
|
3731
|
-
const canActivateChildGuardsMapped = canActivateChildGuards.map((d) => {
|
|
3732
|
-
return defer(() => {
|
|
3733
|
-
const guardsMapped = d.guards.map((c) => {
|
|
3734
|
-
const guard = getToken(c, d.node, moduleInjector);
|
|
3735
|
-
let observable;
|
|
3736
|
-
if (isCanActivateChild(guard)) {
|
|
3737
|
-
observable = wrapIntoObservable(guard.canActivateChild(futureARS, futureRSS));
|
|
3738
|
-
}
|
|
3739
|
-
else if (isFunction(guard)) {
|
|
3740
|
-
observable = wrapIntoObservable(guard(futureARS, futureRSS));
|
|
3741
|
-
}
|
|
3742
|
-
else {
|
|
3743
|
-
throw new Error('Invalid CanActivateChild guard');
|
|
3744
|
-
}
|
|
3745
|
-
return observable.pipe(first());
|
|
3746
|
-
});
|
|
3747
|
-
return of(guardsMapped).pipe(prioritizedGuardValue());
|
|
3763
|
+
return res;
|
|
3764
|
+
}
|
|
3765
|
+
createSegmentGroup(redirectTo, group, segments, posParams) {
|
|
3766
|
+
const updatedSegments = this.createSegments(redirectTo, group.segments, segments, posParams);
|
|
3767
|
+
let children = {};
|
|
3768
|
+
forEach(group.children, (child, name) => {
|
|
3769
|
+
children[name] = this.createSegmentGroup(redirectTo, child, segments, posParams);
|
|
3748
3770
|
});
|
|
3749
|
-
|
|
3750
|
-
|
|
3751
|
-
|
|
3752
|
-
|
|
3753
|
-
|
|
3754
|
-
|
|
3755
|
-
|
|
3756
|
-
|
|
3757
|
-
|
|
3758
|
-
|
|
3759
|
-
|
|
3760
|
-
|
|
3761
|
-
|
|
3762
|
-
|
|
3763
|
-
|
|
3764
|
-
|
|
3765
|
-
|
|
3766
|
-
|
|
3771
|
+
return new UrlSegmentGroup(updatedSegments, children);
|
|
3772
|
+
}
|
|
3773
|
+
createSegments(redirectTo, redirectToSegments, actualSegments, posParams) {
|
|
3774
|
+
return redirectToSegments.map(s => s.path.startsWith(':') ? this.findPosParam(redirectTo, s, posParams) :
|
|
3775
|
+
this.findOrReturn(s, actualSegments));
|
|
3776
|
+
}
|
|
3777
|
+
findPosParam(redirectTo, redirectToUrlSegment, posParams) {
|
|
3778
|
+
const pos = posParams[redirectToUrlSegment.path.substring(1)];
|
|
3779
|
+
if (!pos)
|
|
3780
|
+
throw new Error(`Cannot redirect to '${redirectTo}'. Cannot find '${redirectToUrlSegment.path}'.`);
|
|
3781
|
+
return pos;
|
|
3782
|
+
}
|
|
3783
|
+
findOrReturn(redirectToUrlSegment, actualSegments) {
|
|
3784
|
+
let idx = 0;
|
|
3785
|
+
for (const s of actualSegments) {
|
|
3786
|
+
if (s.path === redirectToUrlSegment.path) {
|
|
3787
|
+
actualSegments.splice(idx);
|
|
3788
|
+
return s;
|
|
3789
|
+
}
|
|
3790
|
+
idx++;
|
|
3767
3791
|
}
|
|
3768
|
-
return
|
|
3769
|
-
}
|
|
3770
|
-
return of(canDeactivateObservables).pipe(prioritizedGuardValue());
|
|
3792
|
+
return redirectToUrlSegment;
|
|
3793
|
+
}
|
|
3771
3794
|
}
|
|
3772
3795
|
|
|
3773
3796
|
/**
|
|
@@ -3777,53 +3800,64 @@ function runCanDeactivate(component, currARS, currRSS, futureRSS, moduleInjector
|
|
|
3777
3800
|
* Use of this source code is governed by an MIT-style license that can be
|
|
3778
3801
|
* found in the LICENSE file at https://angular.io/license
|
|
3779
3802
|
*/
|
|
3780
|
-
|
|
3803
|
+
function applyRedirects(environmentInjector, configLoader, urlSerializer, config) {
|
|
3804
|
+
return switchMap(t => applyRedirects$1(environmentInjector, configLoader, urlSerializer, t.extractedUrl, config)
|
|
3805
|
+
.pipe(map(urlAfterRedirects => ({ ...t, urlAfterRedirects }))));
|
|
3806
|
+
}
|
|
3807
|
+
|
|
3808
|
+
/**
|
|
3809
|
+
* @license
|
|
3810
|
+
* Copyright Google LLC All Rights Reserved.
|
|
3811
|
+
*
|
|
3812
|
+
* Use of this source code is governed by an MIT-style license that can be
|
|
3813
|
+
* found in the LICENSE file at https://angular.io/license
|
|
3814
|
+
*/
|
|
3815
|
+
const NG_DEV_MODE$3 = typeof ngDevMode === 'undefined' || !!ngDevMode;
|
|
3781
3816
|
class NoMatch {
|
|
3782
3817
|
}
|
|
3783
3818
|
function newObservableError(e) {
|
|
3784
3819
|
// TODO(atscott): This pattern is used throughout the router code and can be `throwError` instead.
|
|
3785
3820
|
return new Observable((obs) => obs.error(e));
|
|
3786
3821
|
}
|
|
3787
|
-
function recognize$1(rootComponentType, config, urlTree, url, paramsInheritanceStrategy = 'emptyOnly', relativeLinkResolution = 'legacy') {
|
|
3788
|
-
|
|
3789
|
-
|
|
3790
|
-
|
|
3822
|
+
function recognize$1(injector, rootComponentType, config, urlTree, url, urlSerializer, paramsInheritanceStrategy = 'emptyOnly', relativeLinkResolution = 'legacy') {
|
|
3823
|
+
return new Recognizer(injector, rootComponentType, config, urlTree, url, paramsInheritanceStrategy, relativeLinkResolution, urlSerializer)
|
|
3824
|
+
.recognize()
|
|
3825
|
+
.pipe(switchMap(result => {
|
|
3791
3826
|
if (result === null) {
|
|
3792
3827
|
return newObservableError(new NoMatch());
|
|
3793
3828
|
}
|
|
3794
3829
|
else {
|
|
3795
3830
|
return of(result);
|
|
3796
3831
|
}
|
|
3797
|
-
}
|
|
3798
|
-
catch (e) {
|
|
3799
|
-
// Catch the potential error from recognize due to duplicate outlet matches and return as an
|
|
3800
|
-
// `Observable` error instead.
|
|
3801
|
-
return newObservableError(e);
|
|
3802
|
-
}
|
|
3832
|
+
}));
|
|
3803
3833
|
}
|
|
3804
3834
|
class Recognizer {
|
|
3805
|
-
constructor(rootComponentType, config, urlTree, url, paramsInheritanceStrategy, relativeLinkResolution) {
|
|
3835
|
+
constructor(injector, rootComponentType, config, urlTree, url, paramsInheritanceStrategy, relativeLinkResolution, urlSerializer) {
|
|
3836
|
+
this.injector = injector;
|
|
3806
3837
|
this.rootComponentType = rootComponentType;
|
|
3807
3838
|
this.config = config;
|
|
3808
3839
|
this.urlTree = urlTree;
|
|
3809
3840
|
this.url = url;
|
|
3810
3841
|
this.paramsInheritanceStrategy = paramsInheritanceStrategy;
|
|
3811
3842
|
this.relativeLinkResolution = relativeLinkResolution;
|
|
3843
|
+
this.urlSerializer = urlSerializer;
|
|
3812
3844
|
}
|
|
3813
3845
|
recognize() {
|
|
3814
3846
|
const rootSegmentGroup = split(this.urlTree.root, [], [], this.config.filter(c => c.redirectTo === undefined), this.relativeLinkResolution)
|
|
3815
3847
|
.segmentGroup;
|
|
3816
|
-
|
|
3817
|
-
|
|
3818
|
-
|
|
3819
|
-
|
|
3820
|
-
|
|
3821
|
-
|
|
3822
|
-
|
|
3823
|
-
|
|
3824
|
-
|
|
3825
|
-
|
|
3826
|
-
|
|
3848
|
+
return this.processSegmentGroup(this.injector, this.config, rootSegmentGroup, PRIMARY_OUTLET)
|
|
3849
|
+
.pipe(map(children => {
|
|
3850
|
+
if (children === null) {
|
|
3851
|
+
return null;
|
|
3852
|
+
}
|
|
3853
|
+
// Use Object.freeze to prevent readers of the Router state from modifying it outside of a
|
|
3854
|
+
// navigation, resulting in the router being out of sync with the browser.
|
|
3855
|
+
const root = new ActivatedRouteSnapshot([], Object.freeze({}), Object.freeze({ ...this.urlTree.queryParams }), this.urlTree.fragment, {}, PRIMARY_OUTLET, this.rootComponentType, null, this.urlTree.root, -1, {});
|
|
3856
|
+
const rootNode = new TreeNode(root, children);
|
|
3857
|
+
const routeState = new RouterStateSnapshot(this.url, rootNode);
|
|
3858
|
+
this.inheritParamsAndData(routeState._root);
|
|
3859
|
+
return routeState;
|
|
3860
|
+
}));
|
|
3827
3861
|
}
|
|
3828
3862
|
inheritParamsAndData(routeNode) {
|
|
3829
3863
|
const route = routeNode.value;
|
|
@@ -3832,11 +3866,11 @@ class Recognizer {
|
|
|
3832
3866
|
route.data = Object.freeze(i.data);
|
|
3833
3867
|
routeNode.children.forEach(n => this.inheritParamsAndData(n));
|
|
3834
3868
|
}
|
|
3835
|
-
processSegmentGroup(config, segmentGroup, outlet) {
|
|
3869
|
+
processSegmentGroup(injector, config, segmentGroup, outlet) {
|
|
3836
3870
|
if (segmentGroup.segments.length === 0 && segmentGroup.hasChildren()) {
|
|
3837
|
-
return this.processChildren(config, segmentGroup);
|
|
3871
|
+
return this.processChildren(injector, config, segmentGroup);
|
|
3838
3872
|
}
|
|
3839
|
-
return this.processSegment(config, segmentGroup, segmentGroup.segments, outlet);
|
|
3873
|
+
return this.processSegment(injector, config, segmentGroup, segmentGroup.segments, outlet);
|
|
3840
3874
|
}
|
|
3841
3875
|
/**
|
|
3842
3876
|
* Matches every child outlet in the `segmentGroup` to a `Route` in the config. Returns `null` if
|
|
@@ -3846,102 +3880,125 @@ class Recognizer {
|
|
|
3846
3880
|
* @param segmentGroup - The `UrlSegmentGroup` whose children need to be matched against the
|
|
3847
3881
|
* config.
|
|
3848
3882
|
*/
|
|
3849
|
-
processChildren(config, segmentGroup) {
|
|
3850
|
-
|
|
3851
|
-
|
|
3883
|
+
processChildren(injector, config, segmentGroup) {
|
|
3884
|
+
return from(Object.keys(segmentGroup.children))
|
|
3885
|
+
.pipe(concatMap(childOutlet => {
|
|
3852
3886
|
const child = segmentGroup.children[childOutlet];
|
|
3853
|
-
// Sort the config so that routes with outlets that match the one being activated
|
|
3854
|
-
// first, followed by routes for other outlets, which might match if they have
|
|
3887
|
+
// Sort the config so that routes with outlets that match the one being activated
|
|
3888
|
+
// appear first, followed by routes for other outlets, which might match if they have
|
|
3889
|
+
// an empty path.
|
|
3855
3890
|
const sortedConfig = sortByMatchingOutlets(config, childOutlet);
|
|
3856
|
-
|
|
3857
|
-
|
|
3858
|
-
|
|
3859
|
-
// outlet, return `null`.
|
|
3891
|
+
return this.processSegmentGroup(injector, sortedConfig, child, childOutlet);
|
|
3892
|
+
}), scan((children, outletChildren) => {
|
|
3893
|
+
if (!children || !outletChildren)
|
|
3860
3894
|
return null;
|
|
3861
|
-
}
|
|
3862
3895
|
children.push(...outletChildren);
|
|
3863
|
-
|
|
3864
|
-
|
|
3865
|
-
|
|
3866
|
-
|
|
3867
|
-
|
|
3868
|
-
|
|
3869
|
-
//
|
|
3870
|
-
|
|
3871
|
-
|
|
3872
|
-
|
|
3873
|
-
|
|
3874
|
-
|
|
3875
|
-
}
|
|
3876
|
-
processSegment(config, segmentGroup, segments, outlet) {
|
|
3877
|
-
for (const r of config) {
|
|
3878
|
-
const children = this.processSegmentAgainstRoute(r, segmentGroup, segments, outlet);
|
|
3879
|
-
if (children !== null) {
|
|
3880
|
-
return children;
|
|
3896
|
+
return children;
|
|
3897
|
+
}), takeWhile(children => children !== null), defaultIfEmpty(null), last$1(), map(children => {
|
|
3898
|
+
if (children === null)
|
|
3899
|
+
return null;
|
|
3900
|
+
// Because we may have matched two outlets to the same empty path segment, we can have
|
|
3901
|
+
// multiple activated results for the same outlet. We should merge the children of
|
|
3902
|
+
// these results so the final return value is only one `TreeNode` per outlet.
|
|
3903
|
+
const mergedChildren = mergeEmptyPathMatches(children);
|
|
3904
|
+
if (typeof ngDevMode === 'undefined' || ngDevMode) {
|
|
3905
|
+
// This should really never happen - we are only taking the first match for each
|
|
3906
|
+
// outlet and merge the empty path matches.
|
|
3907
|
+
checkOutletNameUniqueness(mergedChildren);
|
|
3881
3908
|
}
|
|
3882
|
-
|
|
3883
|
-
|
|
3884
|
-
|
|
3885
|
-
|
|
3886
|
-
|
|
3909
|
+
sortActivatedRouteSnapshots(mergedChildren);
|
|
3910
|
+
return mergedChildren;
|
|
3911
|
+
}));
|
|
3912
|
+
}
|
|
3913
|
+
processSegment(injector, routes, segmentGroup, segments, outlet) {
|
|
3914
|
+
return from(routes).pipe(concatMap(r => {
|
|
3915
|
+
return this.processSegmentAgainstRoute(r._injector ?? injector, r, segmentGroup, segments, outlet);
|
|
3916
|
+
}), first((x) => !!x), catchError(e => {
|
|
3917
|
+
if (e instanceof EmptyError) {
|
|
3918
|
+
if (noLeftoversInUrl(segmentGroup, segments, outlet)) {
|
|
3919
|
+
return of([]);
|
|
3920
|
+
}
|
|
3921
|
+
return of(null);
|
|
3922
|
+
}
|
|
3923
|
+
throw e;
|
|
3924
|
+
}));
|
|
3887
3925
|
}
|
|
3888
|
-
processSegmentAgainstRoute(route, rawSegment, segments, outlet) {
|
|
3926
|
+
processSegmentAgainstRoute(injector, route, rawSegment, segments, outlet) {
|
|
3889
3927
|
if (route.redirectTo || !isImmediateMatch(route, rawSegment, segments, outlet))
|
|
3890
|
-
return null;
|
|
3891
|
-
let
|
|
3892
|
-
let consumedSegments = [];
|
|
3893
|
-
let remainingSegments = [];
|
|
3928
|
+
return of(null);
|
|
3929
|
+
let matchResult;
|
|
3894
3930
|
if (route.path === '**') {
|
|
3895
3931
|
const params = segments.length > 0 ? last(segments).parameters : {};
|
|
3896
3932
|
const pathIndexShift = getPathIndexShift(rawSegment) + segments.length;
|
|
3897
|
-
snapshot = new ActivatedRouteSnapshot(segments, params, Object.freeze({ ...this.urlTree.queryParams }), this.urlTree.fragment, getData(route), getOutlet(route), route.component ?? route._loadedComponent ?? null, route, getSourceSegmentGroup(rawSegment), pathIndexShift, getResolve(route),
|
|
3933
|
+
const snapshot = new ActivatedRouteSnapshot(segments, params, Object.freeze({ ...this.urlTree.queryParams }), this.urlTree.fragment, getData(route), getOutlet(route), route.component ?? route._loadedComponent ?? null, route, getSourceSegmentGroup(rawSegment), pathIndexShift, getResolve(route),
|
|
3898
3934
|
// NG_DEV_MODE is used to prevent the getCorrectedPathIndexShift function from affecting
|
|
3899
3935
|
// production bundle size. This value is intended only to surface a warning to users
|
|
3900
3936
|
// depending on `relativeLinkResolution: 'legacy'` in dev mode.
|
|
3901
|
-
(NG_DEV_MODE$
|
|
3937
|
+
(NG_DEV_MODE$3 ? getCorrectedPathIndexShift(rawSegment) + segments.length :
|
|
3902
3938
|
pathIndexShift));
|
|
3939
|
+
matchResult = of({
|
|
3940
|
+
snapshot,
|
|
3941
|
+
consumedSegments: [],
|
|
3942
|
+
remainingSegments: [],
|
|
3943
|
+
});
|
|
3903
3944
|
}
|
|
3904
3945
|
else {
|
|
3905
|
-
|
|
3906
|
-
|
|
3907
|
-
|
|
3908
|
-
|
|
3909
|
-
|
|
3910
|
-
|
|
3911
|
-
|
|
3912
|
-
|
|
3913
|
-
|
|
3946
|
+
matchResult =
|
|
3947
|
+
matchWithChecks(rawSegment, route, segments, injector, this.urlSerializer)
|
|
3948
|
+
.pipe(map(({ matched, consumedSegments, remainingSegments, parameters }) => {
|
|
3949
|
+
if (!matched) {
|
|
3950
|
+
return null;
|
|
3951
|
+
}
|
|
3952
|
+
const pathIndexShift = getPathIndexShift(rawSegment) + consumedSegments.length;
|
|
3953
|
+
const snapshot = new ActivatedRouteSnapshot(consumedSegments, parameters, Object.freeze({ ...this.urlTree.queryParams }), this.urlTree.fragment, getData(route), getOutlet(route), route.component ?? route._loadedComponent ?? null, route, getSourceSegmentGroup(rawSegment), pathIndexShift, getResolve(route), (NG_DEV_MODE$3 ?
|
|
3954
|
+
getCorrectedPathIndexShift(rawSegment) + consumedSegments.length :
|
|
3955
|
+
pathIndexShift));
|
|
3956
|
+
return { snapshot, consumedSegments, remainingSegments };
|
|
3957
|
+
}));
|
|
3914
3958
|
}
|
|
3915
|
-
|
|
3916
|
-
|
|
3917
|
-
|
|
3918
|
-
// snapshots and don't handle redirects here. That should have been done in
|
|
3919
|
-
// `applyRedirects`.
|
|
3920
|
-
childConfig.filter(c => c.redirectTo === undefined), this.relativeLinkResolution);
|
|
3921
|
-
if (slicedSegments.length === 0 && segmentGroup.hasChildren()) {
|
|
3922
|
-
const children = this.processChildren(childConfig, segmentGroup);
|
|
3923
|
-
if (children === null) {
|
|
3924
|
-
return null;
|
|
3959
|
+
return matchResult.pipe(switchMap((result) => {
|
|
3960
|
+
if (result === null) {
|
|
3961
|
+
return of(null);
|
|
3925
3962
|
}
|
|
3926
|
-
|
|
3927
|
-
|
|
3928
|
-
|
|
3929
|
-
|
|
3930
|
-
|
|
3931
|
-
|
|
3932
|
-
|
|
3933
|
-
|
|
3934
|
-
|
|
3935
|
-
|
|
3936
|
-
|
|
3937
|
-
|
|
3938
|
-
|
|
3939
|
-
|
|
3940
|
-
|
|
3941
|
-
|
|
3942
|
-
|
|
3943
|
-
|
|
3944
|
-
|
|
3963
|
+
const { snapshot, consumedSegments, remainingSegments } = result;
|
|
3964
|
+
// If the route has an injector created from providers, we should start using that.
|
|
3965
|
+
injector = route._injector ?? injector;
|
|
3966
|
+
const childInjector = route._loadedInjector ?? injector;
|
|
3967
|
+
const childConfig = getChildConfig(route);
|
|
3968
|
+
const { segmentGroup, slicedSegments } = split(rawSegment, consumedSegments, remainingSegments,
|
|
3969
|
+
// Filter out routes with redirectTo because we are trying to create activated route
|
|
3970
|
+
// snapshots and don't handle redirects here. That should have been done in
|
|
3971
|
+
// `applyRedirects`.
|
|
3972
|
+
childConfig.filter(c => c.redirectTo === undefined), this.relativeLinkResolution);
|
|
3973
|
+
if (slicedSegments.length === 0 && segmentGroup.hasChildren()) {
|
|
3974
|
+
return this.processChildren(childInjector, childConfig, segmentGroup).pipe(map(children => {
|
|
3975
|
+
if (children === null) {
|
|
3976
|
+
return null;
|
|
3977
|
+
}
|
|
3978
|
+
return [new TreeNode(snapshot, children)];
|
|
3979
|
+
}));
|
|
3980
|
+
}
|
|
3981
|
+
if (childConfig.length === 0 && slicedSegments.length === 0) {
|
|
3982
|
+
return of([new TreeNode(snapshot, [])]);
|
|
3983
|
+
}
|
|
3984
|
+
const matchedOnOutlet = getOutlet(route) === outlet;
|
|
3985
|
+
// If we matched a config due to empty path match on a different outlet, we need to
|
|
3986
|
+
// continue passing the current outlet for the segment rather than switch to PRIMARY.
|
|
3987
|
+
// Note that we switch to primary when we have a match because outlet configs look like
|
|
3988
|
+
// this: {path: 'a', outlet: 'a', children: [
|
|
3989
|
+
// {path: 'b', component: B},
|
|
3990
|
+
// {path: 'c', component: C},
|
|
3991
|
+
// ]}
|
|
3992
|
+
// Notice that the children of the named outlet are configured with the primary outlet
|
|
3993
|
+
return this
|
|
3994
|
+
.processSegment(childInjector, childConfig, segmentGroup, slicedSegments, matchedOnOutlet ? PRIMARY_OUTLET : outlet)
|
|
3995
|
+
.pipe(map(children => {
|
|
3996
|
+
if (children === null) {
|
|
3997
|
+
return null;
|
|
3998
|
+
}
|
|
3999
|
+
return [new TreeNode(snapshot, children)];
|
|
4000
|
+
}));
|
|
4001
|
+
}));
|
|
3945
4002
|
}
|
|
3946
4003
|
}
|
|
3947
4004
|
function sortActivatedRouteSnapshots(nodes) {
|
|
@@ -3967,9 +4024,9 @@ function hasEmptyPathConfig(node) {
|
|
|
3967
4024
|
return config && config.path === '' && config.redirectTo === undefined;
|
|
3968
4025
|
}
|
|
3969
4026
|
/**
|
|
3970
|
-
* Finds `TreeNode`s with matching empty path route configs and merges them into `TreeNode` with
|
|
3971
|
-
* children from each duplicate. This is necessary because different outlets can match a
|
|
3972
|
-
* empty path route config and the results need to then be merged.
|
|
4027
|
+
* Finds `TreeNode`s with matching empty path route configs and merges them into `TreeNode` with
|
|
4028
|
+
* the children from each duplicate. This is necessary because different outlets can match a
|
|
4029
|
+
* single empty path route config and the results need to then be merged.
|
|
3973
4030
|
*/
|
|
3974
4031
|
function mergeEmptyPathMatches(nodes) {
|
|
3975
4032
|
const result = [];
|
|
@@ -3990,9 +4047,9 @@ function mergeEmptyPathMatches(nodes) {
|
|
|
3990
4047
|
}
|
|
3991
4048
|
}
|
|
3992
4049
|
// For each node which has children from multiple sources, we need to recompute a new `TreeNode`
|
|
3993
|
-
// by also merging those children. This is necessary when there are multiple empty path configs
|
|
3994
|
-
// a row. Put another way: whenever we combine children of two nodes, we need to also check
|
|
3995
|
-
// of those children can be combined into a single node as well.
|
|
4050
|
+
// by also merging those children. This is necessary when there are multiple empty path configs
|
|
4051
|
+
// in a row. Put another way: whenever we combine children of two nodes, we need to also check
|
|
4052
|
+
// if any of those children can be combined into a single node as well.
|
|
3996
4053
|
for (const mergedNode of mergedNodes) {
|
|
3997
4054
|
const mergedChildren = mergeEmptyPathMatches(mergedNode.children);
|
|
3998
4055
|
result.push(new TreeNode(mergedNode.value, mergedChildren));
|
|
@@ -4050,8 +4107,8 @@ function getResolve(route) {
|
|
|
4050
4107
|
* Use of this source code is governed by an MIT-style license that can be
|
|
4051
4108
|
* found in the LICENSE file at https://angular.io/license
|
|
4052
4109
|
*/
|
|
4053
|
-
function recognize(rootComponentType, config, serializer, paramsInheritanceStrategy, relativeLinkResolution) {
|
|
4054
|
-
return mergeMap(t => recognize$1(rootComponentType, config, t.urlAfterRedirects, serializer(t.urlAfterRedirects), paramsInheritanceStrategy, relativeLinkResolution)
|
|
4110
|
+
function recognize(injector, rootComponentType, config, serializer, paramsInheritanceStrategy, relativeLinkResolution) {
|
|
4111
|
+
return mergeMap(t => recognize$1(injector, rootComponentType, config, t.urlAfterRedirects, serializer.serialize(t.urlAfterRedirects), serializer, paramsInheritanceStrategy, relativeLinkResolution)
|
|
4055
4112
|
.pipe(map(targetSnapshot => ({ ...t, targetSnapshot }))));
|
|
4056
4113
|
}
|
|
4057
4114
|
|
|
@@ -4213,7 +4270,7 @@ class DefaultRouteReuseStrategy extends BaseRouteReuseStrategy {
|
|
|
4213
4270
|
* Use of this source code is governed by an MIT-style license that can be
|
|
4214
4271
|
* found in the LICENSE file at https://angular.io/license
|
|
4215
4272
|
*/
|
|
4216
|
-
const NG_DEV_MODE$
|
|
4273
|
+
const NG_DEV_MODE$2 = typeof ngDevMode === 'undefined' || !!ngDevMode;
|
|
4217
4274
|
/**
|
|
4218
4275
|
* The [DI token](guide/glossary/#di-token) for a router configuration.
|
|
4219
4276
|
*
|
|
@@ -4247,7 +4304,7 @@ class RouterConfigLoader {
|
|
|
4247
4304
|
if (this.onLoadEndListener) {
|
|
4248
4305
|
this.onLoadEndListener(route);
|
|
4249
4306
|
}
|
|
4250
|
-
NG_DEV_MODE$
|
|
4307
|
+
NG_DEV_MODE$2 && assertStandalone(route.path ?? '', component);
|
|
4251
4308
|
route._loadedComponent = component;
|
|
4252
4309
|
}), finalize(() => {
|
|
4253
4310
|
this.componentLoaders.delete(route);
|
|
@@ -4290,7 +4347,7 @@ class RouterConfigLoader {
|
|
|
4290
4347
|
rawRoutes = flatten(injector.get(ROUTES, [], InjectFlags.Self | InjectFlags.Optional));
|
|
4291
4348
|
}
|
|
4292
4349
|
const routes = rawRoutes.map(standardizeConfig);
|
|
4293
|
-
NG_DEV_MODE$
|
|
4350
|
+
NG_DEV_MODE$2 && validateConfig(routes, route.path, requireStandaloneComponents);
|
|
4294
4351
|
return { routes, injector };
|
|
4295
4352
|
}), finalize(() => {
|
|
4296
4353
|
this.childrenLoaders.delete(route);
|
|
@@ -4312,9 +4369,9 @@ class RouterConfigLoader {
|
|
|
4312
4369
|
}));
|
|
4313
4370
|
}
|
|
4314
4371
|
}
|
|
4315
|
-
RouterConfigLoader.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
4316
|
-
RouterConfigLoader.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
4317
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
4372
|
+
RouterConfigLoader.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterConfigLoader, deps: [{ token: i0.Injector }, { token: i0.Compiler }], target: i0.ɵɵFactoryTarget.Injectable });
|
|
4373
|
+
RouterConfigLoader.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterConfigLoader });
|
|
4374
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterConfigLoader, decorators: [{
|
|
4318
4375
|
type: Injectable
|
|
4319
4376
|
}], ctorParameters: function () { return [{ type: i0.Injector }, { type: i0.Compiler }]; } });
|
|
4320
4377
|
|
|
@@ -4356,19 +4413,13 @@ class DefaultUrlHandlingStrategy {
|
|
|
4356
4413
|
* Use of this source code is governed by an MIT-style license that can be
|
|
4357
4414
|
* found in the LICENSE file at https://angular.io/license
|
|
4358
4415
|
*/
|
|
4359
|
-
const NG_DEV_MODE = typeof ngDevMode === 'undefined' || !!ngDevMode;
|
|
4416
|
+
const NG_DEV_MODE$1 = typeof ngDevMode === 'undefined' || !!ngDevMode;
|
|
4360
4417
|
function defaultErrorHandler(error) {
|
|
4361
4418
|
throw error;
|
|
4362
4419
|
}
|
|
4363
4420
|
function defaultMalformedUriErrorHandler(error, urlSerializer, url) {
|
|
4364
4421
|
return urlSerializer.parse('/');
|
|
4365
4422
|
}
|
|
4366
|
-
/**
|
|
4367
|
-
* @internal
|
|
4368
|
-
*/
|
|
4369
|
-
function defaultRouterHook(snapshot, runExtras) {
|
|
4370
|
-
return of(null);
|
|
4371
|
-
}
|
|
4372
4423
|
/**
|
|
4373
4424
|
* The equivalent `IsActiveMatchOptions` options for `Router.isActive` is called with `true`
|
|
4374
4425
|
* (exact = true).
|
|
@@ -4448,13 +4499,12 @@ class Router {
|
|
|
4448
4499
|
this.navigated = false;
|
|
4449
4500
|
this.lastSuccessfulId = -1;
|
|
4450
4501
|
/**
|
|
4451
|
-
*
|
|
4452
|
-
* either before or after the preactivation phase.
|
|
4502
|
+
* Hook that enables you to pause navigation after the preactivation phase.
|
|
4453
4503
|
* Used by `RouterModule`.
|
|
4454
4504
|
*
|
|
4455
4505
|
* @internal
|
|
4456
4506
|
*/
|
|
4457
|
-
this.
|
|
4507
|
+
this.afterPreactivation = () => of(void 0);
|
|
4458
4508
|
/**
|
|
4459
4509
|
* A strategy for extracting and merging URLs.
|
|
4460
4510
|
* Used for AngularJS to Angular migrations.
|
|
@@ -4634,7 +4684,7 @@ class Router {
|
|
|
4634
4684
|
};
|
|
4635
4685
|
}),
|
|
4636
4686
|
// Recognize
|
|
4637
|
-
recognize(this.rootComponentType, this.config,
|
|
4687
|
+
recognize(this.ngModule.injector, this.rootComponentType, this.config, this.urlSerializer, this.paramsInheritanceStrategy, this.relativeLinkResolution),
|
|
4638
4688
|
// Update URL if in `eager` update mode
|
|
4639
4689
|
tap(t => {
|
|
4640
4690
|
if (this.urlUpdateStrategy === 'eager') {
|
|
@@ -4679,17 +4729,6 @@ class Router {
|
|
|
4679
4729
|
}
|
|
4680
4730
|
}
|
|
4681
4731
|
}),
|
|
4682
|
-
// Before Preactivation
|
|
4683
|
-
switchTap(t => {
|
|
4684
|
-
const { targetSnapshot, id: navigationId, extractedUrl: appliedUrlTree, rawUrl: rawUrlTree, extras: { skipLocationChange, replaceUrl } } = t;
|
|
4685
|
-
return this.hooks.beforePreactivation(targetSnapshot, {
|
|
4686
|
-
navigationId,
|
|
4687
|
-
appliedUrlTree,
|
|
4688
|
-
rawUrlTree,
|
|
4689
|
-
skipLocationChange: !!skipLocationChange,
|
|
4690
|
-
replaceUrl: !!replaceUrl,
|
|
4691
|
-
});
|
|
4692
|
-
}),
|
|
4693
4732
|
// --- GUARDS ---
|
|
4694
4733
|
tap(t => {
|
|
4695
4734
|
const guardsStart = new GuardsCheckStart(t.id, this.serializeUrl(t.extractedUrl), this.serializeUrl(t.urlAfterRedirects), t.targetSnapshot);
|
|
@@ -4736,18 +4775,7 @@ class Router {
|
|
|
4736
4775
|
}));
|
|
4737
4776
|
}
|
|
4738
4777
|
return undefined;
|
|
4739
|
-
}),
|
|
4740
|
-
// --- AFTER PREACTIVATION ---
|
|
4741
|
-
switchTap((t) => {
|
|
4742
|
-
const { targetSnapshot, id: navigationId, extractedUrl: appliedUrlTree, rawUrl: rawUrlTree, extras: { skipLocationChange, replaceUrl } } = t;
|
|
4743
|
-
return this.hooks.afterPreactivation(targetSnapshot, {
|
|
4744
|
-
navigationId,
|
|
4745
|
-
appliedUrlTree,
|
|
4746
|
-
rawUrlTree,
|
|
4747
|
-
skipLocationChange: !!skipLocationChange,
|
|
4748
|
-
replaceUrl: !!replaceUrl,
|
|
4749
|
-
});
|
|
4750
|
-
}),
|
|
4778
|
+
}), switchTap(() => this.afterPreactivation()),
|
|
4751
4779
|
// --- LOAD COMPONENTS ---
|
|
4752
4780
|
switchTap((t) => {
|
|
4753
4781
|
const loadComponents = (route) => {
|
|
@@ -4964,7 +4992,7 @@ class Router {
|
|
|
4964
4992
|
* ```
|
|
4965
4993
|
*/
|
|
4966
4994
|
resetConfig(config) {
|
|
4967
|
-
NG_DEV_MODE && validateConfig(config);
|
|
4995
|
+
NG_DEV_MODE$1 && validateConfig(config);
|
|
4968
4996
|
this.config = config.map(standardizeConfig);
|
|
4969
4997
|
this.navigated = false;
|
|
4970
4998
|
this.lastSuccessfulId = -1;
|
|
@@ -5319,9 +5347,9 @@ class Router {
|
|
|
5319
5347
|
return { navigationId };
|
|
5320
5348
|
}
|
|
5321
5349
|
}
|
|
5322
|
-
Router.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5323
|
-
Router.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5324
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5350
|
+
Router.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: Router, deps: "invalid", target: i0.ɵɵFactoryTarget.Injectable });
|
|
5351
|
+
Router.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: Router });
|
|
5352
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: Router, decorators: [{
|
|
5325
5353
|
type: Injectable
|
|
5326
5354
|
}], ctorParameters: function () { return [{ type: i0.Type }, { type: UrlSerializer }, { type: ChildrenOutletContexts }, { type: i3.Location }, { type: i0.Injector }, { type: i0.Compiler }, { type: undefined }]; } });
|
|
5327
5355
|
function validateCommands(commands) {
|
|
@@ -5520,9 +5548,9 @@ class RouterLink {
|
|
|
5520
5548
|
});
|
|
5521
5549
|
}
|
|
5522
5550
|
}
|
|
5523
|
-
RouterLink.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5524
|
-
RouterLink.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.
|
|
5525
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5551
|
+
RouterLink.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterLink, deps: [{ token: Router }, { token: ActivatedRoute }, { token: 'tabindex', attribute: true }, { token: i0.Renderer2 }, { token: i0.ElementRef }], target: i0.ɵɵFactoryTarget.Directive });
|
|
5552
|
+
RouterLink.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.3", type: RouterLink, selector: ":not(a):not(area)[routerLink]", inputs: { queryParams: "queryParams", fragment: "fragment", queryParamsHandling: "queryParamsHandling", preserveFragment: "preserveFragment", skipLocationChange: "skipLocationChange", replaceUrl: "replaceUrl", state: "state", relativeTo: "relativeTo", routerLink: "routerLink" }, host: { listeners: { "click": "onClick()" } }, usesOnChanges: true, ngImport: i0 });
|
|
5553
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterLink, decorators: [{
|
|
5526
5554
|
type: Directive,
|
|
5527
5555
|
args: [{ selector: ':not(a):not(area)[routerLink]' }]
|
|
5528
5556
|
}], ctorParameters: function () { return [{ type: Router }, { type: ActivatedRoute }, { type: undefined, decorators: [{
|
|
@@ -5639,9 +5667,9 @@ class RouterLinkWithHref {
|
|
|
5639
5667
|
});
|
|
5640
5668
|
}
|
|
5641
5669
|
}
|
|
5642
|
-
RouterLinkWithHref.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5643
|
-
RouterLinkWithHref.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.
|
|
5644
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5670
|
+
RouterLinkWithHref.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterLinkWithHref, deps: [{ token: Router }, { token: ActivatedRoute }, { token: i3.LocationStrategy }], target: i0.ɵɵFactoryTarget.Directive });
|
|
5671
|
+
RouterLinkWithHref.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.3", type: RouterLinkWithHref, selector: "a[routerLink],area[routerLink]", inputs: { target: "target", queryParams: "queryParams", fragment: "fragment", queryParamsHandling: "queryParamsHandling", preserveFragment: "preserveFragment", skipLocationChange: "skipLocationChange", replaceUrl: "replaceUrl", state: "state", relativeTo: "relativeTo", routerLink: "routerLink" }, host: { listeners: { "click": "onClick($event.button,$event.ctrlKey,$event.shiftKey,$event.altKey,$event.metaKey)" }, properties: { "attr.target": "this.target", "attr.href": "this.href" } }, usesOnChanges: true, ngImport: i0 });
|
|
5672
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterLinkWithHref, decorators: [{
|
|
5645
5673
|
type: Directive,
|
|
5646
5674
|
args: [{ selector: 'a[routerLink],area[routerLink]' }]
|
|
5647
5675
|
}], ctorParameters: function () { return [{ type: Router }, { type: ActivatedRoute }, { type: i3.LocationStrategy }]; }, propDecorators: { target: [{
|
|
@@ -5866,9 +5894,9 @@ class RouterLinkActive {
|
|
|
5866
5894
|
this.links.some(isActiveCheckFn) || this.linksWithHrefs.some(isActiveCheckFn);
|
|
5867
5895
|
}
|
|
5868
5896
|
}
|
|
5869
|
-
RouterLinkActive.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5870
|
-
RouterLinkActive.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.
|
|
5871
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5897
|
+
RouterLinkActive.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterLinkActive, deps: [{ token: Router }, { token: i0.ElementRef }, { token: i0.Renderer2 }, { token: i0.ChangeDetectorRef }, { token: RouterLink, optional: true }, { token: RouterLinkWithHref, optional: true }], target: i0.ɵɵFactoryTarget.Directive });
|
|
5898
|
+
RouterLinkActive.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.1.0-next.3", type: RouterLinkActive, selector: "[routerLinkActive]", inputs: { routerLinkActiveOptions: "routerLinkActiveOptions", ariaCurrentWhenActive: "ariaCurrentWhenActive", routerLinkActive: "routerLinkActive" }, outputs: { isActiveChange: "isActiveChange" }, queries: [{ propertyName: "links", predicate: RouterLink, descendants: true }, { propertyName: "linksWithHrefs", predicate: RouterLinkWithHref, descendants: true }], exportAs: ["routerLinkActive"], usesOnChanges: true, ngImport: i0 });
|
|
5899
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterLinkActive, decorators: [{
|
|
5872
5900
|
type: Directive,
|
|
5873
5901
|
args: [{
|
|
5874
5902
|
selector: '[routerLinkActive]',
|
|
@@ -5971,9 +5999,9 @@ class DefaultTitleStrategy extends TitleStrategy {
|
|
|
5971
5999
|
}
|
|
5972
6000
|
}
|
|
5973
6001
|
}
|
|
5974
|
-
DefaultTitleStrategy.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5975
|
-
DefaultTitleStrategy.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
5976
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6002
|
+
DefaultTitleStrategy.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: DefaultTitleStrategy, deps: [{ token: i1.Title }], target: i0.ɵɵFactoryTarget.Injectable });
|
|
6003
|
+
DefaultTitleStrategy.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: DefaultTitleStrategy, providedIn: 'root' });
|
|
6004
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: DefaultTitleStrategy, decorators: [{
|
|
5977
6005
|
type: Injectable,
|
|
5978
6006
|
args: [{ providedIn: 'root' }]
|
|
5979
6007
|
}], ctorParameters: function () { return [{ type: i1.Title }]; } });
|
|
@@ -6010,6 +6038,12 @@ class PreloadAllModules {
|
|
|
6010
6038
|
return fn().pipe(catchError(() => of(null)));
|
|
6011
6039
|
}
|
|
6012
6040
|
}
|
|
6041
|
+
PreloadAllModules.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: PreloadAllModules, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
6042
|
+
PreloadAllModules.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: PreloadAllModules, providedIn: 'root' });
|
|
6043
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: PreloadAllModules, decorators: [{
|
|
6044
|
+
type: Injectable,
|
|
6045
|
+
args: [{ providedIn: 'root' }]
|
|
6046
|
+
}] });
|
|
6013
6047
|
/**
|
|
6014
6048
|
* @description
|
|
6015
6049
|
*
|
|
@@ -6024,6 +6058,12 @@ class NoPreloading {
|
|
|
6024
6058
|
return of(null);
|
|
6025
6059
|
}
|
|
6026
6060
|
}
|
|
6061
|
+
NoPreloading.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: NoPreloading, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
6062
|
+
NoPreloading.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: NoPreloading, providedIn: 'root' });
|
|
6063
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: NoPreloading, decorators: [{
|
|
6064
|
+
type: Injectable,
|
|
6065
|
+
args: [{ providedIn: 'root' }]
|
|
6066
|
+
}] });
|
|
6027
6067
|
/**
|
|
6028
6068
|
* The preloader optimistically loads all router configurations to
|
|
6029
6069
|
* make navigations into lazily-loaded sections of the application faster.
|
|
@@ -6106,9 +6146,9 @@ class RouterPreloader {
|
|
|
6106
6146
|
});
|
|
6107
6147
|
}
|
|
6108
6148
|
}
|
|
6109
|
-
RouterPreloader.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6110
|
-
RouterPreloader.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6111
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6149
|
+
RouterPreloader.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterPreloader, deps: [{ token: Router }, { token: i0.Compiler }, { token: i0.EnvironmentInjector }, { token: PreloadingStrategy }, { token: RouterConfigLoader }], target: i0.ɵɵFactoryTarget.Injectable });
|
|
6150
|
+
RouterPreloader.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterPreloader });
|
|
6151
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterPreloader, decorators: [{
|
|
6112
6152
|
type: Injectable
|
|
6113
6153
|
}], ctorParameters: function () { return [{ type: Router }, { type: i0.Compiler }, { type: i0.EnvironmentInjector }, { type: PreloadingStrategy }, { type: RouterConfigLoader }]; } });
|
|
6114
6154
|
|
|
@@ -6119,6 +6159,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.0",
|
|
|
6119
6159
|
* Use of this source code is governed by an MIT-style license that can be
|
|
6120
6160
|
* found in the LICENSE file at https://angular.io/license
|
|
6121
6161
|
*/
|
|
6162
|
+
const ROUTER_SCROLLER = new InjectionToken('');
|
|
6122
6163
|
class RouterScroller {
|
|
6123
6164
|
constructor(router,
|
|
6124
6165
|
/** @docsNotRequired */ viewportScroller, options = {}) {
|
|
@@ -6194,9 +6235,9 @@ class RouterScroller {
|
|
|
6194
6235
|
}
|
|
6195
6236
|
}
|
|
6196
6237
|
}
|
|
6197
|
-
RouterScroller.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6198
|
-
RouterScroller.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6199
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6238
|
+
RouterScroller.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterScroller, deps: "invalid", target: i0.ɵɵFactoryTarget.Injectable });
|
|
6239
|
+
RouterScroller.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterScroller });
|
|
6240
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterScroller, decorators: [{
|
|
6200
6241
|
type: Injectable
|
|
6201
6242
|
}], ctorParameters: function () { return [{ type: Router }, { type: i3.ViewportScroller }, { type: undefined }]; } });
|
|
6202
6243
|
|
|
@@ -6207,6 +6248,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.0",
|
|
|
6207
6248
|
* Use of this source code is governed by an MIT-style license that can be
|
|
6208
6249
|
* found in the LICENSE file at https://angular.io/license
|
|
6209
6250
|
*/
|
|
6251
|
+
const NG_DEV_MODE = typeof ngDevMode === 'undefined' || ngDevMode;
|
|
6210
6252
|
/**
|
|
6211
6253
|
* The directives defined in the `RouterModule`.
|
|
6212
6254
|
*/
|
|
@@ -6216,11 +6258,15 @@ const ROUTER_DIRECTIVES = [RouterOutlet, RouterLink, RouterLinkWithHref, RouterL
|
|
|
6216
6258
|
*
|
|
6217
6259
|
* @publicApi
|
|
6218
6260
|
*/
|
|
6219
|
-
const ROUTER_CONFIGURATION = new InjectionToken('ROUTER_CONFIGURATION'
|
|
6261
|
+
const ROUTER_CONFIGURATION = new InjectionToken(NG_DEV_MODE ? 'router config' : 'ROUTER_CONFIGURATION', {
|
|
6262
|
+
providedIn: 'root',
|
|
6263
|
+
factory: () => ({}),
|
|
6264
|
+
});
|
|
6220
6265
|
/**
|
|
6221
6266
|
* @docsNotRequired
|
|
6222
6267
|
*/
|
|
6223
|
-
const ROUTER_FORROOT_GUARD = new InjectionToken('ROUTER_FORROOT_GUARD');
|
|
6268
|
+
const ROUTER_FORROOT_GUARD = new InjectionToken(NG_DEV_MODE ? 'router duplicate forRoot guard' : 'ROUTER_FORROOT_GUARD');
|
|
6269
|
+
const ROUTER_PRELOADER = new InjectionToken(NG_DEV_MODE ? 'router preloader' : '');
|
|
6224
6270
|
const ROUTER_PROVIDERS = [
|
|
6225
6271
|
Location,
|
|
6226
6272
|
{ provide: UrlSerializer, useClass: DefaultUrlSerializer },
|
|
@@ -6235,10 +6281,6 @@ const ROUTER_PROVIDERS = [
|
|
|
6235
6281
|
},
|
|
6236
6282
|
ChildrenOutletContexts,
|
|
6237
6283
|
{ provide: ActivatedRoute, useFactory: rootRoute, deps: [Router] },
|
|
6238
|
-
RouterPreloader,
|
|
6239
|
-
NoPreloading,
|
|
6240
|
-
PreloadAllModules,
|
|
6241
|
-
{ provide: ROUTER_CONFIGURATION, useValue: { enableTracing: false } },
|
|
6242
6284
|
RouterConfigLoader,
|
|
6243
6285
|
];
|
|
6244
6286
|
function routerNgProbeToken() {
|
|
@@ -6291,6 +6333,7 @@ class RouterModule {
|
|
|
6291
6333
|
ngModule: RouterModule,
|
|
6292
6334
|
providers: [
|
|
6293
6335
|
ROUTER_PROVIDERS,
|
|
6336
|
+
NG_DEV_MODE ? (config?.enableTracing ? provideTracing() : []) : [],
|
|
6294
6337
|
provideRoutes(routes),
|
|
6295
6338
|
{
|
|
6296
6339
|
provide: ROUTER_FORROOT_GUARD,
|
|
@@ -6298,22 +6341,11 @@ class RouterModule {
|
|
|
6298
6341
|
deps: [[Router, new Optional(), new SkipSelf()]]
|
|
6299
6342
|
},
|
|
6300
6343
|
{ provide: ROUTER_CONFIGURATION, useValue: config ? config : {} },
|
|
6301
|
-
|
|
6302
|
-
|
|
6303
|
-
|
|
6304
|
-
deps: [PlatformLocation, [new Inject(APP_BASE_HREF), new Optional()], ROUTER_CONFIGURATION]
|
|
6305
|
-
},
|
|
6306
|
-
{
|
|
6307
|
-
provide: RouterScroller,
|
|
6308
|
-
useFactory: createRouterScroller,
|
|
6309
|
-
deps: [Router, ViewportScroller, ROUTER_CONFIGURATION]
|
|
6310
|
-
},
|
|
6311
|
-
{
|
|
6312
|
-
provide: PreloadingStrategy,
|
|
6313
|
-
useExisting: config && config.preloadingStrategy ? config.preloadingStrategy :
|
|
6314
|
-
NoPreloading
|
|
6315
|
-
},
|
|
6344
|
+
config?.useHash ? provideHashLocationStrategy() : providePathLocationStrategy(),
|
|
6345
|
+
provideRouterScroller(),
|
|
6346
|
+
config?.preloadingStrategy ? providePreloading(config.preloadingStrategy) : [],
|
|
6316
6347
|
{ provide: NgProbeToken, multi: true, useFactory: routerNgProbeToken },
|
|
6348
|
+
config?.initialNavigation ? provideInitialNavigation(config) : [],
|
|
6317
6349
|
provideRouterInitializer(),
|
|
6318
6350
|
],
|
|
6319
6351
|
};
|
|
@@ -6338,10 +6370,10 @@ class RouterModule {
|
|
|
6338
6370
|
return { ngModule: RouterModule, providers: [provideRoutes(routes)] };
|
|
6339
6371
|
}
|
|
6340
6372
|
}
|
|
6341
|
-
RouterModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6342
|
-
RouterModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "14.1.0-next.
|
|
6343
|
-
RouterModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6344
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.
|
|
6373
|
+
RouterModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterModule, deps: [{ token: ROUTER_FORROOT_GUARD, optional: true }, { token: Router, optional: true }], target: i0.ɵɵFactoryTarget.NgModule });
|
|
6374
|
+
RouterModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterModule, declarations: [RouterOutlet, RouterLink, RouterLinkWithHref, RouterLinkActive, ɵEmptyOutletComponent], exports: [RouterOutlet, RouterLink, RouterLinkWithHref, RouterLinkActive, ɵEmptyOutletComponent] });
|
|
6375
|
+
RouterModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterModule });
|
|
6376
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.3", ngImport: i0, type: RouterModule, decorators: [{
|
|
6345
6377
|
type: NgModule,
|
|
6346
6378
|
args: [{
|
|
6347
6379
|
declarations: ROUTER_DIRECTIVES,
|
|
@@ -6355,18 +6387,28 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.0",
|
|
|
6355
6387
|
}] }, { type: Router, decorators: [{
|
|
6356
6388
|
type: Optional
|
|
6357
6389
|
}] }]; } });
|
|
6358
|
-
function
|
|
6359
|
-
|
|
6360
|
-
|
|
6361
|
-
|
|
6362
|
-
|
|
6390
|
+
function provideRouterScroller() {
|
|
6391
|
+
return {
|
|
6392
|
+
provide: ROUTER_SCROLLER,
|
|
6393
|
+
useFactory: () => {
|
|
6394
|
+
const router = inject(Router);
|
|
6395
|
+
const viewportScroller = inject(ViewportScroller);
|
|
6396
|
+
const config = inject(ROUTER_CONFIGURATION);
|
|
6397
|
+
if (config.scrollOffset) {
|
|
6398
|
+
viewportScroller.setOffset(config.scrollOffset);
|
|
6399
|
+
}
|
|
6400
|
+
return new RouterScroller(router, viewportScroller, config);
|
|
6401
|
+
},
|
|
6402
|
+
};
|
|
6363
6403
|
}
|
|
6364
|
-
function
|
|
6365
|
-
return
|
|
6366
|
-
|
|
6404
|
+
function provideHashLocationStrategy() {
|
|
6405
|
+
return { provide: LocationStrategy, useClass: HashLocationStrategy };
|
|
6406
|
+
}
|
|
6407
|
+
function providePathLocationStrategy() {
|
|
6408
|
+
return { provide: LocationStrategy, useClass: PathLocationStrategy };
|
|
6367
6409
|
}
|
|
6368
6410
|
function provideForRootGuard(router) {
|
|
6369
|
-
if (
|
|
6411
|
+
if (NG_DEV_MODE && router) {
|
|
6370
6412
|
throw new Error(`RouterModule.forRoot() called twice. Lazy loaded modules should use RouterModule.forChild() instead.`);
|
|
6371
6413
|
}
|
|
6372
6414
|
return 'guarded';
|
|
@@ -6403,16 +6445,6 @@ function setupRouter(urlSerializer, contexts, location, injector, compiler, conf
|
|
|
6403
6445
|
}
|
|
6404
6446
|
router.titleStrategy = titleStrategy ?? defaultTitleStrategy;
|
|
6405
6447
|
assignExtraOptionsToRouter(opts, router);
|
|
6406
|
-
if ((typeof ngDevMode === 'undefined' || ngDevMode) && opts.enableTracing) {
|
|
6407
|
-
router.events.subscribe((e) => {
|
|
6408
|
-
// tslint:disable:no-console
|
|
6409
|
-
console.group?.(`Router Event: ${e.constructor.name}`);
|
|
6410
|
-
console.log(stringifyEvent(e));
|
|
6411
|
-
console.log(e);
|
|
6412
|
-
console.groupEnd?.();
|
|
6413
|
-
// tslint:enable:no-console
|
|
6414
|
-
});
|
|
6415
|
-
}
|
|
6416
6448
|
return router;
|
|
6417
6449
|
}
|
|
6418
6450
|
function assignExtraOptionsToRouter(opts, router) {
|
|
@@ -6441,112 +6473,136 @@ function assignExtraOptionsToRouter(opts, router) {
|
|
|
6441
6473
|
function rootRoute(router) {
|
|
6442
6474
|
return router.routerState.root;
|
|
6443
6475
|
}
|
|
6444
|
-
|
|
6445
|
-
|
|
6446
|
-
|
|
6447
|
-
|
|
6448
|
-
* a resolver or a guard executes asynchronously.
|
|
6449
|
-
*
|
|
6450
|
-
* Next, we actually run activation in a `BOOTSTRAP_LISTENER`, using the
|
|
6451
|
-
* `afterPreactivation` hook provided by the router.
|
|
6452
|
-
* The router navigation starts, reaches the point when preactivation is done, and then
|
|
6453
|
-
* pauses. It waits for the hook to be resolved. We then resolve it only in a bootstrap listener.
|
|
6454
|
-
*/
|
|
6455
|
-
class RouterInitializer {
|
|
6456
|
-
constructor(injector) {
|
|
6457
|
-
this.injector = injector;
|
|
6458
|
-
this.initNavigation = false;
|
|
6459
|
-
this.destroyed = false;
|
|
6460
|
-
this.resultOfPreactivationDone = new Subject();
|
|
6461
|
-
}
|
|
6462
|
-
appInitializer() {
|
|
6463
|
-
const p = this.injector.get(LOCATION_INITIALIZED, Promise.resolve(null));
|
|
6464
|
-
return p.then(() => {
|
|
6465
|
-
// If the injector was destroyed, the DI lookups below will fail.
|
|
6466
|
-
if (this.destroyed) {
|
|
6467
|
-
return Promise.resolve(true);
|
|
6468
|
-
}
|
|
6469
|
-
let resolve = null;
|
|
6470
|
-
const res = new Promise(r => resolve = r);
|
|
6471
|
-
const router = this.injector.get(Router);
|
|
6472
|
-
const opts = this.injector.get(ROUTER_CONFIGURATION);
|
|
6473
|
-
if (opts.initialNavigation === 'disabled') {
|
|
6474
|
-
router.setUpLocationChangeListener();
|
|
6475
|
-
resolve(true);
|
|
6476
|
-
}
|
|
6477
|
-
else if (opts.initialNavigation === 'enabledBlocking') {
|
|
6478
|
-
router.hooks.afterPreactivation = () => {
|
|
6479
|
-
// only the initial navigation should be delayed
|
|
6480
|
-
if (!this.initNavigation) {
|
|
6481
|
-
this.initNavigation = true;
|
|
6482
|
-
resolve(true);
|
|
6483
|
-
return this.resultOfPreactivationDone;
|
|
6484
|
-
// subsequent navigations should not be delayed
|
|
6485
|
-
}
|
|
6486
|
-
else {
|
|
6487
|
-
return of(null);
|
|
6488
|
-
}
|
|
6489
|
-
};
|
|
6490
|
-
router.initialNavigation();
|
|
6491
|
-
}
|
|
6492
|
-
else {
|
|
6493
|
-
resolve(true);
|
|
6494
|
-
}
|
|
6495
|
-
return res;
|
|
6496
|
-
});
|
|
6497
|
-
}
|
|
6498
|
-
bootstrapListener(bootstrappedComponentRef) {
|
|
6499
|
-
const opts = this.injector.get(ROUTER_CONFIGURATION);
|
|
6500
|
-
const preloader = this.injector.get(RouterPreloader);
|
|
6501
|
-
const routerScroller = this.injector.get(RouterScroller);
|
|
6502
|
-
const router = this.injector.get(Router);
|
|
6503
|
-
const ref = this.injector.get(ApplicationRef);
|
|
6476
|
+
function getBootstrapListener() {
|
|
6477
|
+
const injector = inject(Injector);
|
|
6478
|
+
return (bootstrappedComponentRef) => {
|
|
6479
|
+
const ref = injector.get(ApplicationRef);
|
|
6504
6480
|
if (bootstrappedComponentRef !== ref.components[0]) {
|
|
6505
6481
|
return;
|
|
6506
6482
|
}
|
|
6483
|
+
const router = injector.get(Router);
|
|
6484
|
+
const bootstrapDone = injector.get(BOOTSTRAP_DONE);
|
|
6507
6485
|
// Default case
|
|
6508
|
-
if (
|
|
6486
|
+
if (injector.get(INITIAL_NAVIGATION, null, InjectFlags.Optional) === null) {
|
|
6509
6487
|
router.initialNavigation();
|
|
6510
6488
|
}
|
|
6511
|
-
|
|
6512
|
-
|
|
6489
|
+
injector.get(ROUTER_PRELOADER, null, InjectFlags.Optional)?.setUpPreloading();
|
|
6490
|
+
injector.get(ROUTER_SCROLLER, null, InjectFlags.Optional)?.init();
|
|
6513
6491
|
router.resetRootComponentType(ref.componentTypes[0]);
|
|
6514
|
-
|
|
6515
|
-
|
|
6516
|
-
}
|
|
6517
|
-
ngOnDestroy() {
|
|
6518
|
-
this.destroyed = true;
|
|
6519
|
-
}
|
|
6520
|
-
}
|
|
6521
|
-
RouterInitializer.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.1.0-next.0", ngImport: i0, type: RouterInitializer, deps: [{ token: i0.Injector }], target: i0.ɵɵFactoryTarget.Injectable });
|
|
6522
|
-
RouterInitializer.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.1.0-next.0", ngImport: i0, type: RouterInitializer });
|
|
6523
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.1.0-next.0", ngImport: i0, type: RouterInitializer, decorators: [{
|
|
6524
|
-
type: Injectable
|
|
6525
|
-
}], ctorParameters: function () { return [{ type: i0.Injector }]; } });
|
|
6526
|
-
function getAppInitializer(r) {
|
|
6527
|
-
return r.appInitializer.bind(r);
|
|
6528
|
-
}
|
|
6529
|
-
function getBootstrapListener(r) {
|
|
6530
|
-
return r.bootstrapListener.bind(r);
|
|
6492
|
+
bootstrapDone.next();
|
|
6493
|
+
bootstrapDone.complete();
|
|
6494
|
+
};
|
|
6531
6495
|
}
|
|
6496
|
+
// TODO(atscott): This should not be in the public API
|
|
6532
6497
|
/**
|
|
6533
6498
|
* A [DI token](guide/glossary/#di-token) for the router initializer that
|
|
6534
6499
|
* is called after the app is bootstrapped.
|
|
6535
6500
|
*
|
|
6536
6501
|
* @publicApi
|
|
6537
6502
|
*/
|
|
6538
|
-
const ROUTER_INITIALIZER = new InjectionToken('Router Initializer');
|
|
6503
|
+
const ROUTER_INITIALIZER = new InjectionToken(NG_DEV_MODE ? 'Router Initializer' : '');
|
|
6504
|
+
function provideInitialNavigation(config) {
|
|
6505
|
+
return [
|
|
6506
|
+
config.initialNavigation === 'disabled' ? provideDisabledInitialNavigation() : [],
|
|
6507
|
+
config.initialNavigation === 'enabledBlocking' ? provideEnabledBlockingInitialNavigation() : [],
|
|
6508
|
+
];
|
|
6509
|
+
}
|
|
6539
6510
|
function provideRouterInitializer() {
|
|
6540
6511
|
return [
|
|
6541
|
-
|
|
6512
|
+
// ROUTER_INITIALIZER token should be removed. It's public API but shouldn't be. We can just
|
|
6513
|
+
// have `getBootstrapListener` directly attached to APP_BOOTSTRAP_LISTENER.
|
|
6514
|
+
{ provide: ROUTER_INITIALIZER, useFactory: getBootstrapListener },
|
|
6515
|
+
{ provide: APP_BOOTSTRAP_LISTENER, multi: true, useExisting: ROUTER_INITIALIZER },
|
|
6516
|
+
];
|
|
6517
|
+
}
|
|
6518
|
+
/**
|
|
6519
|
+
* A subject used to indicate that the bootstrapping phase is done. When initial navigation is
|
|
6520
|
+
* `enabledBlocking`, the first navigation waits until bootstrapping is finished before continuing
|
|
6521
|
+
* to the activation phase.
|
|
6522
|
+
*/
|
|
6523
|
+
const BOOTSTRAP_DONE = new InjectionToken(NG_DEV_MODE ? 'bootstrap done indicator' : '', {
|
|
6524
|
+
factory: () => {
|
|
6525
|
+
return new Subject();
|
|
6526
|
+
}
|
|
6527
|
+
});
|
|
6528
|
+
function provideEnabledBlockingInitialNavigation() {
|
|
6529
|
+
return [
|
|
6530
|
+
{ provide: INITIAL_NAVIGATION, useValue: 'enabledBlocking' },
|
|
6542
6531
|
{
|
|
6543
6532
|
provide: APP_INITIALIZER,
|
|
6544
6533
|
multi: true,
|
|
6545
|
-
|
|
6546
|
-
|
|
6534
|
+
deps: [Injector],
|
|
6535
|
+
useFactory: (injector) => {
|
|
6536
|
+
const locationInitialized = injector.get(LOCATION_INITIALIZED, Promise.resolve(null));
|
|
6537
|
+
let initNavigation = false;
|
|
6538
|
+
return () => {
|
|
6539
|
+
return locationInitialized.then(() => {
|
|
6540
|
+
return new Promise(resolve => {
|
|
6541
|
+
const router = injector.get(Router);
|
|
6542
|
+
const bootstrapDone = injector.get(BOOTSTRAP_DONE);
|
|
6543
|
+
router.afterPreactivation = () => {
|
|
6544
|
+
// only the initial navigation should be delayed
|
|
6545
|
+
if (!initNavigation) {
|
|
6546
|
+
initNavigation = true;
|
|
6547
|
+
resolve(true);
|
|
6548
|
+
return bootstrapDone;
|
|
6549
|
+
// subsequent navigations should not be delayed
|
|
6550
|
+
}
|
|
6551
|
+
else {
|
|
6552
|
+
return of(void 0);
|
|
6553
|
+
}
|
|
6554
|
+
};
|
|
6555
|
+
router.initialNavigation();
|
|
6556
|
+
});
|
|
6557
|
+
});
|
|
6558
|
+
};
|
|
6559
|
+
}
|
|
6547
6560
|
},
|
|
6548
|
-
|
|
6549
|
-
|
|
6561
|
+
];
|
|
6562
|
+
}
|
|
6563
|
+
const INITIAL_NAVIGATION = new InjectionToken(NG_DEV_MODE ? 'initial navigation' : '');
|
|
6564
|
+
function provideDisabledInitialNavigation() {
|
|
6565
|
+
return [
|
|
6566
|
+
{
|
|
6567
|
+
provide: APP_INITIALIZER,
|
|
6568
|
+
multi: true,
|
|
6569
|
+
useFactory: () => {
|
|
6570
|
+
const router = inject(Router);
|
|
6571
|
+
return () => {
|
|
6572
|
+
router.setUpLocationChangeListener();
|
|
6573
|
+
};
|
|
6574
|
+
}
|
|
6575
|
+
},
|
|
6576
|
+
{ provide: INITIAL_NAVIGATION, useValue: 'disabled' }
|
|
6577
|
+
];
|
|
6578
|
+
}
|
|
6579
|
+
function provideTracing() {
|
|
6580
|
+
if (NG_DEV_MODE) {
|
|
6581
|
+
return [{
|
|
6582
|
+
provide: ENVIRONMENT_INITIALIZER,
|
|
6583
|
+
multi: true,
|
|
6584
|
+
useFactory: () => {
|
|
6585
|
+
const router = inject(Router);
|
|
6586
|
+
return () => router.events.subscribe((e) => {
|
|
6587
|
+
// tslint:disable:no-console
|
|
6588
|
+
console.group?.(`Router Event: ${e.constructor.name}`);
|
|
6589
|
+
console.log(stringifyEvent(e));
|
|
6590
|
+
console.log(e);
|
|
6591
|
+
console.groupEnd?.();
|
|
6592
|
+
// tslint:enable:no-console
|
|
6593
|
+
});
|
|
6594
|
+
}
|
|
6595
|
+
}];
|
|
6596
|
+
}
|
|
6597
|
+
else {
|
|
6598
|
+
return [];
|
|
6599
|
+
}
|
|
6600
|
+
}
|
|
6601
|
+
function providePreloading(preloadingStrategy) {
|
|
6602
|
+
return [
|
|
6603
|
+
RouterPreloader,
|
|
6604
|
+
{ provide: ROUTER_PRELOADER, useExisting: RouterPreloader },
|
|
6605
|
+
{ provide: PreloadingStrategy, useExisting: preloadingStrategy },
|
|
6550
6606
|
];
|
|
6551
6607
|
}
|
|
6552
6608
|
|
|
@@ -6560,7 +6616,7 @@ function provideRouterInitializer() {
|
|
|
6560
6616
|
/**
|
|
6561
6617
|
* @publicApi
|
|
6562
6618
|
*/
|
|
6563
|
-
const VERSION = new Version('14.1.0-next.
|
|
6619
|
+
const VERSION = new Version('14.1.0-next.3');
|
|
6564
6620
|
|
|
6565
6621
|
/**
|
|
6566
6622
|
* @license
|
|
@@ -6599,5 +6655,5 @@ const VERSION = new Version('14.1.0-next.0');
|
|
|
6599
6655
|
* Generated bundle index. Do not edit.
|
|
6600
6656
|
*/
|
|
6601
6657
|
|
|
6602
|
-
export { ActivatedRoute, ActivatedRouteSnapshot, ActivationEnd, ActivationStart, BaseRouteReuseStrategy, ChildActivationEnd, ChildActivationStart, ChildrenOutletContexts, DefaultTitleStrategy, DefaultUrlSerializer, GuardsCheckEnd, GuardsCheckStart, NavigationCancel, NavigationEnd, NavigationError, NavigationStart, NoPreloading, OutletContext, PRIMARY_OUTLET, PreloadAllModules, PreloadingStrategy, ROUTER_CONFIGURATION, ROUTER_INITIALIZER, ROUTES, ResolveEnd, ResolveStart, RouteConfigLoadEnd, RouteConfigLoadStart, RouteReuseStrategy, Router, RouterEvent, RouterLink, RouterLinkActive, RouterLinkWithHref, RouterModule, RouterOutlet, RouterPreloader, RouterState, RouterStateSnapshot, RoutesRecognized, Scroll, TitleStrategy, UrlHandlingStrategy, UrlSegment, UrlSegmentGroup, UrlSerializer, UrlTree, VERSION, convertToParamMap, createUrlTreeFromSnapshot, provideRoutes, ɵEmptyOutletComponent, ROUTER_PROVIDERS as ɵROUTER_PROVIDERS, assignExtraOptionsToRouter as ɵassignExtraOptionsToRouter, flatten as ɵflatten };
|
|
6658
|
+
export { ActivatedRoute, ActivatedRouteSnapshot, ActivationEnd, ActivationStart, BaseRouteReuseStrategy, ChildActivationEnd, ChildActivationStart, ChildrenOutletContexts, DefaultTitleStrategy, DefaultUrlSerializer, GuardsCheckEnd, GuardsCheckStart, NavigationCancel, NavigationEnd, NavigationError, NavigationStart, NoPreloading, OutletContext, PRIMARY_OUTLET, PreloadAllModules, PreloadingStrategy, ROUTER_CONFIGURATION, ROUTER_INITIALIZER, ROUTES, ResolveEnd, ResolveStart, RouteConfigLoadEnd, RouteConfigLoadStart, RouteReuseStrategy, Router, RouterEvent, RouterLink, RouterLinkActive, RouterLinkWithHref, RouterModule, RouterOutlet, RouterPreloader, RouterState, RouterStateSnapshot, RoutesRecognized, Scroll, TitleStrategy, UrlHandlingStrategy, UrlSegment, UrlSegmentGroup, UrlSerializer, UrlTree, VERSION, convertToParamMap, createUrlTreeFromSnapshot, provideRoutes, ɵEmptyOutletComponent, ROUTER_PROVIDERS as ɵROUTER_PROVIDERS, assignExtraOptionsToRouter as ɵassignExtraOptionsToRouter, flatten as ɵflatten, providePreloading as ɵprovidePreloading };
|
|
6603
6659
|
//# sourceMappingURL=router.mjs.map
|