How to group routes in vue-router - vuejs2

On my site I have a navigations with some categories and nested navigation anchors in them. How can I group this routes in vue-router? The best I've come up with is to place for each route a meta and then group by it.

I use like this (look that component: { render: h => h('router-view') }):
{
// =============================================================================
// MAIN LAYOUT ROUTES
// =============================================================================
path: '',
component: () => import('./layouts/main/Main.vue'),
children: [
// =============================================================================
// Routes
// =============================================================================
{
path: '/',
name: 'home',
component: () => import('./views/Dashboard.vue'),
},
// =============================================================================
// User Routes
// =============================================================================
{
path: '/user',
name: 'user',
component: { render: h => h('router-view') },
children: [
{
path: 'list',
name: 'user.list',
component: () => import('./views/pages/User/List.vue'),
},
]
},
],
}

There is forked and fixed example: https://jsfiddle.net/andrewright/wsmx92bg/
You should know, that children routers opens inside parent template. That means you need to add additional <router-view> inside parent template.
The idea is that: children routers change some block, like part of parent content. Good way to use it - for subcategory menu.

You can use nested routes. In your routes file you can do something similar.
{
path: '/category',
name: 'category',
component: Category,
children: [
{
path: 'subcategory',
name: 'subCategory',
component: ChildComponent,
},
// other nested routes
]
},

Related

How to define vue routers with dynamic child routes?

I am trying something like this
{
path: "/portfolio",
component: () =>
import("../common/components/Layout/Layout/Profile/ProfileLayout"),
meta: { requiresAuth: false },
children: [
{
path: "/:username",
component: () =>
import(/*webpackChunkName: "profile"*/ "../modules/Profile/Profile"),
},
],
},
But the piece of code is not working while routes without child routes working perfectly
{
path: "/profile/:userName",
component: () => import("../modules/profile/UserProfile"),
}
how can i solve the first piece of code ?
You should remove the prepended slash from the child route path :
path: ":username",
or try out :
path: "user/:username",
then you could visit the url like /portfolio/user/john

How can i make few children dynamic routes?

I need few dynamic route in Vue router like
/payouts/:person
/payouts/:pay_id
I tried make some children routes but its not working, its work like this only with id but it not what i want
{
path: 'payouts',
name: 'Payouts',
meta: {
title: 'Payouts'
},
component: () => import('#/pages/Payouts'),
},
{
path: 'payouts/:pay_id',
name: 'Pay_id',
meta: {
title: 'Pay'
},
component: () => import('#/pages/Pay_id'),
},
For parameterised routes use
this.$router.push({name: 'payouts', params: { pay_id: "SomeID"}});
Or
this.$router.push({path: '/newLocation/SomeID'});
for non parameterised route
this.$router.push({path: '/newLocation'});

How to set vue-router nested routes like a children

