Jak uzyskać RouteParams ze składnika nadrzędnego?
App.ts
:
@Component({
...
})
@RouteConfig([
{path: '/', component: HomeComponent, as: 'Home'},
{path: '/:username/...', component: ParentComponent, as: 'Parent'}
])
export class HomeComponent {
...
}
Następnie ParentComponent
mogę łatwo uzyskać parametr mojej nazwy użytkownika i ustawić trasy podrzędne.
Parent.ts
:
@Component({
...
})
@RouteConfig([
{ path: '/child-1', component: ChildOneComponent, as: 'ChildOne' },
{ path: '/child-2', component: ChildTwoComponent, as: 'ChildTwo' }
])
export class ParentComponent {
public username: string;
constructor(
public params: RouteParams
) {
this.username = params.get('username');
}
...
}
Ale jak mogę uzyskać ten sam parametr „nazwa użytkownika” w tych komponentach podrzędnych? Robienie tego samego triku co powyżej, nie robi tego. Ponieważ te parametry są zdefiniowane w ProfileComponent czy coś?
@Component({
...
})
export class ChildOneComponent {
public username: string;
constructor(
public params: RouteParams
) {
this.username = params.get('username');
// returns null
}
...
}
angular
angular2-routing
Aico Klein Ovink
źródło
źródło
<child-one-component [username]="username"> ...
<routerlink [username]="username">...
? I czy to jest droga do @MarkRajcok?<a [router-link]="[ './....', {username: username} ]
zadziała. Przepraszam, nie mam pojęcia, czy to zadziała, czy nie. (Nie grałem jeszcze zbyt wiele w routing.)<router-outlet></router-outlet>
, czy powinienem umieścić na tym wejście. Ponieważ trasy podrzędne zostaną tam wyrenderowane ...Odpowiedzi:
AKTUALIZACJA:
Teraz, gdy finał Angular2 został oficjalnie wydany, prawidłowy sposób na zrobienie tego jest następujący:
ORYGINALNY:
Oto jak to zrobiłem, używając pakietu „@ angular / router”: „3.0.0-alpha.6”:
W tym przykładzie trasa ma następujący format: / parent /: id / child /: childid
źródło
parent
1+ razy. Zobacz stackoverflow.com/a/48511516/4185989 Jednak nadal warto rozważyć wzorzecsubscribe
/unsubscribe
z tej odpowiedzi.this.activatedRoute.parent.snapshot.params.someParam
Nie powinieneś próbować używać
RouteParams
w swoimChildOneComponent
.RouteRegistry
Zamiast tego użyj !AKTUALIZACJA: od tego żądania ściągnięcia (kątowa beta.9): https://github.com/angular/angular/pull/7163
Możesz teraz uzyskać dostęp do aktualnej instrukcji bez
recognize(location.path(), [])
.Przykład:
Jeszcze tego nie próbowałem
Więcej szczegółów tutaj:
https://github.com/angular/angular/blob/master/CHANGELOG.md#200-beta9-2016-03-09 https://angular.io/docs/ts/latest/api/router/Router-class .html
AKTUALIZACJA 2: Niewielka zmiana od kątowej 2.0.0.beta15:
Teraz
currentInstruction
nie jest już funkcją. Co więcej, musisz załadowaćroot
router. (podziękowania dla @ Lxrd-AJ za zgłoszenie)źródło
_router.root.currentInstruction.component.params['id']
. Nacisk na root, gdy otrzymujesz bieżącą instrukcję z routera głównego, a nie_router
. PS: używamangular2.0.0-beta.15
Jak wspomniał Günter Zöchbauer, użyłem komentarza pod adresem https://github.com/angular/angular/issues/6204#issuecomment-173273143 aby rozwiązać mój problem. Użyłem
Injector
klasy from,angular2/core
aby pobrać parametry routingu rodzica. Okazuje się, że kątowy 2 nie obsługuje głęboko zagnieżdżonych tras. Może dodadzą to w przyszłości.źródło
Znalazłem brzydkie, ale działające rozwiązanie, prosząc rodzica (dokładnie drugiego przodka) o wstrzykiwacz i otrzymując
RouteParams
stąd.Coś jak
źródło
RC5 + @ angular / router ":" 3.0.0-rc.1 ROZWIĄZANIE: Wygląda na to, że
this.router.routerState.queryParams
jest przestarzałe. Możesz uzyskać parametry trasy nadrzędnej w ten sposób:źródło
Możesz pobrać komponent trasy nadrzędnej wewnątrz komponentu podrzędnego z wtryskiwacza, a następnie pobrać dowolny z komponentu podrzędnego. W takim przypadku jak ten
źródło
Przekazywanie wystąpienia Injector do konstruktora w komponencie podrzędnym może nie być dobre, jeśli chcesz napisać testy jednostkowe dla swojego kodu.
Najłatwiejszym sposobem obejścia tego jest posiadanie klasy usługi w komponencie nadrzędnym, w której zapisujesz wymagane parametry.
Następnie po prostu wstrzykujesz tę samą usługę do komponentów podrzędnych i uzyskujesz dostęp do parametrów.
Należy zauważyć, że zakres takiej usługi powinien obejmować komponent nadrzędny i jego komponenty potomne przy użyciu „dostawców” w dekoratorze komponentów nadrzędnych.
Polecam ten artykuł o DI i zakresach w Angular 2: http://blog.hardtram.io/angular/2015/08/20/host-and-visibility-in-angular-2-dependency-injection.html
źródło
W RC6, router 3.0.0-rc.2 (prawdopodobnie działa również w RC5), możesz pobrać parametry trasy z adresu URL jako migawkę na wypadek, gdyby parametry się nie zmieniły, bez obserwałów z tą jedną linijką:
this.route.snapshot.parent.params['username'];
Nie zapomnij wstrzyknąć ActivatedRoute w następujący sposób:
constructor(private route: ActivatedRoute) {};
źródło
Dzięki RxJS
Observable.combineLatest
możemy uzyskać coś zbliżonego do idiomatycznej obsługi parametrów:import 'rxjs/add/operator/combineLatest'; import {Component} from '@angular/core'; import {ActivatedRoute, Params} from '@angular/router'; import {Observable} from 'rxjs/Observable'; @Component({ /* ... */ }) export class SomeChildComponent { email: string; id: string; constructor(private route: ActivatedRoute) {} ngOnInit() { Observable.combineLatest(this.route.params, this.route.parent.params) .forEach((params: Params[]) => { this.id = params[0]['id']; this.email = params[1]['email']; }); } }
źródło
Skończyło się na tym, że napisałem tego rodzaju hack do Angular 2 rc.1
import { Router } from '@angular/router-deprecated'; import * as _ from 'lodash'; interface ParameterObject { [key: string]: any[]; }; /** * Traverse route.parent links until root router and check each level * currentInstruction and group parameters to single object. * * e.g. * { * id: [314, 593], * otherParam: [9] * } */ export default function mergeRouteParams(router: Router): ParameterObject { let mergedParameters: ParameterObject = {}; while (router) { let currentInstruction = router.currentInstruction; if (currentInstruction) { let currentParams = currentInstruction.component.params; _.each(currentParams, (value, key) => { let valuesForKey = mergedParameters[key] || []; valuesForKey.unshift(value); mergedParameters[key] = valuesForKey; }); } router = router.parent; } return mergedParameters; }
Teraz na widoku zbieram parametry na widoku zamiast czytać
RouteParams
, po prostu przesyłam je przez router:@Component({ ... }) export class ChildishComponent { constructor(router: Router) { let allParams = mergeRouteParams(router); let parentRouteId = allParams['id'][0]; let childRouteId = allParams['id'][1]; let otherRandomParam = allParams.otherRandomParam[0]; } ... }
źródło
MergedRouteParams
klasy, która implementujeget
metodęRouteParams
klasy standardowej (drugi parametr to indeks, domyślnie zero).W FINAL z małą pomocą RXJS można połączyć obie mapy (od dziecka i rodzica):
Inne pytania, które można mieć:
źródło
Możesz to zrobić na migawce w następujący sposób, ale jeśli się zmieni, Twoja
id
właściwość nie zostanie zaktualizowana.Ten przykład pokazuje również, jak można zasubskrybować wszystkie zmiany parametrów przodków i wyszukać tę, która Cię interesuje, łącząc wszystkie obserwowalne parametrów. Należy jednak zachować ostrożność w przypadku tej metody, ponieważ może istnieć wielu przodków, które mają ten sam klucz / nazwę parametru.
import { Component } from '@angular/core'; import { ActivatedRoute, Params, ActivatedRouteSnapshot } from '@angular/router'; import { Observable } from 'rxjs/Observable'; import { Subscription } from 'rxjs/Subscription'; import 'rxjs/add/observable/merge'; // This traverses the route, following ancestors, looking for the parameter. function getParam(route: ActivatedRouteSnapshot, key: string): any { if (route != null) { let param = route.params[key]; if (param === undefined) { return getParam(route.parent, key); } else { return param; } } else { return undefined; } } @Component({ /* ... */ }) export class SomeChildComponent { id: string; private _parameterSubscription: Subscription; constructor(private route: ActivatedRoute) { } ngOnInit() { // There is no need to do this if you subscribe to parameter changes like below. this.id = getParam(this.route.snapshot, 'id'); let paramObservables: Observable<Params>[] = this.route.pathFromRoot.map(route => route.params); this._parametersSubscription = Observable.merge(...paramObservables).subscribe((params: Params) => { if ('id' in params) { // If there are ancestor routes that have used // the same parameter name, they will conflict! this.id = params['id']; } }); } ngOnDestroy() { this._parameterSubscription.unsubscribe(); } }
źródło
Pobieranie parametrów RouteParams z komponentu nadrzędnego w Angular 8 -
Mam trasę http: // localhost: 4200 / partner / student-profile / 1234 / info
Trasa nadrzędna - profil ucznia
Param - 1234 (student_id)
Trasa dziecięca - informacje
Dostęp do parametrów w trasie podrzędnej (informacje) -
Import
Konstruktor
Dostęp do parametrów trasy nadrzędnej
Teraz nasza zmienna studentId ma wartość param.
źródło