是否可以使用Vue Router中的beforeEnter导航守卫来重定向用户?

发布于 2025-01-11 16:16:31 字数 1870 浏览 3 评论 0原文

我正在使用 Vue2 和 Vue Router 3.5 构建 SPA 应用程序

该应用程序有两个身份验证路由,“admin”和“organization”

中都有自己的前缀

我有路由器设置,以便每个身份验证守卫在 url '/auth/:guard '

'/organization'

'/admin'

路由器文件如下所示:


const routes = [
    organisations,
    authRoutes,
]

const router = new VueRouter({
  mode: 'history',
  base: process.env.BASE_URL,
  routes
})

在组织文件内部,我返回一个对象:

export default {
    path: '/organisations',
    meta: { auth: true, guard: 'organisations' },
    component: () => import('../views/Organisations/OrganisationContainer.vue'),
    beforeEnter: (to, from, next) => {
        return store.dispatch('authentication/check')
            .then(response => {
                if(response) {
                    if(response.guard == 'admin') {
                        return next('/admin')
                    }
                    if(response.guard != 'organisation') {
                        return false
                    }
                }else{
                    return next('/auth/organisation/login')
                }
            })
    },
    children: [
        {
            path: '/',
            name: 'organisation.dash',
            meta: { auth: true, route_identifier: 'dashboard', title: 'Dashboard' },
            component: () => import('../views/Organisations/Dashboard/Dashboard.vue')
        },
}

在之前的项目中,我使用 router.beforeEach 来处理 系统。

router.beforeEach 的问题是我不想有一个大的方法来处理系统中每条路线的导航。如果我可以有类似

“如果有人尝试访问 /organization 路线,并且他们没有登录,则将用户重定向到路线 /auth/organization/login(如果他们是)”的内容, 那就容易多了已登录,但他们是管理员,请将用户重定向到他们的仪表板。”

我计划使用 beforeEnter 来实现此目的 - 但每当我尝试使用 next() 函数进行重定向时,都会返回空白屏幕。如果我返回不带参数的 next() 函数,它不会重定向,但页面仍然加载。

我可能误用了 beforeEnter 导航防护 - 但有谁知道如何使用 beforeEnter 导航防护重定向用户,或者在不使用 beforeEach 并有一个大方法来应对的情况下实现类似的功能?

提前致谢

I'm building an SPA application using Vue2 and Vue Router 3.5

The application has two authentication routes, 'admin' and 'organisation'

I have the router setup so that each auth guard has it's own prefix in the url

'/auth/:guard'

'/organisation'

'/admin'

The router file looks like this:


const routes = [
    organisations,
    authRoutes,
]

const router = new VueRouter({
  mode: 'history',
  base: process.env.BASE_URL,
  routes
})

Inside of the organisations file, I return an object:

export default {
    path: '/organisations',
    meta: { auth: true, guard: 'organisations' },
    component: () => import('../views/Organisations/OrganisationContainer.vue'),
    beforeEnter: (to, from, next) => {
        return store.dispatch('authentication/check')
            .then(response => {
                if(response) {
                    if(response.guard == 'admin') {
                        return next('/admin')
                    }
                    if(response.guard != 'organisation') {
                        return false
                    }
                }else{
                    return next('/auth/organisation/login')
                }
            })
    },
    children: [
        {
            path: '/',
            name: 'organisation.dash',
            meta: { auth: true, route_identifier: 'dashboard', title: 'Dashboard' },
            component: () => import('../views/Organisations/Dashboard/Dashboard.vue')
        },
}

In previous projects I've used the router.beforeEach to handle navigation in the system.

The problem with router.beforeEach is that I don't want to have one large method to handle the navigation for every route in the system. It'd be a whole lot easier if I could just have something like

"If anyone tries to visit a /organisation route, and they aren't logged in, redirect the user to the route /auth/organisation/login, if they are logged in, but they are an admin, redirect the user to their dashboard."

I was planning to use beforeEnter to achieve this - but whenever I attempt to use the next() function to redirect, a blank white screen is returned. If I return the next() function without parameters, it doesn't redirect, but the page still loads.

I'm probably misusing the beforeEnter navigation guard - but does anyone know how I could redirect a user using the beforeEnter navigation guard, or achieve similar functionality without using beforeEach and having a large method to contend with?

Thanks in advance

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

倚栏听风 2025-01-18 16:16:31

router.beforeEach 的问题是我不想有一个
处理系统中每条路线的导航的大型方法。

这种方法完全没有问题,只需确保 beforeEach 中的代码速度快(不要在 beforeEach 中进行 API 调用),如果您有很多代码,那么没有什么可以阻止您将代码分成多个函数,所以它是更具可读性。

但是,如果您确实不需要使用 beforeEach 并且只有几条具有特定要求的路由,则可以使用 beforeEnter 但它与 beforeEach 有点不同.。首先,在您提供的代码片段中,您在路由上定义了一个 beforeEach 回调,但 beforeEach 是路由器级别回调,如 文档中描述

您必须更改代码片段并将 beforeEach 替换为 beforeEnter,如下所示:

export default {
    path: '/organisations',
    meta: { auth: true, guard: 'organisations' },
    component: () => import('../views/Organisations/OrganisationContainer.vue'),
    beforeEnter: (to, from, next) => {
        return store.dispatch('authentication/check')
            .then(response => {
                if(response) {
                    if(response.guard == 'admin') {
                        return next('/admin')
                    }
                    if(response.guard != 'organisation') {
                        return false
                    }
                }else{
                    return next('/auth/organisation/login')
                }
            })
    },
    children: [
        {
            path: '/',
            name: 'organisation.dash',
            meta: { auth: true, route_identifier: 'dashboard', title: 'Dashboard' },
            component: () => import('../views/Organisations/Dashboard/Dashboard.vue')
        },
}

The problem with router.beforeEach is that I don't want to have one
large method to handle the navigation for every route in the system.

There's nothing wrong with this approach at all, just make sure your code in beforeEach is fast (don't make API calls in beforeEach) and if you have a lot of code there's nothing stopping you split the code a bit into multiple functions so it's more readable.

However, if you really don't need to use beforeEach and you only have a few routes with specific requirements you can use beforeEnter but it's a bit different than beforeEach.. First of all, in the code snippet you provided you defined a beforeEach callback on the route, but beforeEach is a router level callback as described in docs.

You have to change your snippet and replace beforeEach with beforeEnter like this:

export default {
    path: '/organisations',
    meta: { auth: true, guard: 'organisations' },
    component: () => import('../views/Organisations/OrganisationContainer.vue'),
    beforeEnter: (to, from, next) => {
        return store.dispatch('authentication/check')
            .then(response => {
                if(response) {
                    if(response.guard == 'admin') {
                        return next('/admin')
                    }
                    if(response.guard != 'organisation') {
                        return false
                    }
                }else{
                    return next('/auth/organisation/login')
                }
            })
    },
    children: [
        {
            path: '/',
            name: 'organisation.dash',
            meta: { auth: true, route_identifier: 'dashboard', title: 'Dashboard' },
            component: () => import('../views/Organisations/Dashboard/Dashboard.vue')
        },
}

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文