Commit 50688879 authored by “yiyousong”'s avatar “yiyousong”

feat: 添加动态菜单

parent 5beea730
#开发环境
NODE_ENV = "development"
VUE_APP_API_BASE_URL=http://192.168.0.98:11078
# VUE_APP_API_BASE_URL=http://192.168.0.98:11078
VUE_APP_API_BASE_URL=http://192.168.0.250:11078
......@@ -10,6 +10,7 @@
"dependencies": {
"@ianwalter/vuex-reset": "^4.3.4",
"@jiaminghi/data-view": "^2.10.0",
"@riophae/vue-treeselect": "^0.4.0",
"axios": "^1.4.0",
"core-js": "^3.8.3",
"crypto-js": "^4.1.1",
......
......@@ -227,6 +227,15 @@ export const addRoleResource = (data) => {
});
};
// 添加角色菜单
export const addRoleMenu = (data) => {
return request({
url: `/bill/role/auth/distributionMenu`,
method: "post",
data,
});
};
/**
* 用户管理
*/
......@@ -347,3 +356,12 @@ export const changeMenuSort = (data) => {
data,
});
};
// 获取菜单树列表
export const getMenuTreeselect = (data) => {
return request({
url: `/bill/menu/treeselect`,
method: "post",
data,
});
};
<template>
<div class="flex h-full w-full flex-col bg-white">
<el-tabs :value="activeKey" @tab-click="changeRouter">
<el-tab-pane v-for="v in secondaryRoutes" :key="v.path" :name="v.path">
<template slot="label">
<i
v-if="v.meta.icon"
:class="['mr-[5px]', 'primary', v.meta.icon]"
></i>
<span class="tab-label">{{ v.meta.title }}</span>
</template>
</el-tab-pane>
</el-tabs>
<div class="flex-1 overflow-y-auto p-[15px]">
<router-view></router-view>
</div>
</div>
</template>
<script>
import { mapGetters } from "vuex";
export default {
name: "TabMenuBar",
data() {
return {
subMenus: [],
};
},
computed: {
...mapGetters("user", ["secondaryRoutes"]),
activeKey() {
return this.$route.path;
},
},
created() {},
methods: {
changeRouter(e) {
this.$router.push(e.name);
},
},
};
</script>
<style lang="less" scoped></style>
......@@ -3,8 +3,8 @@ import store from "@/store";
export const permission = {
inserted: function (el, binding) {
const { value } = binding;
const roles = store.getters["user/userId"];
if (value) {
const roles = store.getters["user/userInfo"].id;
if (value && value instanceof Array && value.length > 0) {
const permissionRoles = value;
const hasPermission = permissionRoles.includes(roles);
if (!hasPermission) {
......@@ -15,3 +15,25 @@ export const permission = {
}
},
};
// 按钮鉴权
export const hasPermi = {
inserted: function (el, binding) {
const { value } = binding;
const permissions = store.getters["user/permissions"];
if (value && value instanceof Array && value.length > 0) {
const permissionFlag = value;
const hasPermissions = permissions.some((permission) => {
return permissionFlag.includes(permission);
});
if (!hasPermissions) {
el.remove();
}
} else {
throw new Error(`请设置操作权限标签值`);
}
},
};
......@@ -17,8 +17,7 @@
:default-active="activeMenu"
mode="horizontal"
router
text-color="rgba(254, 254, 254, 0.65)"
background-color="#0000"
@select="selectMenu"
>
<template v-for="v in menus">
<el-submenu
......@@ -55,7 +54,7 @@
<script>
import HeaderSite from "./HeaderSite.vue";
import { mapState } from "vuex";
import { mapState, mapActions } from "vuex";
export default {
components: {
HeaderSite,
......@@ -75,20 +74,57 @@ export default {
}
return path;
},
...mapState("user", ["menus", "sysName", "sysLogo", "path"]),
...mapState("user", ["menus", "sysName", "sysLogo", "path", "menus"]),
},
created() {
document.title = this.sysName ? this.sysName : this.systemName; // 设置项目标题
},
methods: {
...mapActions("user", ["setSecondaryRoutes"]),
selectMenu(index) {
this.setSecondaryRoutes(index);
},
handleGoHome() {
this.$router.push("/home");
let path = this.menus[0].path;
this.$router.push(path);
},
},
};
</script>
<style lang="less">
.el-menu--popup {
.el-menu-item {
display: flex;
align-items: center;
&:hover {
color: var(--primary) !important;
i {
color: var(--primary);
}
}
}
.is-active {
color: var(--primary) !important;
}
}
</style>
<style lang="less" scoped>
@text-color: #fefefea5;
.mixins(@l,@t) {
content: "";
display: inline-block;
height: 4px;
width: 30%;
background: #ffffff;
border-radius: 2px;
position: absolute;
bottom: 0px;
left: @l;
transform: translateX(@t);
}
.header {
height: 72px;
width: 100%;
......@@ -136,49 +172,67 @@ export default {
:deep(.el-menu) {
height: 100% !important;
border: none !important;
background: #0000;
.el-menu-item {
.el-menu-item:not(.el-submenu) {
height: 100%;
font-size: 16px;
color: #fff;
display: flex;
align-items: center;
border: none !important;
letter-spacing: 1px;
color: @text-color;
i {
color: #fff;
// color: #fff;
color: @text-color;
}
&:hover {
background: #0000 !important;
color: @text-color !important;
&::after {
content: "";
display: inline-block;
height: 4px;
width: 30%;
background: #ffffff;
border-radius: 2px;
position: absolute;
bottom: 0px;
left: 50%;
transform: translateX(-50%);
.mixins(50%,-50%);
}
}
}
.is-active {
.el-submenu {
height: 100%;
font-size: 16px;
.el-submenu__title {
height: 100%;
display: flex;
font-size: 16px;
align-items: center;
border: none !important;
color: @text-color;
&:hover {
background: #0000 !important;
color: #fff !important;
&::after {
.mixins(calc(50% - 20px),-(50% - 20px));
}
}
}
.el-submenu__icon-arrow {
color: @text-color;
}
}
.is-active:not(.el-submenu),
.is-active .el-submenu__title {
color: #fff !important;
background: #0000 !important;
font-weight: 600;
i {
color: #fff;
}
&::after {
content: "";
display: inline-block;
height: 4px;
width: 30%;
background: #ffffff;
border-radius: 2px;
position: absolute;
bottom: 0px;
left: 50%;
transform: translateX(-50%);
.mixins(50%,-50%);
}
}
.is-active .el-submenu__title {
&::after {
left: calc(50% - 20px);
transform: translateX(-(50% - 20px));
}
}
}
......
......@@ -4,19 +4,19 @@
<div class="tab-box flex items-end gap-5">
<router-link
:class="['tab-item', 'top-radius']"
to="/engine/queueupsystem"
v-for="item in secondaryRoutes"
:key="item.path"
:to="item.path"
>
排队取号系统
</router-link>
<router-link
:class="['tab-item', 'top-radius']"
to="/engine/evaluatesystem"
>
评价系统
<i v-if="item.meta.icon" :class="['mr-2', item.meta.icon]"></i>
{{ item.meta.title }}
</router-link>
</div>
<div class="flex gap-5">
<div class="search-box top-radius flex h-full items-center gap-5">
<div
class="search-box top-radius flex h-full items-center gap-5"
v-hasPermi="['engine:query']"
>
<div class="text-[14px] text-[#395EBF]">
统计时段:{{ time[0] }}~{{ time[1] }}
</div>
......@@ -35,6 +35,7 @@
<div
class="engine-btn top-radius"
@click="$router.push('/enginesearch')"
v-hasPermi="['engine:enginesearch']"
>
<img src="@/assets/img/engine.png" class="engine-img mr-2 w-[24px]" />
数据搜索引擎
......@@ -48,6 +49,7 @@
</template>
<script>
import { mapGetters } from "vuex";
export default {
data() {
return {
......@@ -64,6 +66,9 @@ export default {
});
},
},
computed: {
...mapGetters("user", ["secondaryRoutes"]),
},
created() {
this.$nextTick(() => {
this.handleDate();
......
......@@ -13,6 +13,7 @@
:loading="hallLoading"
type="hall"
@export="exportHallEva"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......@@ -37,6 +38,8 @@
type="pjOption"
@export="exportPjOptionEva"
@search="handleSearch"
hasPermiQuery="engine:queueupsystem:query"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......@@ -61,6 +64,8 @@
type="dept"
@export="exportDeptEva"
@search="handleSearch"
hasPermiQuery="engine:queueupsystem:query"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......@@ -85,6 +90,8 @@
type="window"
@export="exportWindowEva"
@search="handleSearch"
hasPermiQuery="engine:queueupsystem:query"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......
......@@ -13,6 +13,7 @@
:loading="hallLoading"
type="hall"
@export="exportHallQueue"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......@@ -37,6 +38,8 @@
type="business"
@export="exportbusinessQueue"
@search="handleSearch"
hasPermiQuery="engine:queueupsystem:query"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......@@ -61,6 +64,8 @@
type="dept"
@export="exportDeptQueue"
@search="handleSearch"
hasPermiQuery="engine:queueupsystem:query"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......@@ -85,6 +90,8 @@
type="window"
@export="exportWindowQueue"
@search="handleSearch"
hasPermiQuery="engine:queueupsystem:query"
hasPermiExport="engine:queueupsystem:export"
></DoubleTable>
</div>
<Pagination
......
......@@ -5,7 +5,11 @@
{{ title }}
</div>
<div class="flex gap-4">
<el-button type="primary" size="small" @click="handleExport"
<el-button
type="primary"
size="small"
@click="handleExport"
v-hasPermi="[hasPermiExport]"
>导出</el-button
>
......@@ -16,6 +20,7 @@
v-model="form.pjOption"
placeholder="请选择评价选项"
clearable
v-hasPermi="[hasPermiQuery]"
>
<el-option
v-for="(v, i) in dict.pjOption"
......@@ -32,6 +37,7 @@
v-model="form.businessName"
placeholder="请选择业务"
clearable
v-hasPermi="[hasPermiQuery]"
>
<el-option
v-for="(v, i) in getTopKeyList(dict.businessList)"
......@@ -48,6 +54,7 @@
v-model="form.deptName"
placeholder="请选择部门"
clearable
v-hasPermi="[hasPermiQuery]"
>
<el-option
v-for="(v, i) in getTopKeyList(dict.sectionNameList)"
......@@ -64,6 +71,7 @@
v-model="form.windowNum"
placeholder="请选择窗口"
clearable
v-hasPermi="[hasPermiQuery]"
>
<el-option
v-for="(v, i) in getTopKeyList(dict.windowFromnumList)"
......@@ -78,6 +86,7 @@
size="small"
v-if="type != 'hall'"
@click="handleSearch"
v-hasPermi="[hasPermiQuery]"
>搜索</el-button
>
</div>
......@@ -153,6 +162,12 @@ export default {
type: Object,
default: () => {},
},
hasPermiQuery: {
type: String,
},
hasPermiExport: {
type: String,
},
},
data() {
return {
......
......@@ -8,6 +8,7 @@
size="small"
:loading="exportLoading"
@click="exportExcel"
v-hasPermi="['market:evaluatereport:export']"
>导出</el-button
>
<div class="text-[#909399]">
......@@ -17,7 +18,10 @@
统计时间段:{{ searchForm.time[0] }} ~ {{ searchForm.time[1] }}
</div>
</div>
<div class="flex items-center">
<div
class="flex items-center"
v-hasPermi="['market:evaluatereport:query']"
>
<el-form ref="searchForm" inline size="small" :model="searchForm">
<el-form-item>
<el-select style="width: 130px" v-model="searchForm.type">
......@@ -52,7 +56,11 @@
</el-form-item>
</el-form>
</div>
<el-popover placement="bottom" trigger="click">
<el-popover
placement="bottom"
trigger="click"
v-hasPermi="['market:evaluatereport:query']"
>
<div class="w-full">
<el-form ref="searchForm2" inline size="small" :model="searchForm2">
<el-form-item>
......
......@@ -10,7 +10,7 @@
</div>
<div class="flex h-full flex-1 flex-col bg-white">
<el-tabs :value="activeKey" @tab-click="changeRouter">
<el-tab-pane v-for="v in subMenus" :key="v.path" :name="v.path">
<el-tab-pane v-for="v in secondaryRoutes" :key="v.path" :name="v.path">
<template slot="label">
<i
v-if="v.meta.icon"
......@@ -28,37 +28,25 @@
</template>
<script>
import { findBottomSubarrays } from "@/utils";
import { mapGetters } from "vuex";
export default {
data() {
return {
subMenus: [],
curTreeData: {}, // 当前选择的站点
};
},
computed: {
...mapGetters("user", ["secondaryRoutes"]),
activeKey() {
return this.$route.path;
},
},
created() {
this.getSubMenus();
},
created() {},
methods: {
changeRouter(e) {
this.$router.push(e.name);
},
// 获取当前顶层路由下的所有子路由
getSubMenus() {
let path = this.$route?.meta.activeMenu
? this.$route.meta.activeMenu
: this.$route.path;
let options = this.$router.options.routes[0].children;
let curRouters = options.filter((v) => v.path == path);
this.subMenus = findBottomSubarrays(curRouters).filter(
(v) => !v.meta.hidden
);
},
// 改变站点选择
changeSite(data) {
this.curTreeData = data;
......
......@@ -8,6 +8,7 @@
size="small"
:loading="exportLoading"
@click="exportExcel"
v-hasPermi="['market:queueupreport:export']"
>导出</el-button
>
<div class="text-[#909399]">
......@@ -17,7 +18,10 @@
统计时间段:{{ searchForm.time[0] }} ~ {{ searchForm.time[1] }}
</div>
</div>
<div class="flex items-center">
<div
class="flex items-center"
v-hasPermi="['market:queueupreport:query']"
>
<el-form ref="searchForm" inline size="small" :model="searchForm">
<el-form-item>
<el-select style="width: 130px" v-model="searchForm.type">
......@@ -52,7 +56,11 @@
</el-form-item>
</el-form>
</div>
<el-popover placement="bottom" trigger="click">
<el-popover
placement="bottom"
trigger="click"
v-hasPermi="['market:queueupreport:query']"
>
<div class="w-full">
<el-form ref="searchForm2" inline size="small" :model="searchForm2">
<!-- <el-form-item>
......
......@@ -7,9 +7,14 @@
<script>
import storage from "@/utils/storage";
import { mapMutations } from "vuex";
import { getHomeData } from "@/api/home";
import { generateRoutes, filterBtn } from "@/utils";
import { calcMenu } from "@/router";
export default {
data() {
return {};
return {
menuList: [],
};
},
created() {
this.getToken();
......@@ -21,9 +26,12 @@ export default {
"SET_sysLogo",
"SET_path",
"SET_userInfo",
"SET_permissions",
"SET_routes",
"SET_menusList",
]),
// 获取token
getToken() {
async getToken() {
let { token, userInfo, siteid, siteName, sysName, sysLogo, path } =
this.$route.query;
if (token && userInfo) {
......@@ -35,7 +43,7 @@ export default {
this.SET_path(path);
storage.set(2, "siteId", siteid);
storage.set(2, "siteName", siteName);
this.$router.push("/home");
await this.getIndixData();
} else {
this.$message.warning("跳转失败,请重新登录");
setTimeout(() => {
......@@ -43,6 +51,32 @@ export default {
}, 2000);
}
},
// 获取菜单列表
async getIndixData() {
let res = await getHomeData();
if (res.data.code == 1) {
let { menuList } = res.data.data;
// 过滤掉按钮
let menus = filterBtn(menuList, false);
let routes = generateRoutes(menus);
// this.SET_routes(routes);
this.SET_menusList(menus);
this.setBtnPermissions(menuList);
calcMenu();
if (routes.length) {
let path = routes[0].path;
this.$router.push(path);
}
}
},
// 添加按钮权限字符
setBtnPermissions(menuList) {
let btnPermissions = filterBtn(menuList)
.filter((v) => v.perms)
.map((v) => v.perms);
this.SET_permissions(btnPermissions);
},
},
};
</script>
......
<template>
<div class="system flex flex-col bg-white">
<el-tabs :value="activeKey" @tab-click="changeRouter">
<el-tab-pane v-for="v in subMenus" :key="v.path" :name="v.path">
<template slot="label">
<i
v-if="v.meta.icon"
:class="['mr-[5px]', 'primary', v.meta.icon]"
></i>
<span class="tab-label">{{ v.meta.title }}</span>
</template>
</el-tab-pane>
</el-tabs>
<div class="system-out-box flex-1">
<router-view></router-view>
</div>
<div class="system">
<TabMenuBar></TabMenuBar>
</div>
</template>
<script>
import { findBottomSubarrays } from "@/utils";
export default {
data() {
return {
subMenus: [],
};
},
computed: {
activeKey() {
return this.$route.path;
},
},
created() {
this.getSubMenus();
},
methods: {
changeRouter(e) {
this.$router.push(e.name);
},
// 获取当前顶层路由下的所有子路由
getSubMenus() {
let path = this.$route?.meta.activeMenu
? this.$route.meta.activeMenu
: this.$route.path;
let options = this.$router.options.routes[0].children;
let curRouters = options.filter((v) => v.path == path);
this.subMenus = findBottomSubarrays(curRouters).filter(
(v) => !v.meta.hidden
);
},
},
computed: {},
created() {},
methods: {},
};
</script>
<style lang="less" scoped>
// :deep(.el-tabs__nav-scroll) {
// padding-left: 15px;
// }
.system {
width: 100%;
height: 100%;
.system-out-box {
padding: 15px;
overflow-y: auto;
}
}
</style>
<template>
<div>
<el-popover placement="bottom-start" trigger="click">
<el-popover placement="bottom-start" trigger="click" width="100%">
<el-tree
:data="treeData"
:props="defaultProps"
......@@ -20,11 +19,11 @@
@clear="handleClear"
></el-input>
</el-popover>
</div>
</template>
<script>
export default {
name: "InputTree",
props: {
treeData: {
type: Array,
......@@ -35,15 +34,19 @@ export default {
value: {
default: "",
},
},
data() {
return {
defaultProps: {
type: Object,
default: () => {
return {
children: "children",
label: "areaName",
},
};
},
},
},
data() {
return {};
},
methods: {
handleClear() {
this.$emit("input", "");
......
......@@ -107,7 +107,7 @@ export default {
{
label: "菜单名称",
prop: "name",
align: "center",
// align: "center",
},
{
label: "ID",
......@@ -242,7 +242,7 @@ export default {
this.current -= 1;
this.getMenuList();
}
this.menuList = [...this.menuList, ...data];
this.menuList = [...this.menuList, ...buildTree(data)];
this.tableData = buildTree(data);
this.total = total;
this.dict = dict;
......
......@@ -3,12 +3,6 @@
<div
class="content grid max-h-[300px] w-full grid-cols-2 gap-x-4 gap-y-2 overflow-auto"
>
<div
:class="['cursor-pointer indent-8', { active: value === '' }]"
@click="handleChange('')"
>
不需要图标
</div>
<div v-for="(v, i) in iconJson" :key="i">
<div
:class="[
......@@ -30,8 +24,8 @@
v-bind="$attrs"
v-on="$listeners"
:value="value"
readonly
:placeholder="placeholder"
clearable
>
<i v-if="value" slot="prefix" :class="value" />
<i v-else slot="prefix" class="el-icon-search" />
......
This diff is collapsed.
import { getSiteBusiness, getDepartment, getWindow } from "@/api/site";
import { getHomeData } from "@/api/home";
import { findInTree } from "@/utils";
export default {
namespaced: true,
state: {
menus: [], // 菜单
menusList: [], // 原始菜单列表
menus: [], // 格式化菜单列表
routes: [], // 路由列表
secondaryRoutes: [], // 二级路由
barList: [], // 登录返回菜单
homeData: {}, // 首页数据
token: "",
......@@ -16,6 +20,7 @@ export default {
businessList: [], // 站点业务列表
deptList: [], // 站点部门列表
windowList: [], // 站点窗口列表
permissions: [], // 按钮权限字符列表
},
getters: {
siteId(state) {
......@@ -37,8 +42,35 @@ export default {
let { barList } = state.homeData;
return barList || [];
},
routes(state) {
return state.routes;
},
menus(state) {
return state.menus;
},
permissions(state) {
return state.permissions;
},
menusList(state) {
return state.menusList;
},
secondaryRoutes(state) {
return state.secondaryRoutes;
},
},
mutations: {
SET_menusList(state, menusList) {
state.menusList = menusList;
},
SET_routes(state, routes) {
state.routes = routes;
},
SET_permissions(state, permissions) {
state.permissions = permissions;
},
SET_secondaryRoutes(state, secondaryRoutes) {
state.secondaryRoutes = secondaryRoutes;
},
SET_path(state, path) {
state.path = path;
},
......@@ -127,5 +159,11 @@ export default {
context.commit("SET_windowList", data);
}
},
// 设置二级路由
setSecondaryRoutes(context, value) {
let routes = findInTree(context.state.menus, "path", value);
let secondaryRoutes = routes.children || [];
context.commit("SET_secondaryRoutes", secondaryRoutes);
},
},
};
import Vue from "vue";
import CryptoJS from "crypto-js";
import moment from "moment";
import { find, get } from "lodash-es";
// 加密数据
export let encrypt = (str, keyStr, ivStr) => {
......@@ -205,3 +206,95 @@ export const getFieldFromArray = (arr, field, treeField) => {
return result;
};
// 生成路由
export const generateRoutes = (menuList) => {
let routers = menuList.map((item) => {
// 构造符合要求的结构
let path = item.url.charAt(0) === "/" ? item.url : "/" + item.url;
let name = item.url.charAt(0) === "/" ? item.url.slice(1) : item.url;
let activeMenu = item.activeDir
? item.activeDir.charAt(0) === "/"
? item.activeDir
: "/" + item.activeDir
: "";
let component = item.component
? item.component.charAt(0) === "/"
? item.component
: "/" + item.component
: null;
const newItem = {
path,
name,
hidden: !!item.visible,
hideChildrenInMenu: !!item.hideChildrenInMenu,
component: () => import(`@/pages${component}`),
meta: {
title: item.name,
icon: item.imgPath,
keepAlive: !!item.cache,
activeMenu,
},
};
// 递归处理子节点
if (item.children && item.children.length > 0) {
newItem.children = generateRoutes(item.children);
}
return newItem;
});
routers.forEach((v) => {
if (v.children && v.children.length) {
v.redirect = v.children[0].path;
}
});
return routers;
};
/**
* 过滤菜单按钮项并提取 menuType = 2 的项
* @param {Array} menuList - 菜单列表
* @param {Boolean} menuType - true 获取 menuType = 2 的项并返回为一维数组, false 剔除 menuType = 2 的项
* @param {Array} btnItems - 用于存储 menuType = 2 的项(递归使用)
* @returns {Array} - 返回提取到的 menuType = 2 的项(如果 menuType 为 true)或剔除 menuType = 2 的菜单
*/
export const filterBtn = (menuList, menuType = true, btnItems = []) => {
const result = menuList
.map((menu) => {
// 深拷贝对象,避免修改原数据
const newMenu = { ...menu };
if (newMenu.children && newMenu.children.length > 0) {
newMenu.children = filterBtn(newMenu.children, menuType, btnItems);
}
const btnItem = newMenu.menuType == 2;
if (menuType) {
if (btnItem) {
btnItems.push(newMenu);
}
return newMenu;
} else {
// 剔除 menuType = 2 的项
return !btnItem ? newMenu : null;
}
})
.filter((menu) => menu !== null); // 过滤掉 null 项
return menuType ? btnItems : result;
};
export function findInTree(data, key, value) {
// 递归遍历树形结构
function recursiveSearch(nodes) {
return find(nodes, (node) => {
if (get(node, key) === value) {
return true;
}
if (node.children) {
return recursiveSearch(node.children);
}
return false;
});
}
return recursiveSearch(data);
}
......@@ -989,6 +989,13 @@
dependencies:
regenerator-runtime "^0.13.11"
"@babel/runtime@^7.3.1":
version "7.25.6"
resolved "https://registry.npmmirror.com/@babel/runtime/-/runtime-7.25.6.tgz#9afc3289f7184d8d7f98b099884c26317b9264d2"
integrity sha512-VBj9MYyDb9tuLq7yzqjgzt6Q+IBQLrGZfdjOekyEirZPHxXWoTSGUTMrpsfi58Up73d13NfYLv8HT9vmznjzhQ==
dependencies:
regenerator-runtime "^0.14.0"
"@babel/template@^7.22.5":
version "7.22.5"
resolved "https://registry.npmmirror.com/@babel/template/-/template-7.22.5.tgz"
......@@ -1222,6 +1229,20 @@
resolved "https://registry.npmmirror.com/@polka/url/-/url-1.0.0-next.21.tgz"
integrity sha512-a5Sab1C4/icpTZVzZc5Ghpz88yQtGOyNqYXcZgOssB2uuAr+wF/MvN6bgtW32q7HHrvBki+BsZ0OuNv6EV3K9g==
"@riophae/vue-treeselect@^0.4.0":
version "0.4.0"
resolved "https://registry.npmmirror.com/@riophae/vue-treeselect/-/vue-treeselect-0.4.0.tgz#0baed5a794cffc580b63591f35c125e51c0df241"
integrity sha512-J4atYmBqXQmiPFK/0B5sXKjtnGc21mBJEiyKIDZwk0Q9XuynVFX6IJ4EpaLmUgL5Tve7HAS7wkiGGSti6Uaxcg==
dependencies:
"@babel/runtime" "^7.3.1"
babel-helper-vue-jsx-merge-props "^2.0.3"
easings-css "^1.0.0"
fuzzysearch "^1.0.3"
is-promise "^2.1.0"
lodash "^4.0.0"
material-colors "^1.2.6"
watch-size "^2.0.0"
"@sideway/address@^4.1.3":
version "4.1.4"
resolved "https://registry.npmmirror.com/@sideway/address/-/address-4.1.4.tgz"
......@@ -2140,7 +2161,7 @@ axios@^1.4.0:
form-data "^4.0.0"
proxy-from-env "^1.1.0"
babel-helper-vue-jsx-merge-props@^2.0.0:
babel-helper-vue-jsx-merge-props@^2.0.0, babel-helper-vue-jsx-merge-props@^2.0.3:
version "2.0.3"
resolved "https://registry.npmmirror.com/babel-helper-vue-jsx-merge-props/-/babel-helper-vue-jsx-merge-props-2.0.3.tgz#22aebd3b33902328e513293a8e4992b384f9f1b6"
integrity sha512-gsLiKK7Qrb7zYJNgiXKpXblxbV5ffSwR0f5whkPAaBAR4fhi6bwRZxX9wBlIc5M/v8CCkXUbXZL4N/nSE97cqg==
......@@ -3104,6 +3125,11 @@ duplexer@^0.1.2:
resolved "https://registry.npmmirror.com/duplexer/-/duplexer-0.1.2.tgz"
integrity sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==
easings-css@^1.0.0:
version "1.0.0"
resolved "https://registry.npmmirror.com/easings-css/-/easings-css-1.0.0.tgz#dde569003bb7a4a0c0b77878f5db3e0be5679c81"
integrity sha512-7Uq7NdazNfVtr0RNmPAys8it0zKCuaqxJStYKEl72D3j4gbvXhhaM7iWNbqhA4C94ygCye6VuyhzBRQC4szeBg==
easy-stack@1.0.1:
version "1.0.1"
resolved "https://registry.npmmirror.com/easy-stack/-/easy-stack-1.0.1.tgz"
......@@ -3684,6 +3710,11 @@ functional-red-black-tree@^1.0.1:
resolved "https://registry.npmmirror.com/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz"
integrity sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g==
fuzzysearch@^1.0.3:
version "1.0.3"
resolved "https://registry.npmmirror.com/fuzzysearch/-/fuzzysearch-1.0.3.tgz#dffc80f6d6b04223f2226aa79dd194231096d008"
integrity sha512-s+kNWQuI3mo9OALw0HJ6YGmMbLqEufCh2nX/zzV5CrICQ/y4AwPxM+6TIiF9ItFCHXFCyM/BfCCmN57NTIJuPg==
gensync@^1.0.0-beta.2:
version "1.0.0-beta.2"
resolved "https://registry.npmmirror.com/gensync/-/gensync-1.0.0-beta.2.tgz"
......@@ -4173,6 +4204,11 @@ is-plain-object@^2.0.4:
dependencies:
isobject "^3.0.1"
is-promise@^2.1.0:
version "2.2.2"
resolved "https://registry.npmmirror.com/is-promise/-/is-promise-2.2.2.tgz#39ab959ccbf9a774cf079f7b40c7a26f763135f1"
integrity sha512-+lP4/6lKUBfQjZ2pdxThZvLUAafmZb8OAxFb8XXtiQmS35INgr85hdOGoEs124ez1FCnZJt6jau/T+alh58QFQ==
is-stream@^1.1.0:
version "1.1.0"
resolved "https://registry.npmmirror.com/is-stream/-/is-stream-1.1.0.tgz"
......@@ -4485,7 +4521,7 @@ lodash.uniq@^4.5.0:
resolved "https://registry.npmmirror.com/lodash.uniq/-/lodash.uniq-4.5.0.tgz"
integrity sha512-xfBaXQd9ryd9dlSDvnvI0lvxfLJlYAZzXomUYzLKtUeOQvOP5piqAWuGtrhWeqaXK9hhoM/iyJc5AV+XfsX3HQ==
lodash@^4.17.14, lodash@^4.17.20, lodash@^4.17.21:
lodash@^4.0.0, lodash@^4.17.14, lodash@^4.17.20, lodash@^4.17.21:
version "4.17.21"
resolved "https://registry.npmmirror.com/lodash/-/lodash-4.17.21.tgz"
integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==
......@@ -4556,6 +4592,11 @@ make-dir@^3.0.2, make-dir@^3.1.0:
dependencies:
semver "^6.0.0"
material-colors@^1.2.6:
version "1.2.6"
resolved "https://registry.npmmirror.com/material-colors/-/material-colors-1.2.6.tgz#6d1958871126992ceecc72f4bcc4d8f010865f46"
integrity sha512-6qE4B9deFBIa9YSpOc9O0Sgc43zTeVYbgDT5veRKSlB2+ZuHNoVVxA1L/ckMUayV9Ay9y7Z/SZCLcGteW9i7bg==
mdn-data@2.0.14:
version "2.0.14"
resolved "https://registry.npmmirror.com/mdn-data/-/mdn-data-2.0.14.tgz"
......@@ -5714,6 +5755,11 @@ regenerator-runtime@^0.13.11:
resolved "https://registry.npmmirror.com/regenerator-runtime/-/regenerator-runtime-0.13.11.tgz"
integrity sha512-kY1AZVr2Ra+t+piVaJ4gxaFaReZVH40AKNo7UCX6W+dEwBo/2oZJzqfuN1qLq1oL45o56cPaTXELwrTh8Fpggg==
regenerator-runtime@^0.14.0:
version "0.14.1"
resolved "https://registry.npmmirror.com/regenerator-runtime/-/regenerator-runtime-0.14.1.tgz#356ade10263f685dda125100cd862c1db895327f"
integrity sha512-dYnhHh0nJoMfnkZs6GmmhFknAGRrLznOu5nc9ML+EJxGvrx6H7teuevqVqCuPcPK//3eDrrjQhehXVx9cnkGdw==
regenerator-transform@^0.15.1:
version "0.15.1"
resolved "https://registry.npmmirror.com/regenerator-transform/-/regenerator-transform-0.15.1.tgz"
......@@ -6688,6 +6734,11 @@ vuex@^3.6.2:
resolved "https://registry.npmmirror.com/vuex/-/vuex-3.6.2.tgz"
integrity sha512-ETW44IqCgBpVomy520DT5jf8n0zoCac+sxWnn+hMe/CzaSejb/eVw2YToiXYX+Ex/AuHHia28vWTq4goAexFbw==
watch-size@^2.0.0:
version "2.0.0"
resolved "https://registry.npmmirror.com/watch-size/-/watch-size-2.0.0.tgz#096ee28d0365bd7ea03d9c8bf1f2f50a73be1474"
integrity sha512-M92R89dNoTPWyCD+HuUEDdhaDnh9jxPGOwlDc0u51jAgmjUvzqaEMynXSr3BaWs+QdHYk4KzibPy1TFtjLmOZQ==
watchpack@^2.4.0:
version "2.4.0"
resolved "https://registry.npmmirror.com/watchpack/-/watchpack-2.4.0.tgz"
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment