How to use the router state in an Angular application with ngrx implementation

1.4k Views Asked by At

I know it is possible to store in a state the routing using the @ngrx/router-store.

This library bind the Angular router with the ngrx-store.

Following the redux principles, it has sense to store the routing because it is a state change of the application, but, practically, what to do with the information stored? Is it useful only if we want to implement side-effects on routing?

3

There are 3 best solutions below

1
On

The same way, not change because of ngrx.

import { NewTicketComponent } from './components/ticket/new-ticket/new-ticket/new-ticket.component';


import { RouterModule, Routes } from '@angular/router';
import { NgModule } from '@angular/core';
import { HomeComponent } from './components/home/home.component';
import { DashboardComponent } from './components/dashboard/dashboard.component';
import { RegisterComponent } from './components/register/register.component';
import { LoginComponent } from './components/login/login.component';
import { ProfileComponent } from './components/profile/profile.component';
import { PublicProfileComponent } from './components/public-profile/public-profile.component';


// Our Array of Angular 2 Routes
const appRoutes: Routes = [
  {
    path: '',
    component: HomeComponent // Default Route
  },
  {
    path: 'dashboard',
    component: DashboardComponent, // Dashboard Route,
    canActivate: [AuthGuard] // User must be logged in to view this route
  },
  {
    path: 'register',
    component: RegisterComponent, // Register Route
    canActivate: [AuthGuard] // User must be logged in to view this route
  },
  {
    path: 'login',
    component: LoginComponent, // Login Route
    canActivate: [NotAuthGuard] // User must NOT be logged in to view this route
  },
  {
    path: 'user/:id',
    component: ProfileComponent, // Profile Route
    canActivate: [AuthGuard] // User must be logged in to view this route
  },
  {
    path: 'profile/user/:username',
    component: PublicProfileComponent, // Public Profile Route
    canActivate: [AuthGuard] // User must be logged in to view this route
  },
  { path: '**', component: HomeComponent } // "Catch-All" Route
];

@NgModule({
  declarations: [],
  imports: [RouterModule.forRoot(appRoutes)],
  providers: [],
  bootstrap: [],
  exports: [RouterModule]
})

export class AppRoutingModule { }

0
On

From my experience, it is not only for the effects. Sometimes you may need to pass the params id of the previous state. 1. Example if you are loading the cart details ( Assuming an e-commerce application). You can get the params id when some one hits the url and store the params in local storage and pass it to different state url.

  canActivate(route: ActivatedRouteSnapshot, state: RouterStateSnapshot): boolean {
    const quickCartId = route.firstChild.firstChild.params.id; //get the previous state of params id 
    if (!this.auth.isAuthenticated()) {
      this.auth.handleAuthenticationURLEntry(state);
      this.auth.login();
      return false;
    }

    // logic for quick cart feature
    if (!!quickCartId) {
      localStorage.setItem(environment.cartId, quickCartId); // replace the id 
      this.cartProvider.load();
    }

    return true;
  }

Hope it helps

0
On

I use route params inside a selector, for example

export const selectCurrentCustomer = createSelector(
  selectCustomers,
  selectRouteParameters,
  (customers, route) => customers[route.customerId]
);

Also as mentioned in the docs, @ngrx/router-store also dispatches navigation actions.