javascriptvue.jsvue-routerrouteparams

Route path contain data that would be fetched into beforeRouteEnter


In my router there is a dynamic Route that I need to set the last part of its path after the data is fetched from the store call in beforeRouteEnter

beforeRouteEnter (to, from, next) {
if(to.params.categoryId) {
  next(vm => {
    store.dispatch('getSearchResults', to.params)
      .then(res => {
        let category = res.data.categories.find(cat => cat.id == to.params.categoryId);
        to.params.CName = category.name;
        // to.path = to.path + `/${category.name}`;
        console.log(to)
      }).catch(err => false)
  })
}else next();

the Route:

{
  path: 'directory/bc-:categoryId(\\d+)?/:CName?',
  name: 'SearchResults',
  component: () => import(/* webpackChunkName: "listing" */ '../views/SearchResults.vue')
},

I need to change the CName in the Route to category.name from the data so that the route finally shows the category name after the Id


Solution

  • You should use a route with 2 children - one that will dispatch the Vuex action and then go to the other child.

    {
      path: 'directory/bc-:categoryId(\\d+)?',
      name: 'SearchResultsParent',
      redirect:
      {
        name: 'SearchResultsFetch',
      },
      component: WrapperComponent,
      children:
      [
        {
          path: '',
          name: 'SearchResultsFetch',
          component: FetchSearchResults,
        },
        {
          path: ':CName',
          name: 'SearchResultsList',
          component: ShowSearchResults,
        },
      ]
    }
    
    // WrapperComponent.vue
    <template>
      ....
      <router-view />
      ....
    </template>
    
    // FetchSearchResults.vue
    <script>
    export default
    {
      created()
      {
        this.fetchData();
      },
      beforeRouteUpdate(to, from, next)
      {
        this.fetchData();
        next();
      },
      methods:
      {
        fetchData()
        {
          store.dispatch('getSearchResults', this.$route.params)
          .then(res => {
            let category = res.data.categories.find(cat => cat.id == this.route.params.categoryId);
            this.$router.push({
              name: 'SearchResultsList',
              params:
              {
                categoryId: this.$route.params.categoryId,
                CName: category.name,
              }
            });
          }).catch(err => false)
        }
      }
    }