I'm trying to put a router that is imported as a constant in main router`s children
router/components/slider/index.js:
const sliderRouter = {
path: '/slider',
name: 'Slider',
meta: {
title: 'Slider'
},
component: () => import('#/views/components/slider'),
}
export default sliderRouter
router/index.js:
...
import authRouter from './modules/auth'
import sliderRouter from './modules/components/slider'
...
export default new Router({
mode: 'history',
linkActiveClass: "active selected",
routes: [
authRouter, // this work
{
path: '/admin',
name: 'primary',
meta: { requiresAuth: true },
// remastered version
component: loadView('MainLayout'),
children: [
sliderRouter, /* make something like this */
//recent routes
{
path: '/home',
name: 'home',
// route level code-splitting
// this generates a separate chunk (about.[hash].js) for this route
// which is lazy-loaded when the route is visited.
// classic version:
component: () => import(/* webpackChunkName: "about" */ '../views/Home.vue')
// component: About
}
]
},
Is it really possible to make the slider router work in such way and inherit from the MainLayout (like a typical child), and also URL would be '/admin/slider'?
I solved it by changing the path in the slider
path: '/slider',
to
path: 'slider',
because it is using like child route which does not require a slash before it`s name

Vue Router duplicate $route info

I have a route and sub route like these.
export default new Router({
routes: [
{
path: '/user',
component: UserView,
meta: {title: 'User Manager'},
children: [
{path: 'editor', component: EditorView, meta: {title: 'User Editor'}}
]
}
]
})
In UserView and EditorView both have mounted function.
export defaults {
mounted () {
console.log(this.$route)
}
}
And i type http://host:port/#/user/editor in browser, the console print twice $route data and they is same object. How could i get UserView route data?
{name: undefined, meta: {…}, path: "/user/editor", hash: "", query: {…}, …}
{name: undefined, meta: {…}, path: "/user/editor", hash: "", query: {…}, …}
UserView and EditorView is in the same page and they html look like this picture.
There are multiple route parts that are matched for a given URL when nested routes are involved. You'll need to search this.$route.matched for the specific route that you are interested in.
If you set a name for the route you're interested in, it'll make it easier to find:
{
path: 'editor',
name: 'editor', // <-- Add this
component: EditorView,
meta: {
title: 'User Editor'
}
}
mounted() {
const route = this.$route.matched.find(r => r.name === 'editor');
console.log(route.meta.title);
}

Vue.js nested routing with default child

I have an issue with a default children route in Vue.js 2.
When I visit localhost/listings initially, it correctly loads index.vue and map.vue as a child.
When I navigate using router-link to localhost/listings/1, and then using router-link back to localhost/listings, then it still loads the show.vue template. This shouldn't happen?
I have no navigation guards or anything that should interfere. Is there anyway to correct this?
My routes:
window.router = new VueRouter({
routes: [
...
{
path: '/listings',
name: 'listing.index',
component: require('./components/listing/index.vue'),
children: [
{
path: '',
component: require('./components/listing/map.vue')
},
{
path: ':id',
name: 'listing.show',
component: require('./components/listing/show.vue')
}
]
},
...
]
});
The "father" router should not be named if you want a default child route, so instead using :to="{name: 'listing.index'}", use the name of the default child route (e.g :to="{name: 'listing.map'}").
The code should look like this:
window.router = new VueRouter({
routes: [
...
{
path: '/listings',
component: require('./components/listing/index.vue'),
children: [
{
path: '',
name: 'listing.map'
component: require('./components/listing/map.vue')
},
{
path: ':id',
name: 'listing.show',
component: require('./components/listing/show.vue')
}
]
},
...
]
});
Maybe try re-arranging the children, routes are fired in the order they match from top-to-bottom, so this should hopefully fix it:
window.router = new VueRouter({
routes: [
...
{
path: '/listings',
name: 'listing.index',
component: require('./components/listing/index.vue'),
children: [
{
path: ':id',
name: 'listing.show',
component: require('./components/listing/show.vue')
}
{
path: '',
component: require('./components/listing/map.vue')
},
]
},
...
]
});
Just for a bit of clarification, your path: '' essentially serves as a "catch all", which is likely why when it's at the top it's being found immediately and so the router never propagates any further down to the :id route.
In Vue 2.6.11 you can automatically redirect to a child route if parent route is hit:
const routes = [
{
name: 'parent',
path: '/',
component: Parent,
children: [
{
name: 'parent.child',
path: 'child',
component: Child,
}
],
/**
* #type {{name: string} | string} Target component to redirect to
*/
redirect: {
name: 'parent.child'
}
}
];
When you are using named routes and you want to load the component with your child inside, you have to use the name route for the child.
In your Navigation menu links, if you use name route for the parent, the child will not load automatically, even if the child path is nothing.
Let's say for example we have a User route, and we want to show list of users inside the component by default so whenever we go to '/user' path we want to load a list of users as a child in there:
routes: [
{
path: '/user',
name: 'User',
component: User,
children: [
{path: '', name: 'UserList', component: UserList}, // <== child path is = '';
]
}
]
If you think about the code, you might assume if you go to route with name 'User' you might get UserList in there as well, because the path for parent and children both are same. but it's not and you have to choose 'UserList' for the name.
Why this is happening?
Because Vuejs loads the exact component you are referring to, not the url.
you can actually test this, instead of using named route in your links, you can just refer the url, this time vuejs will load the parent and child together with no problem, but when you use named route, it doesn't look at the url and loads the component you are referring to.