typescript - Hvordan laste den nåværende ruten på nytt med Angular 2-routeren
Jeg bruker Angular 2 med hashlocation-strategi.
Komponenten lastes med den ruten:
"departments/:id/employees"
Så langt så bra.
Etter at jeg har gjort en vellykket batch-lagring av flere redigerte tabellrader, ønsker jeg å laste gjeldende rute-URL på nytt via:
this.router.navigate([`departments/${this.id}/employees`]);
Men ingenting skjer, hvorfor?
Svar #1
Lag en funksjon i kontrolleren som videresender til den forventede ruten slik:
redirectTo(uri: string) {
this.router.navigateByUrl('/', { skipLocationChange: true }).then(() => {
this.router.navigate([uri])});
}
Så bruker du det slik
this.redirectTo('//place your uri here');
Denne funksjonen vil omdirigere til en midlertidig rute og raskt returnere til destinasjonsruten uten at brukeren merker det.
Svar #2
Dette kan nå gjøres i Angular 5.1 ved å bruke onSameUrlNavigation-egenskapen i Router-konfigurasjonen.
Jeg har lagt til en blogg som forklarer hvordan her, men hovedpoenget er som følger
https://medium.com/engineering-on-the-incline/reloading-current-route-on-click-angular-5-1a1bfc740ab2
I ruterkonfigurasjonen din aktiver onSameUrlNavigation-alternativet, og sett det til 'reload'. Dette får Ruteren til å starte en hendelsessyklus når du prøver å navigere til en rute som allerede er aktiv.
@ngModule({
imports: [RouterModule.forRoot(routes, {onSameUrlNavigation: 'reload'})],
exports: [RouterModule],
})
I rutedefinisjonene dine, sett runGuardsAndResolvers til always. Dette vil fortelle ruteren å alltid starte vaktene og resolver-sykluser, og utløse tilknyttede hendelser.
export const routes: Routes = [
{
path: 'invites',
component: InviteComponent,
children: [
{
path: '',
loadChildren: './pages/invites/invites.module#InvitesModule',
},
],
canActivate: [AuthenticationGuard],
runGuardsAndResolvers: 'always',
}
]
Til slutt, i hver komponent som du ønsker å aktivere opplasting på nytt, må du håndtere hendelsene. Dette kan gjøres ved å importere ruteren, binde seg til hendelsene og kalle en initialiseringsmetode som tilbakestiller komponentens tilstand og henter data på nytt om nødvendig.
export class InviteComponent implements OnInit, OnDestroy {
navigationSubscription;
constructor(
// … your declarations here
private router: Router,
) {
// subscribe to the router events. Store the subscription so we can
// unsubscribe later.
this.navigationSubscription = this.router.events.subscribe((e: any) => {
// If it is a NavigationEnd event re-initalise the component
if (e instanceof NavigationEnd) {
this.initialiseInvites();
}
});
}
initialiseInvites() {
// Set default values and re-fetch any data you need.
}
ngOnDestroy() {
if (this.navigationSubscription) {
this.navigationSubscription.unsubscribe();
}
}
}
Med alle disse trinnene på plass, bør du ha rutinggjenlasting aktivert.
Svar #3
Jeg bruker denne for Angular 11-prosjektet:
reloadCurrentRoute() {
const currentUrl = this.router.url;
this.router.navigateByUrl('/', { skipLocationChange: true }).then(() => {
this.router.navigate([currentUrl]);
});
}
PS: Testet og fungerer på alle versjoner over 7.
Svar #4
REDIGER
For nyere versjoner av Angular (5.1+) bruk svaret foreslått av @Simon McClive
Gammelt svar
Jeg fant denne løsningen på en GitHub-funksjonsforespørsel for Angular:
this._router.routeReuseStrategy.shouldReuseRoute = function(){
return false;
};
this._router.events.subscribe((evt) => {
if (evt instanceof NavigationEnd) {
this._router.navigated = false;
window.scrollTo(0, 0);
}
});
Jeg prøvde å legge dette til i min app.component.ts ngOnInit-funksjon, og det fungerte absolutt. Alle videre klikk på samme lenke laster nå komponenten og dataene på nytt.
Lenke til original GitHub-funksjonsforespørsel
Kreditten går til mihaicux2 på GitHub.
Jeg testet dette på versjon 4.0.0-rc.3 med import { Router, NavigationEnd } from '@angular/router';
Svar #5
Dette er hva jeg gjorde med Angular 12. Jeg er ikke sikker på om dette fungerer i versjoner under 9.
Du må ringe dette når du trenger å laste på nytt.
this.router.navigate([], {
skipLocationChange: true,
queryParamsHandling: 'merge' //== if you need to keep queryParams
})
Router forRoot må ha SameUrlNavigation satt til 'reload'
RouterModule.forRoot(appRoutes, {
// ..
onSameUrlNavigation: 'reload',
// ..
})
Og hver rute du har må ha runGuardsAndResolvers satt til 'always'
{
path: '',
data: {},
runGuardsAndResolvers: 'always'
},
Svar #6
Hvis din navigate() ikke endrer URL-en som allerede vises på adressefeltet i nettleseren din, har ruteren ingenting å gjøre. Det er ikke ruterens jobb å oppdatere dataene. Hvis du vil oppdatere dataene, opprett en tjeneste som injiseres i komponenten og kall load-funksjonen på tjenesten. Hvis de nye dataene blir hentet, vil de oppdatere visningen via bindinger.
Svar #7
Dette fungerer for meg som en sjarm
this.router.navigateByUrl('/', {skipLocationChange: true}).then(()=>
this.router.navigate([<route>]));
Svar #8
Litt tricky: bruk samme sti med noen dummy-parametere. For eksempel-
refresh(){
this.router.navigate(["/same/route/path?refresh=1"]);
}
Svar #9
Angular 2-4 ruteoppdateringshack
For meg fungerer det å bruke denne metoden inne i en rotkomponent (komponent, som finnes på hvilken som helst rute):
onRefresh() {
this.router.routeReuseStrategy.shouldReuseRoute = function(){return false;};
let currentUrl = this.router.url + '?';
this.router.navigateByUrl(currentUrl)
.then(() => {
this.router.navigated = false;
this.router.navigate([this.router.url]);
});
}
Svar #10
Ved endring av parameter vil ikke siden lastes på nytt. Dette er en veldig god funksjon. Det er ikke nødvendig å laste siden på nytt, men vi bør endre verdien på komponenten. paramChange-metoden vil bli kalt ved URL-endring. Så vi kan oppdatere komponentdataene.
/product/: id / details
import { ActivatedRoute, Params, Router } from ‘@angular/router’;
export class ProductDetailsComponent implements OnInit {
constructor(private route: ActivatedRoute, private router: Router) {
this.route.params.subscribe(params => {
this.paramsChange(params.id);
});
}
// Call this method on page change
ngOnInit() {
}
// Call this method on change of the param
paramsChange(id) {
}
