À partir des modules Angular 6 jamais Déchargez.
Le routeur ne vérifie pas actuellement si un module a été détruit après son chargement paresseux. Ainsi, même si vous obtenez le NgModuleRef et que vous appelez destroy manuellement, le routeur pense toujours qu'il a été chargé. Il ne le chargera donc pas paresseusement une seconde fois.
Le routeur se contente de charger le module mais ne gère pas son cycle de vie. Même si vous pouviez détruire un module, cela ne libérerait pas beaucoup de mémoire. Les modules chargés paresseusement sont gérés par des bundles WebPack qui sont chargés avec SystemJS. Une fois qu'ils sont chargés, ils restent en mémoire. Même si Angular détruit l'instance du module, le code source du bundle se trouve toujours dans la mémoire cache des bundles chargés de SystemJS.
Ce problème s'étend aux bibliothèques des fournisseurs. Si vous avez un module à chargement paresseux qui utilise une bibliothèque graphique tierce comme D3, la bibliothèque du fournisseur sera chargée et vous ne pourrez pas la décharger.
Si vous avez besoin d'avoir des fournisseurs qui n'existent que pour des routes spécifiques, alors vous devriez utiliser des fournisseurs de vues.
@Component({
...
viewProviders: [
LazyFeatureService
]
})
export class MyLazyComponent {}
Lorsque vous utilisez le composant ci-dessus comme composant de routeur, alors le service LazyFeatureService
est créé lorsque le module est chargé paresseusement, mais lorsque le composant est détruit, le service est également détruit. La prochaine fois que l'utilisateur visitera la route paresseuse, le service sera à nouveau créé.
Mise à jour :
La raison en est que je dois réinitialiser la configuration du service partagé. En gros, j'ai certaines données de configuration pour l'application, et je dois les remplacer pour le module chargé paresseusement, mais les remettre en place une fois que l'utilisateur n'est plus dans le module.
Vous pouvez y parvenir en utilisant l'option canActivate
y canDeactivate
dans l'itinéraire.
Dans votre configuration de route pour le module paresseux, créez une route de premier niveau pour gérer les activations.
const routes: Routes = [
{
path: '',
canActivate: [ConfigActivator],
canDeactivate: [ConfigActivator],
children: [
// move the routes here
]
};
Vous pouvez alors définir l'activateur comme suit.
@Injectable()
export class ConfigActivator implement CanActivate, CanDeactivate<any> {
public constructor(private config: MyConfigService) {
}
public canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): boolean {
this.config.lazyModuleLoaded();
return true;
}
public canDeactivate(component: any, currentRoute: ActivatedRouteSnapshot, currentState: RouterStateSnapshot, nextState?: RouterStateSnapshot): boolean {
this.config.lazyModuleUnloaded();
return true;
}
}
Ce qui précède appelle des méthodes sur le service pour lui dire quand il doit mettre à jour la configuration en fonction du changement d'état du routeur. Comme il s'agit d'une route de haut niveau pour le module paresseux, elle ne sera déclenchée que lorsque la route est activée, et lorsque la route quitte ce chemin.