Search code examples
javascriptember.jsember-datatransitionember-cli

Ember.js 2, transitionTo using multiple dynamic segments in first level route


I'm using Ember >= 2.13.x.

I need to use transitionTo from a route action to go in another route.

Here is the demo ember-twiddle: https://ember-twiddle.com/3cbb806f31f8d71a6c414452f4fc9ded

I have this situation:

router.json:

Router.map(function() {
  this.route('home', {path: '/'});
  this.route('categories', {path: 'categories'});
  this.route('category', {path: ':category_id'});
  this.route('posts', {path: 'posts'});
  this.route('post', {path: ':category_id/:post_id'}); //I have multiple synamic segments in here
});

routes/application.js:

actions: {
    goToPost() {
        let post = this.store.findRecord('post', 1);
        this.transitionTo('post', post);
    }
}

routes/post.js:

model(params) {
    return this.store.findRecord('post', params.id);
},

serialize(model) {
    console.log('model in serialize():', model);
    return { category_id: model.get('category.id'), post_id: model.id };
}

templates/application.hbs:

<button type="button" {{action 'goToPost'}}>GoToPost with action (transitionTo)</button>

So when I click everything works as expected.

I fetch the model in application action and then I use this.transitionTo('post', post);.

In my post route then I have serialize() which, I read now, is using for URL composition when dynamic segments are present.

My question: I'm using it the right way?

Why I cannot use something like this: this.transitionTo('post', post.category.id, post.id); and let model() in post route fetch the model (from DB or store)?

I also tried to use this.transitionTo('post', {category_id: post.category.id, post_id: post.id}); but obviously the post route model() doesn't load anything because it really thinks the object is already there.

So, I can fix this problem with serialize() method only. Is it the right way?


Solution

  • You don't need to override serialize hook, by default you will get the dynamic segments and queryParams in route model hook arguments.

    model({post_id,category_id}) {
     return this.store.findRecord('post', post_id);
    }
    

    Here is the twiddle

    this.route('category', {path: 'category/:category_id'});
    this.route('post', {path: 'post/:category_id/:post_id'});
    

    I prefer to add corresponding prefix like post so that URL will become easily distinguisable.

    If you want transitionTo to call model hook, then provide object or model in the argument always provide the required parameter may be string or number. Refer: https://guides.emberjs.com/v2.14.0/routing/defining-your-routes/#toc_dynamic-segments