合肥网站优化平台,济南阿里科技网站建设有限公司,商城建站系统,自助建站原理路由
路由的三种模式
1、hash#xff08;哈希#xff09;模式#xff1a;createWebHashHistory()
使用 URL 的 hash#xff08;##xff09;部分来模拟一个完整的 URL#xff0c;当 hash 改变时#xff0c;页面不会重新加载
兼容性好#xff0c;支持旧版浏览器#xf…路由路由的三种模式1、hash哈希模式createWebHashHistory()使用 URL 的 hash#部分来模拟一个完整的 URL当 hash 改变时页面不会重新加载兼容性好支持旧版浏览器不需要服务器端配置URL 中带有 #可能影响美观2、HistoryHTML5模式createWebHistory()利用 HTML5 History APIpushState、replaceState、popstate 事件改变 URL不重新加载页面没有 #URL 更美观3、Memory 模式createMemoryHistory()不依赖浏览器历史记录因此可以在没有 URL 的环境中使用主要用于node环境和SSR渲染如移动端原生应用、测试环境等// 模式路由import{createRouter,createWebHashHistory}fromvue-routerconstroutercreateRouter({history:createWebHashHistory(),// hash// history: createWebHistory(), // history// history: createMemoryHistory(), // memoryroutes:[...]})路由别名在Vue Router中路由别名允许您为路由定义另一个名称使得用户可以通过不同的URL访问同一个组件。constroutes[// 用户访问/时实际上也会渲染Home组件{path:/home,component:Home,alias:/}]// 多别名 用户可以通过/users、/people或/members访问同一个组件constroutes[{path:/users,component:Users,alias:[/people,/members]}]// 带参数的别名constroutes[{path:/user/:id,component:User,alias:/u/:id}]命名视图在路由配置中一个路由可以对应多个组件每个组件用一个命名视图来展示。这对于需要同时展示多个视图的布局非常有用例如侧边栏、主内容区、底部栏等。constroutes[{path:/,components:{default:Home,// 默认视图对应没有名字的 router-viewsidebar:Sidebar,// 对应 router-view namesidebarfooter:Footer// 对应 router-view namefooter}}]templatedivrouter-view namesidebar/router-viewrouter-view/router-view!--默认视图name 为default--router-view namefooter/router-view/div/template路由重定向路由重定向是指当用户访问某个路由时自动跳转到另一个路由并且URL地址会发生变化重定向后浏览器的地址栏会显示新的URL重定向本身不会渲染组件只是跳转// 基本用法constroutes[{path:/home,redirect:/dashboard// 访问/home时重定向到/dashboard// redirect: { name: dashboard } // 重定向到名为dashboard的路由}]// 动态返回重定向目标constroutes[{path:/user/:id,redirect:to{return{path:/profile/:id,params:{from:user}}}}]// 条件重定向constroutes[{path:/admin,redirect:to{if(userRolesuperadmin){return/superadmin/dashboard}elseif(userRoleadmin){return/admin/dashboard}else{return/access-denied}}}]路由附加元信息路由元信息是Vue Router中一个非常有用的功能它允许我们在路由配置中添加自定义数据这些数据可以在导航守卫、组件中访问用于实现权限控制、面包屑、页面标题等功能constroutes[{path:/profile,component:Profile,meta:{requiresAuth:true,// 需要登录title:用户资料,// 页面标题permissions:[view_profile]// 所需权限}}]// 组件访问元信息templatedivh1{{pageTitle}}/h1/div/templatescript setupimport{useRoute}fromvue-routerconstrouteuseRoute()constpageTitleroute.meta.title/script路由懒加载路由懒加载是Vue Router中一个非常重要的性能优化手段它可以减少应用初始加载时的资源大小打包时会进行分包处理按需加载路由对应的组件从而提高应用的首屏加载速度// 静态导入所有组件打包到同一个文件importHomefrom/views/Home.vueimportAboutfrom/views/About.vueimportContactfrom/views/Contact.vueconstroutes[{path:/,component:Home},{path:/about,component:About},{path:/contact,component:Contact}]// 动态导入懒加载constroutes[{path:/,component:()import(/views/Home.vue)// 懒加载},{path:/about,component:()import(/views/About.vue)// 懒加载},{path:/contact,component:()import(/views/Contact.vue)// 懒加载}]路由匹配语法路由匹配语法主要是指定义路由路径path时的规则包括动态路由、捕获所有路由、正则表达式等。// 静态路径constroutes[{path:/,component:Home},{path:/about,component:About},{path:/contact,component:Contact}]// 动态路由参数constroutes[{path:/user/:id,component:User},// 匹配 /user/123, /user/abc{path:/product/:id,component:Product}]// 多段动态参数constroutes[{path:/user/:username/post/:postId,component:Post}]// 路由参数可选匹配constroutes[{path:/user/:id?,component:User}// 匹配 /user 和 /user/123]// 自定义正则 匹配一个或多个constroutes[{path:/:chapters,component:Chapters}// 匹配 /one, /one/two, 至少一个]// 自定义正则表达式匹配constroutes[// 只匹配数字{path:/user/:id(\\d),component:User},// 匹配多个数字{path:/user/:ids(\\d),component:Users}]// 捕获所有路由404页面// 使用 :pathMatch(.*)* 或 :catchAll(.*) 来捕获所有路由constroutes[// 注意捕获所有路由必须放在最后{path:/:pathMatch(.*)*,name:NotFound,component:NotFound}]// 路由优先级// 路由的优先级由定义的顺序决定先定义的路由优先级更高。当多个路由匹配同一路径时先定义的路由会被匹配constroutes[{path:/user/:id,component:User},// 优先匹配{path:/user/me,component:Me}// 永远不会被匹配因为上面的路由先匹配了]RouterLink内置组件RouterLink是用于在应用中进行导航的组件它默认会被渲染成一个a标签并且能够根据目标路由的状态自动设置激活时的CSS类名1、当RouterLink对应的路由匹配成功时会自动应用两个class类名router-link-active和router-link-exact-active。2、类名router-link-active当目标路由模糊匹配成功时这个类名会被添加。3、类名router-link-exact-active只有当目标路由精准匹配成功时包括查询参数和哈希这个类名会被添加。4、你可以通过active-class和exact-active-class属性来自定义激活时的类名。templatediv!--字符串路径--router-link to/homeHome/router-link!--使用对象路径--router-link:to{ path: /home }Home/router-link!--使用命名路由--router-link:to{ name: user, params: { userId: 123 }}User/router-link!--带查询参数--router-link:to{ path: /register, query: { plan: private }}Register/router-link/div/templaterouter-link to/homeactive-classactive-linkexact-active-classexact-active-linkHome/router-link路由传参1、路径参数params传参方式// 1. 字符串路径传参// { path: /user/:id, component: xxx } // 路由定义router.push(/user/123)// 基本使用// 2. 对象形式传参推荐router.push({name:UserDetail,// 使用命名路由params:{id:123}// params 传参})// 3. 对象形式带可选参数router.push({path:/settings/security})// 可选参数可不传接参方式script setupimport{useRoute}fromvue-routerconstrouteuseRoute()constuserIdroute.params.id// 直接访问 params.id/script2、query参数query传参方式// 1. 对象形式传参推荐router.push({path:/search,query:{// query 传参q:vue 3,page:1,sort:date}})// 2. 字符串路径传参router.push(/search?qvue3page2)// 3. 数组参数传参router.push({path:/products,query:{tags:[vue,react,angular],// 数组会自动序列化colors:[red,blue]}})接参方式script setupimport{useRoute}fromvue-router// 接参方式 1组合式 API推荐constrouteuseRoute()constsearchQueryroute.query.q// 访问 query.qconstcurrentPageroute.query.page||1// 带默认值/script3、状态参数state传参方式router.push({name:ProductDetail,state:{// state 传参productData:{// 可传复杂对象id:123,name:Vue 3 教程,price:99.99},fromPage:home}})接参方式script setupimport{useRoute}fromvue-routerconstrouteuseRoute()constproductDataroute.state?.productData// 访问 stateconstfromPageroute.state?.fromPage/script导航守卫1、全局守卫beforeEach全局前置守卫在路由跳转前触发beforeResolve全局解析守卫在导航被确认之前在组件内守卫和异步路由组件被解析之后调用afterEach全局后置钩子在路由跳转完成后触发不会接受 next 函数import{createRouter,createWebHistory}fromvue-routerconstroutercreateRouter({history:createWebHistory(),routes:[// ... 路由配置]})// 全局前置守卫router.beforeEach((to,from,next){// 可以在这里进行权限检查constisAuthenticatedcheckAuth()if(to.meta.requiresAuth!isAuthenticated){// 如果路由需要认证且用户未登录重定向到登录页next(/login)}else{next()// 继续导航}})// 全局解析守卫router.beforeResolve(async(to,from){// 可以在这里进行数据预取等操作if(to.meta.requiresFetch){awaitfetchData()}})// 全局后置钩子router.afterEach((to,from){// 可以用于页面标题设置、埋点等document.titleto.meta.title||默认标题})2、路由独享守卫beforeEnter在进入特定路由前触发constroutes[{path:/dashboard,component:Dashboard,beforeEnter:(to,from,next){// 只有管理员可以访问if(user.role!admin){next(/403)// 重定向到403页面}else{next()}}}]3、组件内守卫beforeRouteEnter在进入组件前调用此时组件实例还未创建beforeRouteUpdate在当前路由改变但是该组件被复用时调用例如动态参数变化beforeRouteLeave在离开组件时调用templatediv!--组件内容--/div/templatescript setup// 从 vue-router 导入组件内守卫函数import{onBeforeRouteLeave,// 离开守卫onBeforeRouteUpdate,// 更新守卫// 注意beforeRouteEnter 在 setup 中没有对应的函数 需要使用其它替代方案去处理}fromvue-routerimport{useRoute,useRouter}fromvue-routerimport{ref,watch}fromvueconstrouteuseRoute()constrouteruseRouter()/script动态路由动态路由是在运行时动态添加、修改或删除的路由规则常用于权限控制、模块懒加载等场景特点1、运行时配置在应用运行时动态配置路由2、权限控制根据用户权限动态生成路由表3、模块化按需加载路由模块4、灵活性适应复杂的业务需求// api 增删查constAPIs{增:router.addRoute() // 添加路由,删:router.removeRoute() // 删除路由,查:router.hasRoute() // 检查路由}// 使用示例// 1. 增加路由router.addRoute({path:/dashboard,name:Dashboard,component:()import(/views/Dashboard.vue)})// 2. 删除路由router.removeRoute(Dashboard)// 3. 检查路由if(router.hasRoute(Dashboard)){console.log(路由存在)}// 4. 获取所有路由constallRoutesrouter.getRoutes()// 5. 添加嵌套路由router.addRoute(ParentRoute,{path:child,component:ChildComponent})动态路由基本实现1、分离静态路由和动态路由// 无需权限的公共路由conststaticRoutes[{path:/,component:Home},{path:/login,component:Login},{path:/404,component:NotFound}]// 需要权限的动态路由constdynamicRoutes[{path:/dashboard,component:Dashboard,meta:{requiresAuth:true}},{path:/admin,component:Admin,meta:{requiresAuth:true,roles:[admin]}}]2、权限验证// 权限验证函数functioncheckPermission(route,userRoles){// 1. 无需权限if(!route.meta?.requiresAuth)returntrue// 2. 需要特定角色if(route.meta.roles){returnroute.meta.roles.some(roleuserRoles.includes(role))}// 3. 只需要登录returntrue}// 过滤动态路由functionfilterRoutesByPermission(routes,userRoles){returnroutes.filter(routecheckPermission(route,userRoles))}3、动态添加asyncfunctionsetupDynamicRoutes(userRoles){// 1. 过滤有权限的路由constallowedRoutesfilterRoutesByPermission(dynamicRoutes,userRoles)// 2. 标记动态路由constmarkedRoutesallowedRoutes.map(route({...route,meta:{...route.meta,isDynamic:true}}))// 3. 批量添加markedRoutes.forEach(route{if(!router.hasRoute(route.name)){router.addRoute(route)}})// 4. 确保404在最后addNotFoundRoute()}