J'ai mis en place le système de routage suivant
export const MyRoutes: Routes = [
{path: '', redirectTo: 'new', pathMatch: 'full'},
{path: ':type', component: MyComponent}
];
et avoir le système de navigation suivant
goToPage('new');
goToPageNo('new', 2);
goToPage(type) {
this.router.navigate([type]);
}
goToPageNo(type, pageNo) {
this.router.navigate([type], {queryParams: {page: pageNo}});
}
Exemple URL ressemble à ceci
http: // localhost: 3000/new? page = 2
Parfois ils ont optional queryParams (page)
Maintenant, je dois lire les paramètres route et queryParams
ngOnInit(): void {
this.paramsSubscription = this.route.params.subscribe((param: any) => {
this.type = param['type'];
this.querySubscription = this.route.queryParams.subscribe((queryParam: any) => {
this.page = queryParam['page'];
if (this.page)
this.goToPageNo(this.type, this.page);
else
this.goToPage(this.type);
});
});
}
ngOnDestroy(): void {
this.paramsSubscription.unsubscribe();
this.querySubscription.unsubscribe();
}
Maintenant, cela ne fonctionne pas comme prévu, visiter des pages sans que queryParams fonctionne, puis je visite une page avec queryParams "goToPageNo" étant appelé plusieurs fois, car je m'abonne à queryParams dans les paramètres de route.
J'ai regardé la documentation Angular 2, ils n'ont aucun exemple ou code où un abonnement à both route params et queryParams est implémenté en même temps.
Un moyen de le faire correctement? Aucune suggestion?
Pour angulaire 6+
import { combineLatest } from 'rxjs';
import { map } from 'rxjs/operators';
...
combineLatest(this.route.params, this.route.queryParams)
.pipe(map(results => ({params: results[0].xxx, query: results[1]})))
.subscribe(results => {
console.log(results);
});
Où xxx
est de votre route
{path: 'post/:xxx', component: MyComponent},
J'ai réussi à obtenir un seul abonnement à la fois à queryParams et à Params en combinant les observables à l'aide de Observable.combineLatest
avant de m'abonner.
Par exemple.
var obsComb = Observable.combineLatest(this.route.params, this.route.queryParams,
(params, qparams) => ({ params, qparams }));
obsComb.subscribe( ap => {
console.log(ap.params['type']);
console.log(ap.qparams['page']);
});
Réponse tardive, mais une autre solution: Au lieu de souscrire aux paramètres et queryparams, je souscris à l'événement NavigationEnd sur le routeur. Ne se déclenche qu'une seule fois et les paramètres et queryparams sont disponibles dans l'instantané: (exemple pour Angular 4)
this.router.events.filter(event=>event instanceof NavigationEnd)
.subscribe(event=>{
let yourparameter = this.activatedroute.snapshot.params.yourparameter;
let yourqueryparameter = this.activatedroute.snapshot.queryParams.yourqueryparameter;
});
En ce qui concerne la désinscription: oui, il est vrai que les paramètres de routage, queryParams ou les événements de navigation sont automatiquement désabonnés par le routeur. Il existe toutefois une exception: si votre route a des enfants, lors de la navigation entre les enfants, aucune désinscription ne sera effectuée. Seulement lorsque vous quittez la route parente!
Par exemple. J'ai eu une situation avec des onglets comme itinéraires enfants. Dans le constructeur du premier composant onglet s'abonner sur route param pour récupérer les données. Chaque fois que je navigue du premier au deuxième onglet et retour, un autre abonnement a été ajouté, ce qui a multiplié le nombre de demandes.
Utilisez ActivatedRouteSnapshot
de votre ActivatedRoute
ActivatedRouteSnapshot
interface a les propriétés params
et queryParams
et vous pouvez obtenir les deux valeurs en même temps.
constructor(private route: ActivatedRoute) {
console.log(this.route.snapshot.params);
console.log(this.route.snapshot.queryParams);
}
Edit: Comme indiqué par OP, nous n’obtenons que la valeur initiale des paramètres avec cette technique.
Exemple Plunker