1

So, I am looking to produce paths like these:

matches/:page/:team/:season

where :team and :season are optional parameters so I could have an url like

matches/results/4/2017 or
matches/results/4 or
matches/results

all should be valid and come through in this.route.snapshot.params

I tried this:

  {path: 'matches', children: [
    {path: '', pathMatch: 'full', redirectTo: 'fixtures'},
    {path: 'competitions', component: CompetitionsPageComponent},
    {path: ':page', component: PageComponent, children: [
      {path: ':team', children:[
          {path: ':season', children:[]}
      ]}
    ]},
  ]},

with no luck, only :page comes through as param

DS_web_developer
  • 3,622
  • 13
  • 52
  • 83
  • how many values can :page have? is that really a route parameter or just a subpath in your routes? – Jota.Toledo Jun 08 '17 at 11:55
  • The next question is, do you want to modelate the routes that you mention as nested routes or siblings? – Jota.Toledo Jun 08 '17 at 11:59
  • so, :pager can have two other values (results/fixtures) that point to the PageComponent... competitions (that is on the same level) points to another component..... and page will have 2 params (/:team/:season) later on another one (:competition)... they are all part of the PageComponent ... the paths listed above illustrate the logic of what I'd like to achieve..... if I do matches/results/7/2016 .... I would like to get from snapshot params: {page: 'results', team: 7, season: 2016}... on that route and settings above I get only {page: 'results} – DS_web_developer Jun 08 '17 at 12:27
  • The explanation will take me a while, but is related to the snapshot that you take from the route parameters – Jota.Toledo Jun 08 '17 at 12:33
  • May I ask in which component are you injecting an instance of ActivatedRoute? – Jota.Toledo Jun 08 '17 at 12:43
  • do it on PageComponent..... ngOnInit() { this.router.events .filter(event => event instanceof NavigationEnd) .map(() => this.route.snapshot.params) .subscribe((params) => { – DS_web_developer Jun 08 '17 at 12:46
  • @DS_web_developer, I think you should define 3 different routes, no children. Otherwise each parameter belongs to the separate segment – Max Koretskyi Jun 08 '17 at 13:33

3 Answers3

4

I think something you want to think about are you really wanting child routes or just the same page or each level? The other example will end up rendering both components ... which might be what you want, but if not then you might spell out each one.

{ path: 'matches/results/', component: ResultsComponent, },
{ path: 'matches/results/:page/', component: PageComponent, },
{ path: 'matches/results/:page/:team/', component: TeamComponent, },
{ path: 'matches/results/:page/:team/:season', component: PageComponent, },

also note the name you use in the path is the name you need to use in the param selector:

params['page']
params['team']
params['season']

example code

this.route.params.subscribe((params) => {
    this.teamService.getTeam(params['team']).subscribe((team) => {
        this.team = team;
    });
});
Tim.Burnell
  • 346
  • 1
  • 9
  • Yeah, this is what I wanted... well, sort of... but close enough. thanks – DS_web_developer Jun 08 '17 at 14:19
  • Hey Tim, how would you pass the params to router.navigate when you are to stay on the same component? (but different url params in regards to :team/:season) – Pakk Mar 22 '18 at 15:55
  • In this example i think you want it to change because they are different components. but if you are using the same component, i think you might want to use query params instead. You can add query params without reloading the component. (but you will want to make sure you process them on load.) – Tim.Burnell Mar 26 '18 at 15:07
3

Consider the following structure:

const paths: Routes = [
  {
    path: 'matches',
    children: [
      { path: '', pathMatch: 'full', redirectTo: 'fixtures' },
      { path: 'fixtures', component: FixturesComponent },
      { path: 'competitions', component: CompetitionsPageComponent },
      {
        path: ':page',
        component: PageComponent,
        children: [
          {
            path: ':team',
            component: TeamComponent
            children: [
              {
                path: ':season',
                component: SeasonComponent,
                children: [

                ]
              }
            ]
          }
        ]
      }
    ]
  }
];

Depending on in which component you inject ActivatedRoute, you will be able to access different route parameters. For example

If you inject ActivatedRoute in SeasonComponent and do the following:

this._route.params.subscribe(p => console.log(JSON.stringify(p)));

You will see an object made of page,team and season properties.

If you do the same for PageComponent, you will get an object made of only one property, page. If u get the point, if you inject ActivatedRoute in the TeamComponent, parameters would have only 2 properties.

The fact that you listen to the Router events and then read the properties in the ActivatedRoute instance dont make a difference, because the injected instance of the ActivatedRoute class contains only the parameters that where present in the route at the moment that the component, in which the instance is being injected, was generated.

So basically, at least with this approach, is not possible to access from a component at a certain level in the component hierarchy to route parameters further down in it.

Hope it helps!

Jota.Toledo
  • 27,293
  • 11
  • 59
  • 73
0

@user2623919 answers close enough...

this is what is working for me... all the routes point to the same PageComponent and in my params I get the ones I set.... this way

{path: 'matches', children: [
  {path: '', pathMatch: 'full', redirectTo: 'fixtures'},
  {path: 'competitions-table', component: CompetitionsPageComponent},
  {path: ':page', component: PageComponent},
  {path: ':page/:team', component: PageComponent},
  {path: ':page/:team/:competition', component: PageComponent},
  {path: ':page/:team/:competition/:season', component: PageComponent}
]},

/matches/results

gives me params {page: 'results'} and

/matches/results/20

gives me params {page: 'results', team: '20'} and so on

Cheers guys

DS_web_developer
  • 3,622
  • 13
  • 52
  • 83