@@ -29,6 +29,17 @@ function isComponentFactoryResolver(item: any): item is ComponentFactoryResolver
2929 return ! ! item . resolveComponentFactory ;
3030}
3131
32+ function callableOnce < T > ( fn : ( ...args : T [ ] ) => void ) {
33+ let called = false ;
34+ return ( ...args : T [ ] ) => {
35+ if ( called ) {
36+ return ;
37+ }
38+ called = true ;
39+ return fn ( ...args ) ;
40+ } ;
41+ }
42+
3243export class DestructibleInjector implements Injector {
3344 private refs = new Set < any > ( ) ;
3445 constructor ( private destructibleProviders : ProviderSet , private parent : Injector ) { }
@@ -71,6 +82,10 @@ export class PageRouterOutlet implements OnDestroy, RouterOutletContract {
7182 private isEmptyOutlet : boolean ;
7283 private viewUtil : ViewUtil ;
7384 private frame : Frame ;
85+ // this function is used to clear the outlet cache (clear history)
86+ // usually it's cleared in `navigatedTo`, but on quick navigation, the event will be fired after angular already added more things to the cache
87+ // so now we call this if the component is detached or deactivated (meaning it's mid-navigation, before cache manipulation)
88+ private postNavFunction : ( ) => void ;
7489
7590 attachEvents : EventEmitter < unknown > = new EventEmitter ( ) ;
7691 detachEvents : EventEmitter < unknown > = new EventEmitter ( ) ;
@@ -209,6 +224,7 @@ export class PageRouterOutlet implements OnDestroy, RouterOutletContract {
209224 if ( ! this . isActivated ) {
210225 return ;
211226 }
227+ this . postNavFunction ?.( ) ;
212228
213229 const c = this . activated . instance ;
214230 destroyComponentRef ( this . activated ) ;
@@ -234,6 +250,8 @@ export class PageRouterOutlet implements OnDestroy, RouterOutletContract {
234250 NativeScriptDebug . routerLog ( `PageRouterOutlet.detach() - ${ routeToString ( this . _activatedRoute ) } ` ) ;
235251 }
236252
253+ this . postNavFunction ?.( ) ;
254+
237255 // Detach from ChangeDetection
238256 this . activated . hostView . detach ( ) ;
239257
@@ -413,28 +431,45 @@ export class PageRouterOutlet implements OnDestroy, RouterOutletContract {
413431 this . locationStrategy . _beginPageNavigation ( this . frame , navOptions ) ;
414432 const isReplace = navOptions . replaceUrl && ! navOptions . clearHistory ;
415433
434+ const currentRoute = this . activatedRoute ;
416435 // Clear refCache if navigation with clearHistory
417436 if ( navOptions . clearHistory ) {
437+ this . outlet . outletKeys . forEach ( ( key ) => this . routeReuseStrategy . markCacheForClear ( key ) ) ;
438+ const wipeCache = callableOnce ( ( ) => {
439+ if ( this . postNavFunction === wipeCache ) {
440+ this . postNavFunction = null ;
441+ }
442+ if ( this . outlet && this . activatedRoute === currentRoute ) {
443+ // potential alternative fix (only fix children of the current outlet)
444+ // const nests = outletKey.split('/');
445+ // this.outlet.outletKeys.filter((k) => k.split('/').length >= nests.length).forEach((key) => this.routeReuseStrategy.clearCache(key));
446+ this . outlet . outletKeys . forEach ( ( key ) => this . routeReuseStrategy . clearMarkedCache ( key ) ) ;
447+ }
448+ } ) ;
449+ this . postNavFunction = wipeCache ;
418450 const clearCallback = ( ) =>
419451 setTimeout ( ( ) => {
420- if ( this . outlet ) {
421- // potential alternative fix (only fix children of the current outlet)
422- // const nests = outletKey.split('/');
423- // this.outlet.outletKeys.filter((k) => k.split('/').length >= nests.length).forEach((key) => this.routeReuseStrategy.clearCache(key));
424- this . outlet . outletKeys . forEach ( ( key ) => this . routeReuseStrategy . clearCache ( key ) ) ;
425- }
452+ wipeCache ( ) ;
426453 } ) ;
427454
428455 page . once ( Page . navigatedToEvent , clearCallback ) ;
429456 } else if ( navOptions . replaceUrl ) {
457+ this . outlet . outletKeys . forEach ( ( key ) => this . routeReuseStrategy . markCacheForPop ( key ) ) ;
458+ const popCache = callableOnce ( ( ) => {
459+ if ( this . postNavFunction === popCache ) {
460+ this . postNavFunction = null ;
461+ }
462+ if ( this . outlet && this . activatedRoute === currentRoute ) {
463+ // potential alternative fix (only fix children of the current outlet)
464+ // const nests = outletKey.split('/');
465+ // this.outlet.outletKeys.filter((k) => k.split('/').length >= nests.length).forEach((key) => this.routeReuseStrategy.popCache(key));
466+ this . outlet . outletKeys . forEach ( ( key ) => this . routeReuseStrategy . clearMarkedCache ( key ) ) ;
467+ }
468+ } ) ;
469+ this . postNavFunction = popCache ;
430470 const clearCallback = ( ) =>
431471 setTimeout ( ( ) => {
432- if ( this . outlet ) {
433- // potential alternative fix (only fix children of the current outlet)
434- // const nests = outletKey.split('/');
435- // this.outlet.outletKeys.filter((k) => k.split('/').length >= nests.length).forEach((key) => this.routeReuseStrategy.popCache(key));
436- this . outlet . outletKeys . forEach ( ( key ) => this . routeReuseStrategy . popCache ( key ) ) ;
437- }
472+ popCache ( ) ;
438473 } ) ;
439474
440475 page . once ( Page . navigatedToEvent , clearCallback ) ;
0 commit comments