使用vue-element-admin框架从后端动态获取菜单功能的实现


Posted in Vue.js onApril 29, 2021

2、详解

​整体思路为:登陆 > 成功后根据用户信息获取菜单 > 根据菜单生成路由信息

2.1、新增asyncRoutes路由

​在vue-router路径src\router\index.js中新增asyncRoutes数组,用来存放后端获取的菜单对应的路由信息。

export const asyncRoutes = [
  { path: '*', redirect: '/404', hidden: true }
]

使用vue-element-admin框架从后端动态获取菜单功能的实现

constantRoutes和asyncRoutes的区别

constantRoutes:不需要动态判断权限的路由,如登录页、404等通用页面。

asyncRoutes:需求动态判断权限并通过addRoutes动态添加的页面

2.2、新建permission.js文件

​在vuex路径src\store\modules\permission.js下新建permission.js文件,该操作为最重要的一步,主要是从后端查询菜单并生成路由。

import { asyncRoutes, constantRoutes } from '@/router'
import { fetchUserMenuList } from '@/api/user'
import Layout from '@/layout'

/**
 * 静态路由懒加载
 * @param view  格式必须为 xxx/xxx 开头不要加斜杠
 * @returns 
 */
export const loadView = (view) => {
  return (resolve) => require([`@/views/${view}.vue`], resolve)
}

/**
 * 把从后端查询的菜单数据拼装成路由格式的数据
 * @param routes
 * @param data 后端返回的菜单数据
 */
export function generaMenu(routes, data) {
  data.forEach(item => {
    const menu = {
      path: item.url, 
      component: item.component === '#' ? Layout : loadView(item.component), 
      hidden: item.status === 0, // 状态为0的隐藏
      redirect: item.redirect,
      children: [],
      name: item.code,
      meta: item.meta
    }

    if (item.children) {
      generaMenu(menu.children, item.children)
    }
    routes.push(menu)
  })
  return routes
}

const state = {
  routes: [],
  addRoutes: []
}

const mutations = {
  SET_ROUTES: (state, routes) => {
    state.addRoutes = routes
    // 拼接静态路由和动态路由
    state.routes = constantRoutes.concat(routes)
  }
}

const actions = {
  generateRoutes({ commit }, token) {
    return new Promise(resolve => {
      // 通过token从后端获取用户菜单,并加入全局状态
      fetchUserMenuList(token).then(res => {
        const menuData = Object.assign([], res.data)
        const tempAsyncRoutes = Object.assign([], asyncRoutes)
        const accessedRoutes = generaMenu(tempAsyncRoutes, menuData)

        commit('SET_ROUTES', accessedRoutes)
        resolve(accessedRoutes)
      }).catch(error => {
        console.log(error)
      })
    })
  }
}

export default {
  namespaced: true,
  state,
  mutations,
  actions
}

2.3、在vuex中注册permission模块

​如果使用的是vue-element-admin请跳过此步,因为它在src\store\index.js中自动注册了src\store\modules下的所有模块。如果你使用的是vue-element-template,可以参考admin,将index.js文件改造一下,也可以手动import一下。

import Vue from 'vue'
import Vuex from 'vuex'
import getters from './getters'

Vue.use(Vuex)

// https://webpack.js.org/guides/dependency-management/#requirecontext
const modulesFiles = require.context('./modules', true, /\.js$/)

// you do not need `import app from './modules/app'`
// it will auto require all vuex module from modules file
const modules = modulesFiles.keys().reduce((modules, modulePath) => {
  // set './app.js' => 'app'
  const moduleName = modulePath.replace(/^\.\/(.*)\.\w+$/, '$1')
  const value = modulesFiles(modulePath)
  modules[moduleName] = value.default
  return modules
}, {})

const store = new Vuex.Store({
  modules,
  getters
})

export default store

2.4、在getters中增加路由状态

​在vuex路径src\store\getters.js添加menusRoutes状态

menusRoutes: state => state.permission.routes

使用vue-element-admin框架从后端动态获取菜单功能的实现

2.5、修改菜单生成数据来源

​在路径src\layout\components\Sidebar\index.vue修改routes数据来源,原来数据源是路由,改为从vuex中获取。

routes() {
      // return this.$router.options.routes
      return this.$store.getters.menusRoutes
    },

使用vue-element-admin框架从后端动态获取菜单功能的实现

​至此,从后端获取菜单数据到页面展示的逻辑已经完毕,下面开始在登陆后进行调用。

2.6、登陆后获取菜单

​在vuex路径src\store\modules\user.js的login方法中,加入登陆成功通过token获取菜单生成路由逻辑。

// 获取菜单,调用其他文件中actions时必须加 { root: true }
          dispatch('permission/generateRoutes', data, { root: true }).then((accessRoutes) => {
            router.addRoutes(accessRoutes)
          })

使用vue-element-admin框架从后端动态获取菜单功能的实现

2.7、解决刷新后页面空白

