webpack 路由配置-【钓鱼工具】vue+路由+菜单+选项卡一键管理后端

2023-12-12 0 4,599 百度已收录

“脚本之家

”,与数百万开发者

作者 | 自然框架

出品| 脚本之家(ID:jb51net)

做一个管理后端,首先要设置路由,然后配置菜单(有时还需要导航),然后创建动态选项卡,最后添加权限判断。

这篇是不是有点长了? 尤其是路由设置和菜单配置webpack 路由配置,是不是很相似? 那么能不能更简单一点呢? 如果我们只需设置一次即可完成所有工作,不是很好吗?

我们可以通过简单的封装来实现这个愿望。

webpack 路由配置-【钓鱼工具】vue+路由+菜单+选项卡一键管理后端

定义一个结构

我们可以参考vue-router的设置和el-menu的参数来设置适合我们需求的结构:

import { createRouter } from '@naturefw/ui-elp'

import home from '../views/home.vue'

const router = {
/**
* 基础路径
*/

baseUrl: baseUrl,

/**
* 首页
*/

home: home,

menus: [
{
menuId: '1', // 相当于路由的 name
title: '全局状态', // 浏览器的标题
naviId: '0', // 导航ID
path: 'global', // 相当于 路由 的path
icon: FolderOpened, // 菜单里的图标
childrens: [ // 子菜单,不是子路由。
{
menuId: '1010', // 相当于路由的 name
title: '纯state',
path: 'state',
icon: Document,
// 加载的组件
component: () => import('../views/state-global/10-state.vue')
// 还可以有子菜单。
},
{
menuId: '1020',
title: '一般的状态',
path: 'standard',
icon: Document,
component: () => import('../views/state-global/20-standard.vue')
}
]
},
{
menuId: '2000',
title: '局部状态',
naviId: '0',
path: 'loacl',
icon: FolderOpened,
childrens: [
{
menuId: '2010',
title: '父子组件',
path: 'parent-son',
icon: Document,
component: () => import('../views/state-loacl/10-parent.vue')
}
]
}
]
}

export default createRouter(router )

根据Router的配置,添加菜单所需的标题、图标等属性,就基本完成了。

加载到主程序中。

设置好之后,我们就可以将其挂载到main上了。

import { createApp } from 'vue'
import App from './App.vue'

// 简易路由
import router from './router'

createApp(App)
.use(router)
.mount('#app')

webpack 路由配置-【钓鱼工具】vue+路由+菜单+选项卡一键管理后端

路线和菜单

就是这样。 是不是很简单呢? 因为我们已经将其他代码封装成组件了。

封装n级菜单

我们可以在el-menu的基础上封装一个动态的n级菜单组件(nf-menu)。

菜单组件可以基于el-menu封装webpack 路由配置,也可以基于其他组件封装,也可以自己写一个。 这里我们以el-menu为例介绍一下封装形式:

  <el-menu
ref="domMenu"
class="el-menu-vertical-demo"
@select="select"
background-color="#6c747c"
text-color="#fff"
active-text-color="#ffd04b"
>

<sub-menu1
:subMenu="menus"
/>

</el-menu>

父菜单比较简单,设置el-menu需要的属性,然后加载子菜单组件。

  <template v-for="(item, index) in subMenu">

<template v-if="item.childrens && item.childrens.length > 0">
<el-sub-menu
:key="item.menuId + '_' + index"
:index="item.menuId"
style="vertical-align: middle;"

>

<template #title>
<component
:is="item.icon"
style="width: 1.5em; height: 1.5em; margin-right: 8px;vertical-align: middle;"
>

</component>
<span>{{item.title}}</span>
</template>

<my-sub-menu2
:subMenu="item.childrens"
/>

</el-sub-menu>
</template>

<el-menu-item v-else
:index="item.menuId"
:key="item.menuId + 'son_' + index"

>

<template #title>
<span style="float: left;">
<component
:is="item.icon"
style="width: 1.5em; height: 1.5em; margin-right: 8px;vertical-align: middle;"
>

</component>
<span >{{item.title}}</span>
</span>
</template>
</el-menu-item>
</template>

然后只要设置属性,一个n级菜单就准备好了。

封装动态选项卡

现在菜单已经存在,下一步是选项卡。 为了满足不同的需求,这里封装了两种组件,一种是单选项卡,一种是动态多选项卡。

  <component :is="$router.getComponent()">
</component>

使用Component直接加载组件即可。

  <el-tabs
v-model="$router.currentRoute.key"
type="border-card"
>

<el-tab-pane label="桌面" name="home">
<component :is="$router.home">
</component>
</el-tab-pane>
<el-tab-pane
v-for="key in $router.tabs"
:key="key"
:label="$router.menuList[key].title"
:name="key"
>

<template #label>
<span>{{$router.menuList[key].title}}  
<circle-close-filled
style="width: 1.0em; height: 1.0em; margin-top: 8px;"
@click.stop="$router.removeTab(key)" />

</span>
</template>
<component :is="$router.menuList[key].component">
</component>
</el-tab-pane>
</el-tabs>

为了维持状态,这里采用了一个笨方法。 通过点击菜单加载的组件放置在el-tab-pane中,通过切换tab来显示组件。

源代码:

制定一个简单的路线

读了半天,你有没有发现,好像少了一个重要的环节?

