欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

vue-element-admin路由动态设置

程序员文章站 2024-03-26 09:27:47
...

vue-element-admin默认是按照路由meta.role角色,动态匹配的。但通常是不灵活的。总不能每次设置一个角色,前端还要动态配置。
相对理想的状态,是后台配置一个用户,设置role权限,权限绑定了你需要的路由模块。

本文讲述如何根据后台路由,动态渲染后台管理系统菜单栏。

下载模板

链接

修改配置

只需要把原先根据role匹配路由的方式,换成接口获取路由就行
store/modules/perimission.js.

import { constantRoutes } from '@/router'
// import { getRouters } from '@/api/menu'
import Layout from '@/layout'

const permission = {
  namespaced: true,
  state: {
    routes: [],
    addRoutes: []
  },
  mutations: {
    SET_ROUTES: (state, routes) => {
      state.addRoutes = routes
      state.routes = constantRoutes.concat(routes)
    }
  },
  actions: {
    // 生成路由
    generateRoutes({ commit }) {
      return new Promise(resolve => {
        // 向后端请求路由数据 模拟数据在router.js中选择一份路由复制出来,测试
        const accessRoutes = [  
          {
            path: '/icon',
            component: 'Layout',
            children: [
              {
                path: 'index',
                component: 'icons/index',
                name: 'Icons',
                meta: { title: 'Icons', icon: 'icon', noCache: true }
              }
            ]
          }
        ]

        const accessedRoutes = filterAsyncRouter(accessRoutes)

        commit('SET_ROUTES', accessedRoutes) // 左侧页面展示
        resolve(accessedRoutes)  // 此处返回值 router.addRouter()
      })
    }
  }
}

// 遍历后台传来的路由字符串,转换为组件对象
function filterAsyncRouter(asyncRouterMap) {
  return asyncRouterMap.filter(route => {
    if (route.component) {
      // Layout组件特殊处理
      if (route.component === 'Layout') {
        route.component = Layout
      } else {
        route.component = loadView(route.component)
      }
    }
    if (route.children != null && route.children && route.children.length) {
      route.children = filterAsyncRouter(route.children)
    }
    return true
  })
}

// export const loadView = view => {
//
//   return () => import(`@/views/${view}`);
// };

export const loadView = view => {
  // 路由懒加载
  return resolve => require(['@/views/' + view], resolve)
}

export default permission

vue-element-admin路由动态设置

vue-element-admin路由动态设置

router/index.js 可以不改

asyncRoutes() 按照个人需求,要不要  一般情况下一个基本配置路由,还有一个就是动态路由了

const createRouter = () => new Router({
  // mode: 'history', // require service support
  scrollBehavior: () => ({ y: 0 }),
  routes: constantRoutes
})

const router = createRouter()

// Detail see: https://github.com/vuejs/vue-router/issues/1234#issuecomment-357941465
export function resetRouter() { // 防止路由重复
  const newRouter = createRouter()
  router.matcher = newRouter.matcher // reset router
}

export default router

现在运行,看看测试的路由能不能打开,不出意外,完工。

到此前端工作,ok了。如果你想看看后端是如何生成的,可以接着看,已node+mysql为例

路由数据以此为例

        const accessRoutes = [
          {
            path: '/icon',
            component: 'Layout',
            children: [
              {
                path: 'index',
                component: 'icons/index',
                name: 'Icons',
                meta: { title: 'Icons', icon: 'icon', noCache: true }
              }
            ]
          },
          {
            path: '/nested',
            component: 'Layout',
            redirect: '/nested/menu1/menu1-1',
            name: 'Nested',
            meta: {
              title: 'Nested Routes',
              icon: 'nested'
            },
            children: [
              {
                path: 'menu1',
                component: 'nested/menu1/index', // Parent router-view
                name: 'Menu1',
                meta: { title: 'Menu 1' },
                redirect: '/nested/menu1/menu1-1',
                children: [
                  {
                    path: 'menu1-1',
                    component: 'nested/menu1/menu1-1',
                    name: 'Menu1-1',
                    meta: { title: 'Menu 1-1' }
                  },
                  {
                    path: 'menu1-2',
                    component: 'nested/menu1/menu1-2',
                    name: 'Menu1-2',
                    redirect: '/nested/menu1/menu1-2/menu1-2-1',
                    meta: { title: 'Menu 1-2' },
                    children: [
                      {
                        path: 'menu1-2-1',
                        component: 'nested/menu1/menu1-2/menu1-2-1',
                        name: 'Menu1-2-1',
                        meta: { title: 'Menu 1-2-1' }
                      },
                      {
                        path: 'menu1-2-2',
                        component: 'nested/menu1/menu1-2/menu1-2-2',
                        name: 'Menu1-2-2',
                        meta: { title: 'Menu 1-2-2' }
                      }
                    ]
                  },
                  {
                    path: 'menu1-3',
                    component: 'nested/menu1/menu1-3',
                    name: 'Menu1-3',
                    meta: { title: 'Menu 1-3' }
                  }
                ]
              },
              {
                path: 'menu2',
                name: 'Menu2',
                component: 'nested/menu2/index',
                meta: { title: 'Menu 2' }
              }
            ]
          }
        ]

现在为止前端的工作就完成了,感兴趣的可以接着看后端配置(菜鸡一个,如果有好的建议,欢迎交流)

表(具体字段可以根据实际业务)

'use strict';

module.exports = app => {
  const { STRING, INTEGER, BOOLEAN } = app.Sequelize;

  const AdminRouter = app.model.define(
    'adminRouter',
    {
      id: { type: INTEGER, primaryKey: true, autoIncrement: true },
      pid: { type: INTEGER, allowNull: true, defaultValue: null},
      name: { type: STRING},
      path: { type:STRING, content: '路由地址'},
      component: { type: STRING, content: '路由页面路径'},
      title: { type: STRING(30), allowNull: true},
      order: { type: INTEGER, defaultValue: 0 },
      icon: { type: STRING},
      hidden: { type: BOOLEAN, content: '是否显示路由'}
    },
    {
      tableName: 'adminRouter',
      
    }
  );
  return AdminRouter;
};


录入资料(手动)
vue-element-admin路由动态设置
查找数据后树形返回数据就行

注意事项,比如title和icon是放在meta字段里的,我现在是分下的

vue-element-admin路由动态设置
我这边是前端再做个转化

vue-element-admin路由动态设置
vue-element-admin路由动态设置

vue-element-admin路由动态设置
收工