​以上内容已经可以实现登陆后展示左侧菜单功能,但是会发现每次刷新页面后,页面都会变空白。这是因为在页面刷新时,会重新加载vue实例,vuex的store中的数据会被重新赋值,导致我们存在vuex中的路由信息被清空。

​在src\permission.js中增加重新获取路由代码。

const accessRoutes = await store.dispatch('permission/generateRoutes', store.getters.token)
          router.addRoutes(accessRoutes)
          next({ ...to, replace: true })

使用vue-element-admin框架从后端动态获取菜单功能的实现

3、总结

​至此根据用户信息动态获取菜单内容已经全部完成。

到此这篇关于使用vue-element-admin框架从后端动态获取菜单的文章就介绍到这了,更多相关vue-element-admin动态获取菜单内容请搜索三水点靠木以前的文章或继续浏览下面的相关文章希望大家以后多多支持三水点靠木!

Vue.js 相关文章推荐
Vue组件生命周期运行原理解析
Nov 25 Vue.js
在vue中动态修改css其中一个属性值操作
Dec 07 Vue.js
vue 基于abstract 路由模式 实现页面内嵌的示例代码
Dec 14 Vue.js
vue实现图片裁剪后上传
Dec 16 Vue.js
Vue——解决报错 Computed property "****" was assigned to but it has no setter.
Dec 19 Vue.js
vue使用vue-quill-editor富文本编辑器且将图片上传到服务器的功能
Jan 13 Vue.js
vue element和nuxt的使用技巧分享
Jan 14 Vue.js
vscode自定义vue模板的实现
Jan 27 Vue.js
原生JS封装vue Tab切换效果
Apr 28 Vue.js
vue+spring boot实现校验码功能
May 27 Vue.js
Vue中foreach数组与js中遍历数组的写法说明
Jun 05 Vue.js
vue本地构建热更新卡顿的问题“75 advanced module optimization”完美解决方案
Aug 05 Vue.js
vue使用v-model进行跨组件绑定的基本实现方法
关于vue中如何监听数组变化
vue实现简单数据双向绑定
Apr 28 #Vue.js
vue引入Excel表格插件的方法
Apr 28 #Vue.js
原生JS封装vue Tab切换效果
vue项目两种方式实现竖向表格的思路分析
vue首次渲染全过程
You might like
php中simplexml_load_file函数用法实例
2014/11/12 PHP
PHP 微信支付类 demo
2015/11/30 PHP
PHP中Enum(枚举)用法实例详解
2015/12/07 PHP
PHP session垃圾回收机制实例分析
2019/06/28 PHP
JavaScript使用prototype定义对象类型
2007/02/07 Javascript
Javascript 面向对象(三)接口代码
2012/05/23 Javascript
js 程序执行与顺序实现详解
2013/05/13 Javascript
js禁止页面刷新禁止用F5键刷新禁止右键的示例代码
2013/09/23 Javascript
多个checkbox被选中时如何判断是否有自己想要的
2014/09/22 Javascript
jQuery实现的图片分组切换焦点图插件
2015/01/06 Javascript
jQuery中常用的遍历函数用法实例总结
2015/09/01 Javascript
js实现卡片式项目管理界面UI设计效果
2015/12/08 Javascript
详解Bootstrap的aria-label和aria-labelledby应用
2016/01/04 Javascript
jquery实现右侧栏菜单选择操作
2016/03/04 Javascript
微信开发 js实现tabs选项卡效果
2016/10/28 Javascript
js实现文字跑马灯效果
2017/02/23 Javascript
bootstrap常用组件之头部导航实现代码
2017/04/20 Javascript
JS实现的汉字与Unicode码相互转化功能分析
2018/05/25 Javascript
微信小程序实现天气预报功能
2018/07/18 Javascript
webpack的CSS加载器的使用
2018/09/11 Javascript
[03:44]2014DOTA2国际邀请赛 71专访:DK战队赛前讨论视频遭泄露
2014/07/13 DOTA
详细解读Python中解析XML数据的方法
2015/10/15 Python
PyQt5每天必学之进度条效果
2018/04/19 Python
Python 使用xlwt模块将多行多列数据循环写入excel文档的操作
2020/11/10 Python
KIKO MILANO西班牙官网:意大利领先的化妆品和护肤品品牌
2019/05/03 全球购物
德国最新街头服饰网上商店:BODYCHECK
2019/09/15 全球购物
北京泡泡网网络有限公司.net面试题
2012/07/17 面试题
社区志愿者心得体会
2014/01/03 职场文书
项目经理聘任书
2014/03/29 职场文书
给老婆的保证书
2015/01/16 职场文书
英文感谢信格式
2015/01/21 职场文书
就业意向协议书
2015/01/29 职场文书
单位病假条范文
2015/08/17 职场文书
读《瓦尔登湖》有感:每个人都需要一个瓦尔登湖
2019/10/17 职场文书
CSS几步实现赛博朋克2077风格视觉效果
2021/06/16 HTML / CSS
详解Go语言Slice作为函数参数的使用
2021/07/02 Golang