138 votes

Comment obtenir un paramètre sur une route Angular2 à la manière d'Angular ?

Route

const appRoutes: Routes = [
    { path: '', redirectTo: '/companies/unionbank', pathMatch: 'full'},
    { path: 'companies/:bank', component: BanksComponent },
    { path: '**', redirectTo: '/companies/unionbank' }
]

Composant

const NAVBAR = [
    { 
        name: 'Banks',
        submenu: [
            { routelink: '/companies/unionbank', name: 'Union Bank' },
            { routelink: '/companies/metrobank', name: 'Metro Bank' },
            { routelink: '/companies/bdo', name: 'BDO' },
            { routelink: '/companies/chinabank', name: 'China Bank' },
        ]
    },
    ...
]

Exemple de lien : http://localhost:8099/#/companies/bdo

Je veux obtenir String bdo dans le lien de l'exemple ci-dessus.

Je sais que je peux obtenir le lien en utilisant window.location.href et le diviser en tableau. Ainsi, je peux obtenir le dernier paramètre, mais je veux savoir s'il y a une méthode appropriée pour le faire à la manière angulaire.

Toute aide serait appréciée. Merci

298voto

BeetleJuice Points 19471

Mise à jour : septembre 2019

Comme quelques personnes l'ont mentionné, les paramètres de l'option paramMap doivent être accédés en utilisant la méthode commune Map API :

Pour obtenir un instantané des paramètres, lorsque vous ne vous souciez pas qu'ils puissent changer :

this.bankName = this.route.snapshot.paramMap.get('bank');

Pour s'abonner et être alerté des changements dans les valeurs des paramètres (généralement à la suite de la navigation du routeur)

this.route.paramMap.subscribe( paramMap => {
    this.bankName = paramMap.get('bank');
})

Mise à jour : août 2017

Depuis Angular 4, params ont été dépréciés en faveur de la nouvelle interface paramMap . Le code pour le problème ci-dessus devrait fonctionner si vous remplacez simplement l'un par l'autre.

Réponse originale

Si vous vous injectez ActivatedRoute dans votre composant, vous serez en mesure d'extraire les paramètres de la route

    import {ActivatedRoute} from '@angular/router';
    ...

    constructor(private route:ActivatedRoute){}
    bankName:string;

    ngOnInit(){
        // 'bank' is the name of the route parameter
        this.bankName = this.route.snapshot.params['bank'];
    }

Si vous souhaitez que les utilisateurs naviguent directement d'une banque à l'autre, sans passer d'abord par un autre composant, vous devez accéder au paramètre par le biais d'un observable :

    ngOnInit(){
        this.route.params.subscribe( params =>
            this.bankName = params['bank'];
        )
    }

Pour les docs, y compris les différences entre les deux consultez ce lien et recherchez " route activée "

0 votes

Existe-t-il une restriction selon laquelle les composants chargés dans une sortie de routeur d'un composant parent verront différents paramètres ActiveRoute - J'ai rencontré un cas où le parent voit un paramètre, mais les composants contenus ne voient pas le même paramètre...

0 votes

Cela ne fonctionnait pas pour moi parce que j'ai ajouté l'ActivatedRoute comme fournisseur de mon composant. Donc, assurez-vous que vous ne faites pas cela ! Cela fonctionne comme un charme avec angular 4.2.4.

1 votes

Pour paramMap vous devriez utiliser params.get('bank') à la place.

28voto

KMJungersen Points 105

À partir de la version 6+ d'Angular, le traitement est légèrement différent de celui des versions précédentes. Comme @BeetleJuice le mentionne dans le document réponse ci-dessus , paramMap est une nouvelle interface pour obtenir des paramètres de route, mais l'exécution est un peu différente dans les versions plus récentes d'Angular. En supposant que c'est dans un composant :

private _entityId: number;

constructor(private _route: ActivatedRoute) {
    // ...
}

ngOnInit() {
    // For a static snapshot of the route...
    this._entityId = this._route.snapshot.paramMap.get('id');

    // For subscribing to the observable paramMap...
    this._route.paramMap.pipe(
        switchMap((params: ParamMap) => this._entityId = params.get('id'))
    );

    // Or as an alternative, with slightly different execution...
    this._route.paramMap.subscribe((params: ParamMap) =>  {
        this._entityId = params.get('id');
    });
}

Je préfère utiliser les deux parce qu'ainsi, au chargement direct de la page, je peux obtenir le paramètre ID, et aussi si je navigue entre les entités liées, l'abonnement sera mis à jour correctement.

Source dans Angular Docs

1 votes

Pourquoi switchMap sera-t-il nécessaire ici ? L'abonnement ne sera-t-il pas également appelé au chargement direct de la page ?

4 votes

@crush D'après les documents liés ci-dessus : "Vous pourriez penser à utiliser le RxJS map opérateur. Mais le HeroService renvoie un Observable<Hero> . Vous aplatissez donc l'Observable avec le switchMap à la place. Le site switchMap L'opérateur annule également les demandes précédentes en cours de vol. Si l'utilisateur se dirige à nouveau vers cet itinéraire avec une nouvelle demande de vol, l'opérateur annule également les demandes précédentes. id tandis que le HeroService récupère toujours l'ancien id , switchMap rejette l'ancienne demande et renvoie le héros de la nouvelle demande. id ."

1voto

KK Nebula Points 11

Vous pouvez essayer ceci pour le paramètre get route :

import { Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router';

@Component({
  selector: 'app-hero',
  templateUrl: './hero.component.html',
  styleUrls: ['./hero.component.css']
})
export class HeroComponent implements OnInit {

  constructor(private activeRoute: ActivatedRoute) { 
    this.activeRoute.queryParams.subscribe((qp) => {
      console.log('Get Router Params:', this.activeRoute.snapshot.params.bank);
    });
  }

  ngOnInit(): void {
  }

}

Vous pouvez vérifier plus de détails sur l'itinéraire à l'URL aquí

0voto

belzebubele Points 73

Au lieu d'utiliser paramMap, vous pouvez aussi faire preuve de fantaisie et utiliser un Route Resolver, bien que cela puisse être un peu excessif et qu'il soit généralement utilisé pour récupérer des données pendant le processus de navigation...

Configuration du résolveur

import { Injectable } from '@angular/core';
import { Resolve } from '@angular/router';

import { Observable, of } from 'rxjs';
import { delay } from 'rxjs/operators';

@Injectable({
  providedIn: 'root'
})
export class LastUrlPathResolver implements Resolve<Observable<string>> {

  constructor(activatedRouteSnapshot: ActivatedRouteSnapshot){}

  resolve(): Observable<string> {
    return activatedRouteSnapshot.url[activatedRouteSnapshot.url.length-1]
  }
}

configuration des itinéraires

import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';

import { NewsResolver } from './news.resolver';

import { TopComponent } from './top/top.component';
import { HomeComponent } from './home/home.component';

const routes: Routes = [
  {
    path: '',
    pathMatch: 'full',
    component: HomeComponent
  },
  {
    path: 'top',
    component: TopComponent,
    resolve: { message: LastUrlPathResolver }
  }
];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule]
})
export class AppRoutingModule { }

utilisez-le comme

import { Component, OnInit } from '@angular/core';

import { ActivatedRoute } from '@angular/router';

@Component({ ... })
export class TopComponent implements OnInit {
  data: any;

  constructor(private route: ActivatedRoute) {}

  ngOnInit(): void {
    this.data = this.route.snapshot.data;
  }
}

Pour en savoir plus https://www.digitalocean.com/community/tutorials/angular-route-resolvers

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X