fix(common): prevent duplicate URL change notifications (#37459)

Prevent duplicate notifications from being emitted when multiple URL change listeners are registered using SpyLocation#onUrlChange.

Use `@internal` annotation for the `_urlChangeSubscription` properties instead of the `private` access modifier. Otherwise, we get in trouble because of  `SpyLocation implements Location`.

PR Close #37459
This commit is contained in:
Lars Gyrup Brink Nielsen 2020-06-05 23:24:35 +02:00 committed by atscott
parent 0b7845964b
commit 7edb026619
2 changed files with 10 additions and 4 deletions

View File

@ -64,7 +64,8 @@ export class Location {
_platformLocation: PlatformLocation; _platformLocation: PlatformLocation;
/** @internal */ /** @internal */
_urlChangeListeners: ((url: string, state: unknown) => void)[] = []; _urlChangeListeners: ((url: string, state: unknown) => void)[] = [];
private _urlChangeSubscription?: SubscriptionLike; /** @internal */
_urlChangeSubscription?: SubscriptionLike;
constructor(platformStrategy: LocationStrategy, platformLocation: PlatformLocation) { constructor(platformStrategy: LocationStrategy, platformLocation: PlatformLocation) {
this._platformStrategy = platformStrategy; this._platformStrategy = platformStrategy;

View File

@ -30,6 +30,8 @@ export class SpyLocation implements Location {
_platformLocation: PlatformLocation = null!; _platformLocation: PlatformLocation = null!;
/** @internal */ /** @internal */
_urlChangeListeners: ((url: string, state: unknown) => void)[] = []; _urlChangeListeners: ((url: string, state: unknown) => void)[] = [];
/** @internal */
_urlChangeSubscription?: SubscriptionLike;
setInitialPath(url: string) { setInitialPath(url: string) {
this._history[this._historyIndex].path = url; this._history[this._historyIndex].path = url;
@ -123,9 +125,12 @@ export class SpyLocation implements Location {
} }
onUrlChange(fn: (url: string, state: unknown) => void) { onUrlChange(fn: (url: string, state: unknown) => void) {
this._urlChangeListeners.push(fn); this._urlChangeListeners.push(fn);
this.subscribe(v => {
this._notifyUrlChangeListeners(v.url, v.state); if (!this._urlChangeSubscription) {
}); this._urlChangeSubscription = this.subscribe(v => {
this._notifyUrlChangeListeners(v.url, v.state);
});
}
} }
/** @internal */ /** @internal */