详解基于vue-router的动态权限控制实现方案


Posted in Javascript onSeptember 28, 2017

使用vue开发带权限管理系统,尤其是采用了vue-router做路由,很多人都遇到的一个问题就是如何动态加载路由path对应的component。

典型的应用场景就是:前端菜单不静态的写在vue程序里,而是要从后台程序和数据库返回的菜单来动态加载到vue应用中。

网上很多问权限的问题,但几乎找不到很好的解决答案,在很长一段时间里,非常打击使用vue技术栈开发的信心。最有质量的一篇文章是:https://3water.com/article/124801.htm

但作者并没有完全解决这个问题,还留有几个问题是:

1)登录之后跳转到首页,此时路由已经是加载完成的了不能更改,菜单可以显示但是没有路由。

2)前端应用人为刷新网页路由产生某些问题。

本文即在这篇文章的基础上对这两个问题解决,以使其完整。

前提是认真拜读上面提到的那篇文章,下面直接用代码说话:

问题1的解决思路:

登录之后跳转到首页,router是vue应用的router 引入进登录方法,在登录之后跳转之前对router进行改变,改变要点1是精确赋值到router的routes具体地方,比如我这里是routes[0]的子路由,2是用addRoutes函数使其生效。

登录功能的js

export const login = ({commit}, data) => { Service.post('/login', Qs.stringify(data))
  .then(res => {
   const success = Object.is(res.statusText, 'OK') && Object.is(res.data.code, '0')
   if (success) {
    var menus = generateMenus(res.data.menus)
    window.sessionStorage.routes = JSON.stringify(menus)
    if (menuModule.state.items.length <= 0) { // 避免注销后在不刷新页面的情况下再登录重复加载路由
     commit(types.ADD_MENU, menus)
     // 动态加载路由关键2行
     router.options.routes[0].children.push(...generateRoutesFromMenu(menuModule.state.items))
     router.addRoutes(router.options.routes)
    }
    window.sessionStorage.loginName = data.loginName
    router.push({path: '/'})
   } else {
    commit('loginErr', res.data.msg)
   }
  })
}


function generateRoutesFromMenu (menu = [], routes = []) {
 for (let i = 0, l = menu.length; i < l; i++) {
  let item = menu[i]
  if (item.path) {
   routes.push(item)
  }
  if (!item.component) {
   item.component = resolve => require([`views/` + item.component + `.vue`], resolve)
   generateRoutesFromMenu(item.children, routes)
  }
 }
 return routes
}

问题2的解决思路:

是不在主app里引入实例化vue-router的js,而是直接在app里实例化router,目的就是网页刷新的时候每次都确保生成动态的router。

app.js部分代码:

Vue.use(Router)
let menus = window.sessionStorage.routes //登录成功返回的菜单
if (menus) {
 let items = JSON.parse(menus)
 store.commit(ADD_MENU, items)
}

const router = new Router({
 mode: 'hash',
 linkActiveClass: 'is-active',
 scrollBehavior: () => ({ y: 0 }),
 routes: [
  {
   name: 'Main',
   path: '/',
   component: require('views/Main.vue'),
   children: [ //动态路由之所以作为Main的子路由是基于:登录之后跳转到Main主页,该主页是类似于frame的页面加载框架,只有将动态路由作为Main的子路由才能确保其他页面显示到Main框架内。
    ...generateRoutesFromMenu(menuModule.state.items)
   ]
  },
  {
   name: 'Login',
   path: '/login',
   component: require('views/Login.vue')
  }
 ]
})

function generateRoutesFromMenu (menu = [], routes = []) {
 for (let i = 0, l = menu.length; i < l; i++) {
  let item = menu[i]
  if (item.path) {
   routes.push(item)
  }
  if (!item.component) {
   item.component = resolve => require([`views/` + item.component + `.vue`], resolve)
   generateRoutesFromMenu(item.children, routes)
  }
 }
 return routes
}

另附menu items代码

