Angular 5 — routing

Photo by Andrew Neel

in the last article, we created a pokemon-list component, which displays an unordered list of pokemon names. the goal of this article is to be able to click on a pokmon name and get redirected to a details route which displays some additional details for the selected pokemon.

let’s do it.

  1. create a new pokemon-details component to display the additional details for selected pokemon.
ng generate component pokemon-details

we will return to this later in this article.

2. create a routing module

ng generate module app-routing

this creates AppRoutingModule. before going into the details of routing, let’s import this into it’s companion AppModule by adding to imports array.

follow same naming convention for a routing module, as it’s companion module, suffixing just Routing to the companion module.
eg. ThisModule >> ThisRoutingModule

3. currently our router module looks like below (like any other module generated from cli)

since we haven’t looked inside the details of a typical module yet, let’s quickly see the two important properties of @NgModule decorator metadata —

  • imports — array of other modules that components in current module will need to function. we see above, CommonModule is added to imports array. CommonModule contains all the basic angular directives like *ngIf, *ngFor etc.
  • declarations — array of declarable classes: components, directives and pipes

generally, routing module will never have it’s own components etc and in turn no templates, so we should get rid of declarations property and CommonModule references.

here is the cleaner router module:

4. import RouterModule and Routes from @angular/router library.

  • we need to re-export RouterModule in our routing module, so the companion module components have access to routing directives like RouterLink (explained later in this article) etc.
  • Routes is an array of Route configurations. Each Route, apart from many other important properties, has two basic properties: path which is the url string in browser and component which is the component created on visiting this route.
Route tells our application to match the path in browser url and decide which component to display.

updated routing module is this now:

it’s time to add some routes now.

5. currently, when we run our application using ng serve and visit http://localhost:4200/ we see a list of pokemons. let’s give this a route url /pokemons

to do this, we need to first create an array of Route objects of type Routes, and then add RouterModule.forRoot(<Routes array>) (if the companion module is root module, forChild for all other routing modules) to our routing module imports array.

what this tell our application is to match the path http://localhost:4200/pokemons and load PokemonListComponent.

6. try visiting this path in the url and you should still be able to see the list of pokemon names. pretty cool, yeah.

let’s quickly configure another Route to redirect to /pokemons url, when we provide an empty url.

ok, so now visiting http://localhost:4200/ will redirect us to http://localhost:4200/pokemons and we should see our list of pokemons, as we did before.

7. there is one thing wrong though in our routing so far. pokemon-list component is directly used in app.component.html template, rather this should now be the responsibility of our router to create the component based on route. it needs a placeholder though, to know where to render the component.

RouterOutlet directive provides that placeholder.

update app.component.html with below line:


everything still runs the same but with a powerful change behind the scenes. now, when /pokemons url is matched, router takes the matching component pokemon-list and appends after router-outlet which you can see in the dom.

8. let’s now create another route to display pokemon-details. what we want here is to be able to click on a name in pokemon list and get redirected to a url like /pokemon/<selected-pokemon-id> to see details for that pokemon. here is the updated router file:

the :id above at the end of new path url is placeholder for the selected pokemon id. PokemonDetailsComponent is what we created in step 1 to display the details, that we will work on next. before that, add the click and redirect to this new route functionality to our list.

update pokemon-list.component.html with below html:

  • pokemon name span is now updated to an anchor tag.
  • RouterLink directive provides navigation to the new route that we created. note how we are passing {{pokemon._id}} in place of :id from route path url.

9. and there, you have a click navigation enabled on your pokemon list. if you click on any of the names, you should be redirected to a similar url like below,


where last part is the id of selected pokemon, that is coming from api data.

but for now, details component displays just a hard-coded text. let’s update this to display some interesting details.

10. we need details for the selected pokemon id. update PokemonService that we created in previous article, to get single pokemon details by it’s id.

11. use the above service during OnInit hook of our PokemonDetailsComponent as shown below:

apart from the familiar component that we know from previous articles, we are importing ActivatedRoute class from router library. this class holds route specific information, which in this case is the id of selected pokemon (remember :id from route config path).

12. now that we have details of the selected pokemon, let’s update component view template to display some of this data:

notice [src] in img tag above. this is an example of one-way property (not attribute, though the name is same) binding in angular templates.
[src] is equivalent to ng-src from angular 1.x
also, | is a pipe, equivalent to filters in angular 1.x

and we have our details route ready, to display selected pokemon name (in uppercase), photo and evolution source.

next, we will look into the details of one of the core concepts of angular — dependency injection (DI)and services.

<prev | next(coming soon)>