Vue.js 动态路由
在 Vue.js 中,动态路由通常是通过 Vue Router 插件来实现的。Vue Router 允许你在路由路径中使用动态段,这些段可以捕获 URL 中的部分,并将它们传递给组件作为参数。
设置 Vue Router
首先,你需要安装 Vue Router 并在你的项目中配置它。
bash
npm install vue-router
然后,在你的项目中设置路由:
javascript
// router.js
import Vue from 'vue';
import Router from 'vue-router';
import PostDetail from './components/PostDetail.vue';
Vue.use(Router);
export default new Router({
routes: [
{
path: '/posts/:postId',
name: 'post-detail',
component: PostDetail
},
],
});
接下来,在你的 Vue 应用中引入并使用这个路由器:
javascript
// main.js
import Vue from 'vue';
import App from './App.vue';
import router from './router'; // 引入上面定义的路由器
new Vue({
el: '#app',
router, // 使用路由器
render: h => h(App),
});
动态路由组件
在你的组件中,你可以通过 $route.params 访问动态路由参数:
html
<template>
<div>
<h1>Post Detail</h1>
<p>ID: {{ $route.params.postId }}</p>
</div>
</template>
<script>
export default {
name: 'PostDetail',
};
</script>
Nuxt.js 动态路由
Nuxt.js 对动态路由的支持更为简单直观,因为它是基于文件系统的。如果你有一个动态路由 /posts/:postId
,你只需要创建一个 _postId.vue 文件在 pages/posts
目录下即可。
创建动态路由页面
在 pages 目录下创建 posts 文件夹,并在其中创建 _postId.vue
文件:
html
<template>
<div>
<h1>Post Detail</h1>
<p>ID: {{ $route.params.postId }}</p>
</div>
</template>
<script>
export default {
async asyncData({ params }) {
// 你可以在这里根据 postId 获取数据
return { postId: params.postId };
},
};
</script>
这样就自动创建了一个 /posts/:postId 的动态路由。
Vue.js 中间件
Vue.js 没有内置的中间件概念,但是你可以使用路由守卫来实现类似的功能。路由守卫可以让你在路由改变之前或之后执行某些逻辑。
使用路由守卫
例如,你可以使用全局前置守卫来检查用户是否已经登录:
javascript
// router.js
router.beforeEach((to, from, next) => {
if (to.matched.some(record => record.meta.requiresAuth)) {
if (!isLoggedIn()) {
next({
path: '/login',
query: { redirect: to.fullPath }
});
} else {
next();
}
} else {
next(); // 确保一定要调用 next()!
}
});
在路由元信息中指定
你可以给路由添加 meta 属性来标记哪些路由需要认证:
javascript
{
path: '/secret',
name: 'secret',
component: SecretPage,
meta: { requiresAuth: true }
}
Nuxt.js 中间件
Nuxt.js 提供了中间件的概念,可以在页面加载之前执行一些逻辑,比如认证检查。
创建中间件
在 middleware
文件夹下创建一个文件,例如 auth.js
:
javascript
// middleware/auth.js
export default function ({ store, redirect }) {
if (!store.getters['auth/isLoggedIn']) {
return redirect('/login');
}
}
应用中间件
然后在你的页面中引用这个中间件:
yaml
// pages/secret.vue
middleware: 'auth'
或者在 nuxt.config.js 中全局应用:
javascript
export default {
router: {
middleware: ['auth']
}
}
Vue.js 动态路由高级用法
嵌套路由
在 Vue.js 中,你可以使用嵌套路由来组织复杂的页面结构。例如,你可以创建一个博客系统,其中包含多个分类和文章:
javascript
// router.js
import Vue from 'vue';
import Router from 'vue-router';
import Posts from './components/Posts.vue';
import PostDetail from './components/PostDetail.vue';
Vue.use(Router);
export default new Router({
routes: [
{
path: '/posts',
component: Posts,
children: [
{
path: ':postId',
name: 'post-detail',
component: PostDetail
}
]
}
]
});
路由守卫
除了全局前置守卫外,还可以使用其他类型的路由守卫:
全局后置守卫:在路由改变完成后执行:
javascript
router.afterEach((to, from) => {
// 执行一些操作,如更新标题
document.title = to.meta.title;
});
组件内的守卫:在组件内定义守卫:
javascript
export default {
beforeRouteEnter(to, from, next) {
// 在渲染该组件的对应路由被 confirm 前调用
next(vm => {
vm.fetchData();
});
},
beforeRouteUpdate(to, from, next) {
// 在当前路由改变,但是该组件被复用时调用
this.fetchData();
next();
},
beforeRouteLeave(to, from, next) {
// 用户离开此组件的对应路由时调用
if (this.isDirty) {
next(false);
} else {
next();
}
}
};
Nuxt.js 动态路由高级用法
嵌套路由
在 Nuxt.js 中,嵌套路由同样可以通过文件系统来实现。例如:
plaintext
pages/
posts/
index.vue
_id.vue
这将自动生成以下路由:
bash
/posts
/posts/:id
复杂的动态路由
Nuxt.js 还支持更复杂的动态路由,例如嵌套动态段:
bash
plaintext
pages/
users/
_userId/
posts/
_postId.vue
这将生成以下路由:
/users/:userId/posts/:postId
异步数据加载
Nuxt.js 提供了多种方法来异步加载数据,例如 asyncData 和 fetch 方法:
javascript
// pages/posts/_id.vue
export default {
async asyncData({ params, $axios }) {
const post = await $axios.$get(`/api/posts/${params.id}`);
return { post };
}
};
Nuxt.js 中间件高级用法
组合中间件
你可以组合多个中间件来执行一系列逻辑:
javascript
// middleware/auth.js
export default function ({ store, redirect }) {
if (!store.getters['auth/isLoggedIn']) {
return redirect('/login');
}
}
// middleware/admin.js
export default function ({ store, redirect }) {
if (!store.getters['auth/isAdmin']) {
return redirect('/forbidden');
}
}
然后在页面中应用这些中间件:
yaml
// pages/admin/dashboard.vue
middleware: ['auth', 'admin']
中间件参数
中间件可以接收额外的参数:
javascript
// middleware/auth.js
export default function ({ store, redirect }, inject) {
inject('isLoggedIn', store.getters['auth/isLoggedIn']);
if (!store.getters['auth/isLoggedIn']) {
return redirect('/login');
}
}
全局中间件
你可以在 nuxt.config.js
中全局应用中间件:
javascript
export default {
router: {
middleware: ['auth']
}
}