你猜对了,路由封装还没有被引入。

这里我们不想设计像vue-router那样的通用路由,而是设计适合管理后端的推荐路由。

菜单是多级的,url也是多级的,与菜单对应,但是路由是单级的,不嵌套。

换句话说,如果点击任意级别的(叶)菜单,都会加载同级别的组件。

另外,暂时不考虑组件加载后的路由设置。 我认为这可以通过加载的组件来实现。

import { defineAsyncComponent, reactive, watch, inject } from 'vue'

const flag = Symbol('nf-router-menu___')

/**
* 一个简单的路由
* @param { string } baseUrl 基础路径
* @param { components } home 基础路径
* @param { array } menus 路由设置,数组,多级
* * [{
* * * menuId: '菜单ID'
* * * naviId: '0', // 导航ID,可以不设置
* * * title: '标题',
* * * path: '路径',
* * * icon: Edit, // 图标组件
* * * component: () => import('./views/xxx.vue') // 要加载的组件,可以不设置
* * * childrens: [ // 子菜单,可以多级
* * * * {
* * * * * menuId: '菜单ID'
* * * * * title: '标题',
* * * * * path: '路径',
* * * * * icon: Edit, // 图标组件
* * * * * component: () => import('./views/xxx.vue') // 要加载的组件
* * * * }
* * * ]
* * },
* * 其他菜单
* * ]
* @returns
*/

class Router {
constructor (info) {
// 设置当前选择的路由
this.currentRoute = reactive({
key: 'home', // 默认的首页
paths: [] // 记录打开的多级菜单的信息
})
this.baseUrl = info.baseUrl // 基础路径,应对网站的二级目录
this.baseTitle = document.title // 初始的标题
this.isRefresh = false // 是否刷新进入
this.home = info.home // 默认的首页
this.menus = reactive(info.menus) // 菜单集合,数组形式,支持多级,可以设置导航ID
this.menuList = {} // 变成单层的树,便于用key查找。
this.tabs = reactive(new Set([])) // 点击过且没有关闭的二级菜单,做成动态tab标签

this.setup()
}

/**
* 初始化设置
*/

setup = () => {
// 监听当前路由,设置 tabs 和标题、url
watch(() => this.currentRoute.key, (key) => {

})
}

/**
* 添加新路由,主要是实现根据用户权限加载对应的菜单。
*/

addRoute = (newMenus, props = {}) => {

}

/**
* 删除路由
* @param { array } path 菜单的路径,[] 表示根菜单
* @param { string | number } id 要删除的菜单ID
*/

removeRoute = (path = [], id = '') => {

}

/**
* 刷新时依据url加载组件
*/

refresh = () => {

}

/**
* 加载路由指定的组件
* @returns
*/

getComponent = () => {
if (this.currentRoute.key === '' || this.currentRoute.key === 'home') {
return this.home
} else {
return this.menuList[this.currentRoute.key].component
}
}

/**
* 删除tab
* @param { string } key
* @returns
*/

removeTab = (key) => {

}

/**
* 安装插件
* @param {*} app
*/

install = (app) => {
// 便于模板获取
app.config.globalProperties.$router = this
// 便于代码获取
app.provide(flag, this)
}
}

/**
* 创建简易路由
*/

const createRouter = (info) => {
// 创建路由,
const router = new Router(info)
// 判断url,是否需要加载组件
setTimeout(() => {
router.refresh()
}, 300)
// 使用vue的插件,设置全局路由
return router
}

/**
* 获取路由
* @returns
*/

const useRouter = () => {
return inject(flag)
}

export {
createRouter,
useRouter
}

由于篇幅有限,这里只介绍路由的整体结构。 具体实现方法请看源码:

源代码:

菜单和权限

以上就是静态路由导航设置方法。 对于管理后台来说,一个本质的需求就是根据用户的权限加载路由和菜单。

因此,我们提供了addRoute方法来实现动态添加路由的功能。 这样我们就可以等待用户登录,获取用户的权限,然后根据权限加载路由和菜单。

  const router = useRouter()

router.addRoute([
{
menuId: 'dt-100',
title: '添加根菜单',
naviId: '0',
path: 'new-router',
icon: FolderOpened,
childrens: [
{
menuId: '100-10',
title: '动态菜单',
path: 'ui',
icon: Document,
component: () => import('../ui/base/c-01html.vue')
}
]
}
], { index: 1 })

同时,还可以添加权限歧视。 菜单是基于el-menu实现的。 您可以添加一个select事件,然后确定对丰宝的权限。 如果没有权限,可以跳转到登录组件。


const router = useRouter()

const myselect = (index, indexPath) => {
// 验证权限,如果没有权限,加载登录组件
if (没有权限) {
router.currentRoute.paths = ''
router.currentRoute.key = '登录组件的key'
}
}

示例项目

收藏 (0) 打赏

感谢您的支持,我会继续努力的!

打开微信/支付宝扫一扫,即可进行扫码打赏哦,分享从这里开始,精彩与您同在
点赞 (0)

悟空资源网 webpack webpack 路由配置-【钓鱼工具】vue+路由+菜单+选项卡一键管理后端 https://www.wkzy.net/game/199738.html

常见问题

相关文章

官方客服团队

为您解决烦忧 - 24小时在线 专业服务