hookehuyr

refactor(router): 优化路由认证检查逻辑

重构路由认证检查逻辑,使用更灵活的正则和精确匹配模式,提高代码可维护性
1 /* 1 /*
2 * @Date: 2025-03-20 20:36:36 2 * @Date: 2025-03-20 20:36:36
3 * @LastEditors: hookehuyr hookehuyr@gmail.com 3 * @LastEditors: hookehuyr hookehuyr@gmail.com
4 - * @LastEditTime: 2025-03-21 15:59:36 4 + * @LastEditTime: 2025-03-21 17:58:10
5 * @FilePath: /mlaj/src/router/index.js 5 * @FilePath: /mlaj/src/router/index.js
6 * @Description: 文件描述 6 * @Description: 文件描述
7 */ 7 */
...@@ -31,13 +31,13 @@ const routes = [ ...@@ -31,13 +31,13 @@ const routes = [
31 path: '/courses/:id/reviews', 31 path: '/courses/:id/reviews',
32 name: 'CourseReviews', 32 name: 'CourseReviews',
33 component: () => import('../views/courses/CourseReviewsPage.vue'), 33 component: () => import('../views/courses/CourseReviewsPage.vue'),
34 - meta: { title: '课程评价' } 34 + meta: { title: '课程评价' },
35 }, 35 },
36 { 36 {
37 path: '/courses-list', 37 path: '/courses-list',
38 name: 'CourseList', 38 name: 'CourseList',
39 component: () => import('../views/courses/CourseListPage.vue'), 39 component: () => import('../views/courses/CourseListPage.vue'),
40 - meta: { title: '课程列表' } 40 + meta: { title: '课程列表' },
41 }, 41 },
42 { 42 {
43 path: '/profile', 43 path: '/profile',
...@@ -49,79 +49,79 @@ const routes = [ ...@@ -49,79 +49,79 @@ const routes = [
49 path: '/login', 49 path: '/login',
50 name: 'Login', 50 name: 'Login',
51 component: () => import('../views/auth/LoginPage.vue'), 51 component: () => import('../views/auth/LoginPage.vue'),
52 - meta: { title: '登录' } 52 + meta: { title: '登录' },
53 }, 53 },
54 { 54 {
55 path: '/register', 55 path: '/register',
56 name: 'Register', 56 name: 'Register',
57 component: () => import('../views/auth/RegisterPage.vue'), 57 component: () => import('../views/auth/RegisterPage.vue'),
58 - meta: { title: '注册' } 58 + meta: { title: '注册' },
59 }, 59 },
60 { 60 {
61 path: '/forgotPwd', 61 path: '/forgotPwd',
62 name: 'ForgotPassword', 62 name: 'ForgotPassword',
63 component: () => import('../views/auth/ForgotPasswordPage.vue'), 63 component: () => import('../views/auth/ForgotPasswordPage.vue'),
64 - meta: { title: '忘记密码' } 64 + meta: { title: '忘记密码' },
65 }, 65 },
66 { 66 {
67 path: '/activities', 67 path: '/activities',
68 name: 'Activities', 68 name: 'Activities',
69 component: () => import('../views/activities/ActivitiesPage.vue'), 69 component: () => import('../views/activities/ActivitiesPage.vue'),
70 - meta: { title: '活动列表' } 70 + meta: { title: '活动列表' },
71 }, 71 },
72 { 72 {
73 path: '/activities/:id', 73 path: '/activities/:id',
74 name: 'ActivityDetail', 74 name: 'ActivityDetail',
75 component: () => import('../views/activities/ActivityDetailPage.vue'), 75 component: () => import('../views/activities/ActivityDetailPage.vue'),
76 props: true, 76 props: true,
77 - meta: { title: '活动详情' } 77 + meta: { title: '活动详情' },
78 }, 78 },
79 { 79 {
80 path: '/activities/:id/signup', 80 path: '/activities/:id/signup',
81 name: 'ActivitySignup', 81 name: 'ActivitySignup',
82 component: () => import('../views/activities/ActivitySignupPage.vue'), 82 component: () => import('../views/activities/ActivitySignupPage.vue'),
83 meta: { 83 meta: {
84 - title: '活动报名' 84 + title: '活动报名',
85 - } 85 + },
86 }, 86 },
87 { 87 {
88 path: '/profile/activities', 88 path: '/profile/activities',
89 name: 'MyActivities', 89 name: 'MyActivities',
90 component: () => import('../views/activities/MyActivitiesPage.vue'), 90 component: () => import('../views/activities/MyActivitiesPage.vue'),
91 - meta: { title: '我的活动' } 91 + meta: { title: '我的活动' },
92 }, 92 },
93 { 93 {
94 path: '/checkout', 94 path: '/checkout',
95 name: 'CheckoutPage', 95 name: 'CheckoutPage',
96 component: () => import('../views/checkout/CheckoutPage.vue'), 96 component: () => import('../views/checkout/CheckoutPage.vue'),
97 props: true, 97 props: true,
98 - meta: { title: '结账' } 98 + meta: { title: '结账' },
99 }, 99 },
100 { 100 {
101 path: '/profile/courses', 101 path: '/profile/courses',
102 name: 'MyCourses', 102 name: 'MyCourses',
103 component: () => import('../views/courses/MyCoursesPage.vue'), 103 component: () => import('../views/courses/MyCoursesPage.vue'),
104 - meta: { title: '我的课程' } 104 + meta: { title: '我的课程' },
105 }, 105 },
106 { 106 {
107 path: '/profile/orders', 107 path: '/profile/orders',
108 name: 'Orders', 108 name: 'Orders',
109 component: () => import('../views/profile/OrdersPage.vue'), 109 component: () => import('../views/profile/OrdersPage.vue'),
110 - meta: { title: '我的订单' } 110 + meta: { title: '我的订单' },
111 }, 111 },
112 { 112 {
113 path: '/profile/favorites', 113 path: '/profile/favorites',
114 name: 'MyFavorites', 114 name: 'MyFavorites',
115 component: () => import('../views/profile/MyFavoritesPage.vue'), 115 component: () => import('../views/profile/MyFavoritesPage.vue'),
116 - meta: { title: '我的收藏' } 116 + meta: { title: '我的收藏' },
117 }, 117 },
118 { 118 {
119 path: '/test', 119 path: '/test',
120 name: 'test', 120 name: 'test',
121 component: () => import('../views/test.vue'), 121 component: () => import('../views/test.vue'),
122 - meta: { title: 'test' } 122 + meta: { title: 'test' },
123 }, 123 },
124 - ...checkinRoutes 124 + ...checkinRoutes,
125 ] 125 ]
126 126
127 const router = createRouter({ 127 const router = createRouter({
...@@ -130,30 +130,49 @@ const router = createRouter({ ...@@ -130,30 +130,49 @@ const router = createRouter({
130 scrollBehavior(to, from, savedPosition) { 130 scrollBehavior(to, from, savedPosition) {
131 // 每次路由切换后,页面滚动到顶部 131 // 每次路由切换后,页面滚动到顶部
132 return savedPosition || { top: 0, left: 0 } 132 return savedPosition || { top: 0, left: 0 }
133 - } 133 + },
134 }) 134 })
135 135
136 // 需要登录才能访问的路由 136 // 需要登录才能访问的路由
137 const authRequiredRoutes = [ 137 const authRequiredRoutes = [
138 - '/profile', 138 + {
139 - '/profile/activities', 139 + path: '/profile',
140 - '/profile/courses', 140 + exact: false,
141 - '/profile/orders', 141 + },
142 - '/profile/favorites', 142 + {
143 - '/checkout' 143 + path: '/checkout',
144 + exact: true,
145 + },
146 + {
147 + path: '/activities/[^/]+/signup',
148 + regex: true,
149 + },
144 ] 150 ]
145 151
146 // 导航守卫 152 // 导航守卫
147 router.beforeEach((to, from, next) => { 153 router.beforeEach((to, from, next) => {
148 const currentUser = JSON.parse(localStorage.getItem('currentUser')) 154 const currentUser = JSON.parse(localStorage.getItem('currentUser'))
149 155
150 - // 检查是否需要认证 156 + // 检查当前路由是否需要认证
151 - if (authRequiredRoutes.some(route => to.path.startsWith(route))) { 157 + const needAuth = authRequiredRoutes.some((route) => {
152 - if (!currentUser) { 158 + // 如果是正则匹配模式
153 - // 未登录时重定向到登录页面 159 + if (route.regex) {
154 - next({ path: '/login', query: { redirect: to.fullPath } }) 160 + return new RegExp(`^${route.path}$`).test(to.path)
155 - return 161 + }
162 + // 如果是精确匹配模式
163 + if (route.exact) {
164 + return to.path === route.path
156 } 165 }
166 + // 默认前缀匹配模式
167 + // 判断路由路径是否以指定路径开头,用于匹配需要认证的路由及其子路由
168 + // 例如: /profile/courses 应该匹配 /profile 规则
169 + return to.path.startsWith(route.path)
170 + })
171 +
172 + if (needAuth && !currentUser) {
173 + // 未登录时重定向到登录页面
174 + next({ path: '/login', query: { redirect: to.fullPath } })
175 + return
157 } 176 }
158 177
159 next() 178 next()
......