diff --git a/modules/@angular/router/rollup.config.js b/modules/@angular/router/rollup.config.js index ad3c6ce884..dbd55d6301 100644 --- a/modules/@angular/router/rollup.config.js +++ b/modules/@angular/router/rollup.config.js @@ -10,27 +10,28 @@ export default { '@angular/platform-browser': 'ng.platformBrowser', '@angular/platform-browser-dynamic': 'ng.platformBrowserDynamic', + 'rxjs/BehaviorSubject': 'Rx', 'rxjs/Observable': 'Rx', 'rxjs/Subject': 'Rx', - 'rxjs/BehaviorSubject': 'Rx', - 'rxjs/Observer': 'Rx', 'rxjs/Subscription': 'Rx', + 'rxjs/util/EmptyError': 'Rx', - 'rxjs/observable/PromiseObservable': 'Rx', // this is wrong, but this stuff has changed in rxjs b.6 so we need to fix it when we update. - 'rxjs/add/operator/map': 'Rx.Observable.prototype', - 'rxjs/add/operator/mergeAll': 'Rx.Observable.prototype', - 'rxjs/add/operator/concatAll': 'Rx.Observable.prototype', - 'rxjs/add/operator/mergeMap': 'Rx.Observable.prototype', - 'rxjs/add/operator/reduce': 'Rx.Observable.prototype', - 'rxjs/add/operator/every': 'Rx.Observable.prototype', - 'rxjs/add/operator/first': 'Rx.Observable.prototype', - 'rxjs/add/operator/catch': 'Rx.Observable.prototype', - 'rxjs/add/operator/last': 'Rx.Observable.prototype', - 'rxjs/add/operator/toPromise': 'Rx.Observable.prototype', 'rxjs/observable/from': 'Rx.Observable', 'rxjs/observable/fromPromise': 'Rx.Observable', 'rxjs/observable/forkJoin': 'Rx.Observable', 'rxjs/observable/of': 'Rx.Observable', - 'rxjs/util/EmptyError': 'Rx.EmptyError' - } + + 'rxjs/operator/toPromise': 'Rx.Observable.prototype', + 'rxjs/operator/map': 'Rx.Observable.prototype', + 'rxjs/operator/mergeAll': 'Rx.Observable.prototype', + 'rxjs/operator/concatAll': 'Rx.Observable.prototype', + 'rxjs/operator/mergeMap': 'Rx.Observable.prototype', + 'rxjs/operator/reduce': 'Rx.Observable.prototype', + 'rxjs/operator/every': 'Rx.Observable.prototype', + 'rxjs/operator/first': 'Rx.Observable.prototype', + 'rxjs/operator/catch': 'Rx.Observable.prototype', + 'rxjs/operator/last': 'Rx.Observable.prototype' + }, + plugins: [ + ] } diff --git a/modules/@angular/router/src/apply_redirects.ts b/modules/@angular/router/src/apply_redirects.ts index 82717104ef..694c051394 100644 --- a/modules/@angular/router/src/apply_redirects.ts +++ b/modules/@angular/router/src/apply_redirects.ts @@ -6,15 +6,16 @@ * found in the LICENSE file at https://angular.io/license */ -import 'rxjs/add/operator/first'; -import 'rxjs/add/operator/catch'; -import 'rxjs/add/operator/concatAll'; - import {Injector} from '@angular/core'; import {Observable} from 'rxjs/Observable'; import {Observer} from 'rxjs/Observer'; import {from} from 'rxjs/observable/from'; import {of } from 'rxjs/observable/of'; +import {_catch} from 'rxjs/operator/catch'; +import {concatAll} from 'rxjs/operator/concatAll'; +import {first} from 'rxjs/operator/first'; +import {map} from 'rxjs/operator/map'; +import {mergeMap} from 'rxjs/operator/mergeMap'; import {EmptyError} from 'rxjs/util/EmptyError'; import {Route, Routes} from './config'; @@ -62,34 +63,38 @@ class ApplyRedirects { private urlTree: UrlTree, private config: Routes) {} apply(): Observable { - return this.expandSegmentGroup(this.injector, this.config, this.urlTree.root, PRIMARY_OUTLET) - .map(rootSegmentGroup => this.createUrlTree(rootSegmentGroup)) - .catch(e => { - if (e instanceof AbsoluteRedirect) { - // after an absolute redirect we do not apply any more redirects! - this.allowRedirects = false; - const group = - new UrlSegmentGroup([], {[PRIMARY_OUTLET]: new UrlSegmentGroup(e.segments, {})}); - // we need to run matching, so we can fetch all lazy-loaded modules - return this.match(group); - } else if (e instanceof NoMatch) { - throw this.noMatchError(e); - } else { - throw e; - } - }); + const expanded$ = + this.expandSegmentGroup(this.injector, this.config, this.urlTree.root, PRIMARY_OUTLET); + const urlTrees$ = map.call( + expanded$, (rootSegmentGroup: UrlSegmentGroup) => this.createUrlTree(rootSegmentGroup)); + return _catch.call(urlTrees$, (e: any) => { + if (e instanceof AbsoluteRedirect) { + // after an absolute redirect we do not apply any more redirects! + this.allowRedirects = false; + const group = + new UrlSegmentGroup([], {[PRIMARY_OUTLET]: new UrlSegmentGroup(e.segments, {})}); + // we need to run matching, so we can fetch all lazy-loaded modules + return this.match(group); + } else if (e instanceof NoMatch) { + throw this.noMatchError(e); + } else { + throw e; + } + }); } private match(segmentGroup: UrlSegmentGroup): Observable { - return this.expandSegmentGroup(this.injector, this.config, segmentGroup, PRIMARY_OUTLET) - .map(rootSegmentGroup => this.createUrlTree(rootSegmentGroup)) - .catch((e): Observable => { - if (e instanceof NoMatch) { - throw this.noMatchError(e); - } else { - throw e; - } - }); + const expanded$ = + this.expandSegmentGroup(this.injector, this.config, segmentGroup, PRIMARY_OUTLET); + const mapped$ = map.call( + expanded$, (rootSegmentGroup: UrlSegmentGroup) => this.createUrlTree(rootSegmentGroup)); + return _catch.call(mapped$, (e: any): Observable => { + if (e instanceof NoMatch) { + throw this.noMatchError(e); + } else { + throw e; + } + }); } private noMatchError(e: NoMatch): any { @@ -107,8 +112,9 @@ class ApplyRedirects { injector: Injector, routes: Route[], segmentGroup: UrlSegmentGroup, outlet: string): Observable { if (segmentGroup.segments.length === 0 && segmentGroup.hasChildren()) { - return this.expandChildren(injector, routes, segmentGroup) - .map(children => new UrlSegmentGroup([], children)); + return map.call( + this.expandChildren(injector, routes, segmentGroup), + (children: any) => new UrlSegmentGroup([], children)); } else { return this.expandSegment( injector, segmentGroup, routes, segmentGroup.segments, outlet, true); @@ -125,22 +131,20 @@ class ApplyRedirects { private expandSegment( injector: Injector, segmentGroup: UrlSegmentGroup, routes: Route[], segments: UrlSegment[], outlet: string, allowRedirects: boolean): Observable { - const processRoutes = - of (...routes) - .map(r => { - return this - .expandSegmentAgainstRoute( - injector, segmentGroup, routes, r, segments, outlet, allowRedirects) - .catch((e) => { - if (e instanceof NoMatch) - return of (null); - else - throw e; - }); - }) - .concatAll(); - - return processRoutes.first(s => !!s).catch((e: any, _: any): Observable => { + const routes$ = of (...routes); + const processedRoutes$ = map.call(routes$, (r: any) => { + const expanded$ = this.expandSegmentAgainstRoute( + injector, segmentGroup, routes, r, segments, outlet, allowRedirects); + return _catch.call(expanded$, (e: any) => { + if (e instanceof NoMatch) + return of (null); + else + throw e; + }); + }); + const concattedProcessedRoutes$ = concatAll.call(processedRoutes$); + const first$ = first.call(concattedProcessedRoutes$, (s: any) => !!s); + return _catch.call(first$, (e: any, _: any): Observable => { if (e instanceof EmptyError) { throw new NoMatch(segmentGroup); } else { @@ -214,25 +218,27 @@ class ApplyRedirects { if (!matched) return noMatch(rawSegmentGroup); const rawSlicedSegments = segments.slice(lastChild); - - return this.getChildConfig(injector, route).mergeMap(routerConfig => { + const childConfig$ = this.getChildConfig(injector, route); + return mergeMap.call(childConfig$, (routerConfig: any) => { const childInjector = routerConfig.injector; const childConfig = routerConfig.routes; const {segmentGroup, slicedSegments} = split(rawSegmentGroup, consumedSegments, rawSlicedSegments, childConfig); if (slicedSegments.length === 0 && segmentGroup.hasChildren()) { - return this.expandChildren(childInjector, childConfig, segmentGroup) - .map(children => new UrlSegmentGroup(consumedSegments, children)); + const expanded$ = this.expandChildren(childInjector, childConfig, segmentGroup); + return map.call( + expanded$, (children: any) => new UrlSegmentGroup(consumedSegments, children)); } else if (childConfig.length === 0 && slicedSegments.length === 0) { return of (new UrlSegmentGroup(consumedSegments, {})); } else { - return this - .expandSegment( - childInjector, segmentGroup, childConfig, slicedSegments, PRIMARY_OUTLET, true) - .map(cs => new UrlSegmentGroup(consumedSegments.concat(cs.segments), cs.children)); + const expanded$ = this.expandSegment( + childInjector, segmentGroup, childConfig, slicedSegments, PRIMARY_OUTLET, true); + return map.call( + expanded$, + (cs: any) => new UrlSegmentGroup(consumedSegments.concat(cs.segments), cs.children)); } }); } @@ -242,12 +248,12 @@ class ApplyRedirects { if (route.children) { return of (new LoadedRouterConfig(route.children, injector, null)); } else if (route.loadChildren) { - return runGuards(injector, route).mergeMap(shouldLoad => { + return mergeMap.call(runGuards(injector, route), (shouldLoad: any) => { if (shouldLoad) { if ((route)._loadedConfig) { return of ((route)._loadedConfig); } else { - return this.configLoader.load(injector, route.loadChildren).map(r => { + return map.call(this.configLoader.load(injector, route.loadChildren), (r: any) => { (route)._loadedConfig = r; return r; }); @@ -265,7 +271,7 @@ class ApplyRedirects { function runGuards(injector: Injector, route: Route): Observable { const canLoad = route.canLoad; if (!canLoad || canLoad.length === 0) return of (true); - const obs = from(canLoad).map(c => { + const obs = map.call(from(canLoad), (c: any) => { const guard = injector.get(c); if (guard.canLoad) { return wrapIntoObservable(guard.canLoad(route)); diff --git a/modules/@angular/router/src/router.ts b/modules/@angular/router/src/router.ts index 4041983058..bd456a160c 100644 --- a/modules/@angular/router/src/router.ts +++ b/modules/@angular/router/src/router.ts @@ -6,12 +6,6 @@ * found in the LICENSE file at https://angular.io/license */ -import 'rxjs/add/operator/map'; -import 'rxjs/add/operator/mergeMap'; -import 'rxjs/add/operator/mergeAll'; -import 'rxjs/add/operator/reduce'; -import 'rxjs/add/operator/every'; - import {Location} from '@angular/common'; import {Compiler, ComponentFactoryResolver, Injector, NgModuleFactoryLoader, ReflectiveInjector, Type} from '@angular/core'; import {Observable} from 'rxjs/Observable'; @@ -19,6 +13,11 @@ import {Subject} from 'rxjs/Subject'; import {Subscription} from 'rxjs/Subscription'; import {from} from 'rxjs/observable/from'; import {of } from 'rxjs/observable/of'; +import {every} from 'rxjs/operator/every'; +import {map} from 'rxjs/operator/map'; +import {mergeAll} from 'rxjs/operator/mergeAll'; +import {mergeMap} from 'rxjs/operator/mergeMap'; +import {reduce} from 'rxjs/operator/reduce'; import {applyRedirects} from './apply_redirects'; import {ResolveData, Routes, validateConfig} from './config'; @@ -476,41 +475,43 @@ export class Router { const storedState = this.currentRouterState; const storedUrl = this.currentUrlTree; - applyRedirects(this.injector, this.configLoader, url, this.config) - .mergeMap(u => { - appliedUrl = u; - return recognize( - this.rootComponentType, this.config, appliedUrl, this.serializeUrl(appliedUrl)); - }) + const redirectsApplied$ = applyRedirects(this.injector, this.configLoader, url, this.config); - .map((newRouterStateSnapshot) => { - this.routerEvents.next(new RoutesRecognized( - id, this.serializeUrl(url), this.serializeUrl(appliedUrl), newRouterStateSnapshot)); - return newRouterStateSnapshot; + const snapshot$ = mergeMap.call(redirectsApplied$, (u: UrlTree) => { + appliedUrl = u; + return recognize( + this.rootComponentType, this.config, appliedUrl, this.serializeUrl(appliedUrl)); + }); - }) - .map((routerStateSnapshot) => { - return createRouterState(routerStateSnapshot, this.currentRouterState); + const emitRecognzied$ = map.call(snapshot$, (newRouterStateSnapshot: RouterStateSnapshot) => { + this.routerEvents.next(new RoutesRecognized( + id, this.serializeUrl(url), this.serializeUrl(appliedUrl), newRouterStateSnapshot)); + return newRouterStateSnapshot; + }); - }) - .map((newState: RouterState) => { - state = newState; - preActivation = - new PreActivation(state.snapshot, this.currentRouterState.snapshot, this.injector); - preActivation.traverse(this.outletMap); - }) - .mergeMap(_ => { - return preActivation.checkGuards(); + const routerState$ = map.call(emitRecognzied$, (routerStateSnapshot: RouterStateSnapshot) => { + return createRouterState(routerStateSnapshot, this.currentRouterState); + }); - }) - .mergeMap(shouldActivate => { - if (shouldActivate) { - return preActivation.resolveData().map(() => shouldActivate); - } else { - return of (shouldActivate); - } + const preactivation$ = map.call(routerState$, (newState: RouterState) => { + state = newState; + preActivation = + new PreActivation(state.snapshot, this.currentRouterState.snapshot, this.injector); + preActivation.traverse(this.outletMap); + }); - }) + const preactivation2$ = + mergeMap.call(preactivation$, () => { return preActivation.checkGuards(); }); + + const resolveData$ = mergeMap.call(preactivation2$, (shouldActivate: boolean) => { + if (shouldActivate) { + return map.call(preActivation.resolveData(), () => shouldActivate); + } else { + return of (shouldActivate); + } + }); + + resolveData$ .forEach((shouldActivate: boolean) => { if (!shouldActivate || id !== this.navigationId) { navigationIsSuccessful = false; @@ -595,34 +596,34 @@ export class PreActivation { checkGuards(): Observable { if (this.checks.length === 0) return of (true); - return from(this.checks) - .map(s => { - if (s instanceof CanActivate) { - return andObservables( - from([this.runCanActivateChild(s.path), this.runCanActivate(s.route)])); - } else if (s instanceof CanDeactivate) { - // workaround https://github.com/Microsoft/TypeScript/issues/7271 - const s2 = s as CanDeactivate; - return this.runCanDeactivate(s2.component, s2.route); - } else { - throw new Error('Cannot be reached'); - } - }) - .mergeAll() - .every(result => result === true); + const checks$ = from(this.checks); + const runningChecks$ = map.call(checks$, (s: any) => { + if (s instanceof CanActivate) { + return andObservables( + from([this.runCanActivateChild(s.path), this.runCanActivate(s.route)])); + } else if (s instanceof CanDeactivate) { + // workaround https://github.com/Microsoft/TypeScript/issues/7271 + const s2 = s as CanDeactivate; + return this.runCanDeactivate(s2.component, s2.route); + } else { + throw new Error('Cannot be reached'); + } + }); + const mergedChecks$ = mergeAll.call(runningChecks$); + return every.call(mergedChecks$, (result: any) => result === true); } resolveData(): Observable { if (this.checks.length === 0) return of (null); - return from(this.checks) - .mergeMap(s => { - if (s instanceof CanActivate) { - return this.runResolve(s.route); - } else { - return of (null); - } - }) - .reduce((_, __) => _); + const checks$ = from(this.checks); + const runningChecks$ = mergeMap.call(checks$, (s: any) => { + if (s instanceof CanActivate) { + return this.runResolve(s.route); + } else { + return of (null); + } + }); + return reduce.call(runningChecks$, (_: any, __: any) => _); } private traverseChildRoutes( @@ -706,7 +707,7 @@ export class PreActivation { private runCanActivate(future: ActivatedRouteSnapshot): Observable { const canActivate = future._routeConfig ? future._routeConfig.canActivate : null; if (!canActivate || canActivate.length === 0) return of (true); - const obs = from(canActivate).map(c => { + const obs = map.call(from(canActivate), (c: any) => { const guard = this.getToken(c, future); if (guard.canActivate) { return wrapIntoObservable(guard.canActivate(future, this.future)); @@ -725,8 +726,8 @@ export class PreActivation { .map(p => this.extractCanActivateChild(p)) .filter(_ => _ !== null); - return andObservables(from(canActivateChildGuards).map(d => { - const obs = from(d.guards).map(c => { + return andObservables(map.call(from(canActivateChildGuards), (d: any) => { + const obs = map.call(from(d.guards), (c: any) => { const guard = this.getToken(c, c.node); if (guard.canActivateChild) { return wrapIntoObservable(guard.canActivateChild(future, this.future)); @@ -748,22 +749,21 @@ export class PreActivation { private runCanDeactivate(component: Object, curr: ActivatedRouteSnapshot): Observable { const canDeactivate = curr && curr._routeConfig ? curr._routeConfig.canDeactivate : null; if (!canDeactivate || canDeactivate.length === 0) return of (true); - return from(canDeactivate) - .map(c => { - const guard = this.getToken(c, curr); - if (guard.canDeactivate) { - return wrapIntoObservable(guard.canDeactivate(component, curr, this.curr)); - } else { - return wrapIntoObservable(guard(component, curr, this.curr)); - } - }) - .mergeAll() - .every(result => result === true); + const canDeactivate$ = map.call(from(canDeactivate), (c: any) => { + const guard = this.getToken(c, curr); + if (guard.canDeactivate) { + return wrapIntoObservable(guard.canDeactivate(component, curr, this.curr)); + } else { + return wrapIntoObservable(guard(component, curr, this.curr)); + } + }); + const merged$ = mergeAll.call(canDeactivate$); + return every.call(merged$, (result: any) => result === true); } private runResolve(future: ActivatedRouteSnapshot): Observable { const resolve = future._resolve; - return this.resolveNode(resolve.current, future).map(resolvedData => { + return map.call(this.resolveNode(resolve.current, future), (resolvedData: any): any => { resolve.resolvedData = resolvedData; future.data = merge(future.data, resolve.flattenedResolvedData); return null; diff --git a/modules/@angular/router/src/router_config_loader.ts b/modules/@angular/router/src/router_config_loader.ts index 2acffae7ec..fccf355443 100644 --- a/modules/@angular/router/src/router_config_loader.ts +++ b/modules/@angular/router/src/router_config_loader.ts @@ -10,6 +10,8 @@ import {Compiler, ComponentFactoryResolver, Injector, NgModuleFactory, NgModuleF import {Observable} from 'rxjs/Observable'; import {fromPromise} from 'rxjs/observable/fromPromise'; import {of } from 'rxjs/observable/of'; +import {map} from 'rxjs/operator/map'; +import {mergeMap} from 'rxjs/operator/mergeMap'; import {LoadChildren, Route} from './config'; import {flatten, wrapIntoObservable} from './utils/collection'; @@ -29,7 +31,7 @@ export class RouterConfigLoader { constructor(private loader: NgModuleFactoryLoader, private compiler: Compiler) {} load(parentInjector: Injector, loadChildren: LoadChildren): Observable { - return this.loadModuleFactory(loadChildren).map(r => { + return map.call(this.loadModuleFactory(loadChildren), (r: any) => { const ref = r.create(parentInjector); return new LoadedRouterConfig( flatten(ref.injector.get(ROUTES)), ref.injector, ref.componentFactoryResolver); @@ -41,9 +43,9 @@ export class RouterConfigLoader { return fromPromise(this.loader.load(loadChildren)); } else { const offlineMode = this.compiler instanceof Compiler; - return wrapIntoObservable(loadChildren()) - .mergeMap( - t => offlineMode ? of (t) : fromPromise(this.compiler.compileModuleAsync(t))); + return mergeMap.call( + wrapIntoObservable(loadChildren()), + (t: any) => offlineMode ? of (t) : fromPromise(this.compiler.compileModuleAsync(t))); } } } diff --git a/modules/@angular/router/src/utils/collection.ts b/modules/@angular/router/src/utils/collection.ts index 37ae7a5c6a..99cf81eca6 100644 --- a/modules/@angular/router/src/utils/collection.ts +++ b/modules/@angular/router/src/utils/collection.ts @@ -6,12 +6,14 @@ * found in the LICENSE file at https://angular.io/license */ -import 'rxjs/add/operator/concatAll'; -import 'rxjs/add/operator/last'; - import {Observable} from 'rxjs/Observable'; import {fromPromise} from 'rxjs/observable/fromPromise'; import {of } from 'rxjs/observable/of'; +import {concatAll} from 'rxjs/operator/concatAll'; +import {every} from 'rxjs/operator/every'; +import * as l from 'rxjs/operator/last'; +import {map} from 'rxjs/operator/map'; +import {mergeAll} from 'rxjs/operator/mergeAll'; import {PRIMARY_OUTLET} from '../shared'; @@ -95,7 +97,7 @@ export function waitForMap( forEach(obj, (a: A, k: string) => { if (k === PRIMARY_OUTLET) { - waitFor.push(fn(k, a).map((_: B) => { + waitFor.push(map.call(fn(k, a), (_: B) => { res[k] = _; return _; })); @@ -104,7 +106,7 @@ export function waitForMap( forEach(obj, (a: A, k: string) => { if (k !== PRIMARY_OUTLET) { - waitFor.push(fn(k, a).map((_: B) => { + waitFor.push(map.call(fn(k, a), (_: B) => { res[k] = _; return _; })); @@ -112,14 +114,17 @@ export function waitForMap( }); if (waitFor.length > 0) { - return of (...waitFor).concatAll().last().map((last) => res); + const concatted$ = concatAll.call(of (...waitFor)); + const last$ = l.last.call(concatted$); + return map.call(last$, () => res); } else { return of (res); } } export function andObservables(observables: Observable>): Observable { - return observables.mergeAll().every(result => result === true); + const merged$ = mergeAll.call(observables); + return every.call(merged$, (result: any) => result === true); } export function wrapIntoObservable(value: T | Promise| Observable): Observable { diff --git a/modules/@angular/router/test/integration.spec.ts b/modules/@angular/router/test/integration.spec.ts index 3cee22e1f0..d844994220 100644 --- a/modules/@angular/router/test/integration.spec.ts +++ b/modules/@angular/router/test/integration.spec.ts @@ -6,14 +6,13 @@ * found in the LICENSE file at https://angular.io/license */ -import 'rxjs/add/operator/map'; - import {CommonModule, Location} from '@angular/common'; import {Component, NgModule, NgModuleFactoryLoader} from '@angular/core'; import {ComponentFixture, TestBed, fakeAsync, inject, tick} from '@angular/core/testing'; import {expect} from '@angular/platform-browser/testing/matchers'; import {Observable} from 'rxjs/Observable'; import {of } from 'rxjs/observable/of'; +import {map} from 'rxjs/operator/map'; import {ActivatedRoute, ActivatedRouteSnapshot, CanActivate, CanDeactivate, Event, NavigationCancel, NavigationEnd, NavigationError, NavigationStart, Params, Resolve, Router, RouterModule, RouterStateSnapshot, RoutesRecognized} from '../index'; import {RouterTestingModule, SpyNgModuleFactoryLoader} from '../testing'; @@ -1791,7 +1790,7 @@ class TeamCmp { recordedParams: Params[] = []; constructor(public route: ActivatedRoute) { - this.id = route.params.map(p => p['id']); + this.id = map.call(route.params, (p: any) => p['id']); route.params.forEach(_ => this.recordedParams.push(_)); } } @@ -1802,7 +1801,7 @@ class UserCmp { recordedParams: Params[] = []; constructor(route: ActivatedRoute) { - this.name = route.params.map(p => p['name']); + this.name = map.call(route.params, (p: any) => p['name']); route.params.forEach(_ => this.recordedParams.push(_)); } } @@ -1818,7 +1817,7 @@ class QueryParamsAndFragmentCmp { fragment: Observable; constructor(route: ActivatedRoute) { - this.name = route.queryParams.map(p => p['name']); + this.name = map.call(route.queryParams, (p: any) => p['name']); this.fragment = route.fragment; } }