Bootstrap

vite+vue3实现动态路由

在做这个动态路由的时候踩了很多坑,其中大部分是粗心了

动态菜单主要是导入的方式 import.meta.glob

参考:功能 | Vite 官方中文文档

1、多层路由渲染(用3层路由做demo)

拿到接口的数据是后台直接处理好的结构,但是在addRoute的时候发现其他层没有添加上,这个地方就处理成一级目录先把动态路由添加上再说

const whiteList = ['/login']// 免登录白名单
const modules = import.meta.glob('../views/**/*.vue')

router.beforeEach((to, from, next) => {
	document.title = `${to.meta.title}`
  const token=Cookies.get('token')
  if(token){
    if (to.path === '/login') {
      next()
    }else{

      if(store.state.menulist.length==0){
        $api.getUserData().then(res =>{
          if(res){
            if(res.code==0){
              let menulist=[];
              let newChildren=[];
             for(let i=0;i<res.data.menuWithCurrentRoleList.length;i++){
                let item=res.data.menuWithCurrentRoleList[i];
                let children=[];
                
                if(item.subMenuList){
                  for(let j=0;j<item.subMenuList.length;j++){
                    let items=item.subMenuList[j]
                    items.path=items.router;
                    let asarr=[];
                    if(items.subMenuList){
                      for(let jj=0;jj<items.subMenuList.length;jj++){
                        let as=items.subMenuList[jj]
                        
                        let aobjs={
                          "path":as.href, 
                          "name":as.moduleName, 
                          children:[],
                          subMenuList:as.subMenuList,
                          parent:3,
                          "meta":{
                            "title":as.name,
                          },
                          // component: () => import(`../views${as.href}.vue`),/**这个静态路由只能本地使用**/
                          component: modules[`../views${as.href}.vue`],
                        }
                       
                        asarr.push(aobjs)
                        newChildren.push(aobjs)
                      }
                    }
                    let aobj={
                      "path":items.href, 
                      "name":items.moduleName, 
                      children:[],
                      parent:2,
                      subMenuList:asarr,
                      "meta":{
                        "title":items.name,
                      },
                      //  component: () => import(`../views${items.href}.vue`),
                      component: modules[/* @vite-ignore */`../views${items.href}.vue`],
                    }

                    children.push(aobj)
                    newChildren.push(aobj)
                  }
                }
                let obj={
                    "path":item.href, 
                    "name":item.moduleName, 
                    children:[],
                    parent:1,
                    subMenuList:children,
                    "meta":{
                      "title":item.name,
                    },
                    // component: () => import(`../views${item.href}.vue`),
                    component: modules[`../views${item.href}.vue`],
                  }
                  // console.log(obj.component,'====111===',item.href)
                
                menulist.push(obj)
                newChildren.push(obj)
              }

              store.dispatch('setMenulist',newChildren).then(() => {
                newChildren.forEach((route) => {
                  router.addRoute('home',{ ...route });
                });
                next({ ...to, replace: true });
              }); 
            }
          }
        })
      }else{
        next()
      }
      
    }
  }else{
    if (whiteList.indexOf(to.path) !== -1) { // 在免登录白名单,直接进入
      next()
    } else {
      next(`/login?redirect=${to.fullPath}`) // 否则全部重定向到登录页
    }
  }
})

说明:

import.meta.glob('../views/**/*.vue')

一个*表示文件,两个**表示文件夹,.vue是说这个下面的所有.vue文件

我当时遇到的问题有点奇怪,有的路由菜单可以点击,有的不可以,我当时粗心有2点。

1、文件名大小写被我忽略了,没有注意到,所以,一定要注意文件名有没有错

2、使用modules的时候我第三层的前面加了()=>然后在打印component的时候, 打印出来的是变量名

第一个框起来的是路径错误,我没有这个文件

第二个框起来的是正确的,路径正确也可以正常访问

第三个错误的,因为我加了component:()=>modules,实际不需要加,我当时没有注意到这个地方,找了好久的问题 

最后:如果有好的多层动态菜单处理方法,大家可以告诉我呀。

;