const state = {
 items: [ // 什么菜单都不定义,完全由后端返回
 ]
}
const mutations = {
 [types.ADD_MENU] (state, menuItems) {
  if (menuItems.length > 0) {
   menuItems.map(function (item) {
    item.children.map(function (child) {
     child.component = lazyLoading(child.component)
    })
   })
   state.items.push(...menuItems)
  }
 },

lazyloding

export default (name, index = false) => () => import(`views/${name}${index ? '/index' : ''}.vue`)

git代码暂不能全部公开,有问题可留言。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
javascript form 验证函数 弹出对话框形式
Jun 23 Javascript
JQuery扩展插件Validate 1 基本使用方法并打包下载
Sep 05 Javascript
javascript动画对象支持加速、减速、缓入、缓出的实现代码
Sep 30 Javascript
jQuery瀑布流插件Wookmark使用实例
Apr 02 Javascript
一个不错的字符串转码解码函数(自写)
Jul 31 Javascript
JavaScript Math.ceil 方法(对数值向上取整)
Jan 09 Javascript
JS实现很酷的EMAIL地址添加功能实例
Feb 28 Javascript
jquery实现叠层3D文字特效代码分享
Aug 21 Javascript
jQuery UI Grid 模态框中的表格实例代码
Apr 01 jQuery
Vuejs实现带样式的单文件组件新方法
May 02 Javascript
vue使用svg文件补充-svg放大缩小操作(使用d3.js)
Sep 22 Javascript
js轮播图之旋转木马效果
Oct 13 Javascript
node.js学习之断言assert的使用示例
Sep 28 #Javascript
vue-router+vuex addRoutes实现路由动态加载及菜单动态加载
Sep 28 #Javascript
node.js学习之事件模块Events的使用示例
Sep 28 #Javascript
es6中的解构赋值、扩展运算符和rest参数使用详解
Sep 28 #Javascript
JS获取日期的方法实例【昨天,今天,明天,前n天,后n天的日期】
Sep 28 #Javascript
jquery实现左右轮播图效果
Sep 28 #jQuery
bootstrap table实现点击翻页功能 可记录上下页选中的行
Sep 28 #Javascript
You might like
php面向对象全攻略 (十六) 对象的串行化
2009/09/30 PHP
PHP网页游戏学习之Xnova(ogame)源码解读(十三)
2014/06/26 PHP
通过Email发送PHP错误的方法
2015/07/20 PHP
Thinkphp框架开发移动端接口(1)
2016/08/18 PHP
php中实现进程锁与多进程的方法
2016/09/18 PHP
thinkphp多表查询两表有重复相同字段的完美解决方法
2016/09/22 PHP
windows环境下使用Composer安装ThinkPHP5
2018/05/18 PHP
两个Javascript小tip资料
2010/11/23 Javascript
jQuery表单获取和失去焦点输入框提示效果的实例代码
2013/08/01 Javascript
javascript中createElement的两种创建方式
2015/05/14 Javascript
贴近用户体验的Jquery日期、时间选择插件
2015/08/19 Javascript
js实现跨域的4种实用方法原理分析
2015/10/29 Javascript
JS模仿腾讯图片站的图片翻页按钮效果完整实例
2016/06/21 Javascript
深入理解Node.js 事件循环和回调函数
2016/11/02 Javascript
jQuery日程管理插件fullcalendar使用详解
2017/01/07 Javascript
vue中用H5实现文件上传的方法实例代码
2017/05/27 Javascript
深入理解Vue 单向数据流的原理
2017/11/09 Javascript
vue 根据数组中某一项的值进行排序的方法
2018/08/30 Javascript
微信小程序常见页面跳转操作简单示例
2019/05/01 Javascript
浅谈Vue3.0新版API之composition-api入坑指南
2020/04/30 Javascript
详解Vue 数据更新了但页面没有更新的 7 种情况汇总及延伸总结
2020/05/28 Javascript
Vue实现购物车基本功能
2020/11/08 Javascript
[01:11:37]完美世界DOTA2联赛PWL S2 SZ vs FTD.C 第一场 11.19
2020/11/19 DOTA
Python自定义函数的创建、调用和函数的参数详解
2014/03/11 Python
Django 限制访问频率的思路详解
2019/12/24 Python
tensorflow实现从.ckpt文件中读取任意变量
2020/05/26 Python
pycharm配置python 设置pip安装源为豆瓣源
2021/02/05 Python
借助HTML5 Canvas来绘制三角形和矩形等多边形的方法
2016/03/14 HTML / CSS
上课迟到检讨书100字
2014/01/11 职场文书
职工趣味运动会方案
2014/02/10 职场文书
教师爱岗敬业演讲稿
2014/05/05 职场文书
化学专业自荐信
2014/05/28 职场文书
学校2014重阳节活动策划方案
2014/09/16 职场文书
《家庭教育》读后感3篇
2019/12/18 职场文书
Nginx 根据URL带的参数转发的实现
2021/04/01 Servers
《艾尔登法环》1.03.3补丁上线 碎星伤害调整
2022/04/06 其他游戏