# 前言
使用场景:
- 验证用户权限,满足条件时进入导航,否则重定向到登录页面。
- 实现不同的页面缓存策略,如单个页面缓存,动态路由缓存。
vue-router提供了三个不同维度的导航守卫:
- 全局守卫
- 路由独享守卫
- 组件内的守卫
# 全局守卫
- 全局前置守卫(导航触发时调用)
- 全局解析守卫(在导航确认前,并在所有组件内守卫解析完调用)
- 全局后置守卫(导航已完成时调用)
# 使用方法
// main.js 入口文件
import router from './router'; // 引入路由
// 全局前置守卫
router.beforeEach((to, from, next) => {
next();
});
// 全局解析守卫
router.beforeResolve((to, from, next) => {
next();
});
// 全局后置守卫
router.afterEach((to, from) => {
});
# to、from、next 这三个参数
- to、from 分别对应,"将要进入" 和 "将要离开" 的路由对象,即平时通过
this.$route获取到的对象。 - next函数,保证至少调用一次,否则不会进入下一个钩子。
- next(),进入下个路由
- next(false),停止,并回到上一个路由
- next({path}),停止,并跳转到另外一个路由
- next方法允许设置一些参数
# 路由独享守卫
仅一个enter
const router = new VueRouter({
routes: [
{
path: '/foo',
component: Foo,
beforeEnter: (to, from, next) => {
// 在全局前置守卫后调用,
// 所以不会被全局守卫覆盖
// ...
}
}
]
})
# 组件内导航守卫
- beforeRouteEnter
- beforeRouteUpdate
- beforeRouteLeave
const Foo = {
template: `...`,
beforeRouteEnter (to, from, next) {
// 在渲染该组件的对应路由被 确认 前调用
// 不!能!获取组件实例 `this`
// 因为当守卫执行前,组件实例还没被创建
// 但可以在传递的回调中访问实例
// next((vm)=>{ vm即实例 })
},
beforeRouteUpdate (to, from, next) {
// 在当前路由改变,但是该组件被复用时调用
// 举例来说,对于一个带有动态参数的路径 /foo/:id,在 /foo/1 和 /foo/2 之间跳转的时候,
// 由于会渲染同样的 Foo 组件,因此组件实例会被复用。而这个钩子就会在这个情况下被调用。
// 可以访问组件实例 `this`
},
beforeRouteLeave (to, from, next) {
// 导航离开该组件的对应路由时调用
// 可以访问组件实例 `this`
}
}
# 路由导航解析流程
- 触发进入其他路由。
- 调用要离开路由的组件守卫beforeRouteLeave
- 调用局前置守卫:beforeEach
- 在重用的组件里调用 beforeRouteUpdate
- 调用路由独享守卫 beforeEnter。
- 解析异步路由组件。
- 在将要进入的路由组件中调用beforeRouteEnter
- 调用全局解析守卫 beforeResolve
- 导航被确认。
- 调用全局后置钩子的 afterEach 钩子。
- 触发DOM更新(mounted)。
- 执行beforeRouteEnter 守卫中传给 next 的回调函数
← keep-alive详解 实现路由缓存 →