refactor: 优化数据加载逻辑.
This commit is contained in:
@@ -10,7 +10,7 @@
|
|||||||
<span title="当前版本">v{{ version }}</span>
|
<span title="当前版本">v{{ version }}</span>
|
||||||
</a-space>
|
</a-space>
|
||||||
<span class="copyright">
|
<span class="copyright">
|
||||||
Copyright<icon-copyright /> 2023 By OrionOpsPro
|
Copyright<icon-copyright /> 2023 By lijiahang
|
||||||
</span>
|
</span>
|
||||||
</a-space>
|
</a-space>
|
||||||
</a-layout-footer>
|
</a-layout-footer>
|
||||||
|
|||||||
@@ -206,12 +206,12 @@
|
|||||||
import { useDark, useFullscreen, useToggle } from '@vueuse/core';
|
import { useDark, useFullscreen, useToggle } from '@vueuse/core';
|
||||||
import { useAppStore, useTabBarStore, useTipsStore, useUserStore } from '@/store';
|
import { useAppStore, useTabBarStore, useTipsStore, useUserStore } from '@/store';
|
||||||
import { LOCALE_OPTIONS } from '@/locale';
|
import { LOCALE_OPTIONS } from '@/locale';
|
||||||
import { triggerMouseEvent } from '@/utils';
|
import { triggerMouseEvent } from '@/utils/event';
|
||||||
import { openAppSettingKey, toggleDrawerMenuKey } from '@/types/symbol';
|
import { openAppSettingKey, toggleDrawerMenuKey } from '@/types/symbol';
|
||||||
import { preferenceTipsKey } from './const';
|
import { preferenceTipsKey } from './const';
|
||||||
import { REDIRECT_ROUTE_NAME, routerToTag } from '@/router/constants';
|
import { REDIRECT_ROUTE_NAME, routerToTag } from '@/router/constants';
|
||||||
import Menu from '@/components/system/menu/tree/index.vue';
|
import Menu from '@/components/system/menu/tree/index.vue';
|
||||||
import UpdatePasswordModal from '@/components/user/role/update-password-modal.vue';
|
import UpdatePasswordModal from '@/components/user/user/update-password-modal.vue';
|
||||||
import MessageBox from '@/components/system/message-box/index.vue';
|
import MessageBox from '@/components/system/message-box/index.vue';
|
||||||
|
|
||||||
const tipsStore = useTipsStore();
|
const tipsStore = useTipsStore();
|
||||||
|
|||||||
@@ -45,7 +45,8 @@
|
|||||||
|
|
||||||
// 初始化选项
|
// 初始化选项
|
||||||
onBeforeMount(() => {
|
onBeforeMount(() => {
|
||||||
optionData.value = cacheStore.roles.map(s => {
|
cacheStore.loadRoles().then(roles => {
|
||||||
|
optionData.value = roles.map(s => {
|
||||||
return {
|
return {
|
||||||
label: `${s.name} (${s.code})`,
|
label: `${s.name} (${s.code})`,
|
||||||
disabled: s.status === RoleStatus.DISABLED,
|
disabled: s.status === RoleStatus.DISABLED,
|
||||||
@@ -53,6 +54,7 @@
|
|||||||
};
|
};
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@@ -18,7 +18,7 @@
|
|||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
import type { PropType } from 'vue';
|
import type { PropType } from 'vue';
|
||||||
import type { SelectOptionData } from '@arco-design/web-vue';
|
import type { SelectOptionData } from '@arco-design/web-vue';
|
||||||
import { computed, ref, onBeforeMount } from 'vue';
|
import { computed, ref, onMounted } from 'vue';
|
||||||
import { useCacheStore } from '@/store';
|
import { useCacheStore } from '@/store';
|
||||||
import { labelFilter } from '@/types/form';
|
import { labelFilter } from '@/types/form';
|
||||||
|
|
||||||
@@ -43,14 +43,17 @@
|
|||||||
const optionData = ref<Array<SelectOptionData>>([]);
|
const optionData = ref<Array<SelectOptionData>>([]);
|
||||||
|
|
||||||
// 初始化选项
|
// 初始化选项
|
||||||
onBeforeMount(() => {
|
onMounted(() => {
|
||||||
optionData.value = cacheStore.users.map(s => {
|
// 加载用户列表
|
||||||
|
cacheStore.loadUsers().then(users => {
|
||||||
|
optionData.value = users.map(s => {
|
||||||
return {
|
return {
|
||||||
label: `${s.nickname} (${s.username})`,
|
label: `${s.nickname} (${s.username})`,
|
||||||
value: s.id,
|
value: s.id,
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@@ -14,8 +14,8 @@
|
|||||||
v-model:page-size="(pagination as PaginationProps).pageSize"
|
v-model:page-size="(pagination as PaginationProps).pageSize"
|
||||||
v-bind="pagination"
|
v-bind="pagination"
|
||||||
:auto-adjust="false"
|
:auto-adjust="false"
|
||||||
@change="page => emits('emitter', HeaderEmitter.PAGE_CHANGE, page, (pagination as PaginationProps).pageSize)"
|
@change="page => bubblesEmitter(HeaderEmitter.PAGE_CHANGE, page, (pagination as PaginationProps).pageSize)"
|
||||||
@page-size-change="limit => emits('emitter', HeaderEmitter.PAGE_CHANGE, 1, limit)" />
|
@page-size-change="limit => bubblesEmitter(HeaderEmitter.PAGE_CHANGE, 1, limit)" />
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!-- 操作部分 -->
|
<!-- 操作部分 -->
|
||||||
@@ -28,7 +28,7 @@
|
|||||||
v-if="!handleVisible?.disableAdd"
|
v-if="!handleVisible?.disableAdd"
|
||||||
class="click-icon-wrapper card-header-icon-wrapper"
|
class="click-icon-wrapper card-header-icon-wrapper"
|
||||||
title="创建"
|
title="创建"
|
||||||
@click="emits('emitter', HeaderEmitter.ADD)">
|
@click="bubblesEmitter(HeaderEmitter.ADD)">
|
||||||
<icon-plus />
|
<icon-plus />
|
||||||
</div>
|
</div>
|
||||||
<!-- 左侧侧操作槽位 -->
|
<!-- 左侧侧操作槽位 -->
|
||||||
@@ -48,9 +48,9 @@
|
|||||||
:placeholder="searchInputPlaceholder as string"
|
:placeholder="searchInputPlaceholder as string"
|
||||||
size="small"
|
size="small"
|
||||||
allow-clear
|
allow-clear
|
||||||
@input="e => emits('emitter', HeaderEmitter.UPDATE_SEARCH_VALUE, e)"
|
@input="e => bubblesEmitter(HeaderEmitter.UPDATE_SEARCH_VALUE, e)"
|
||||||
@change="e => emits('emitter', HeaderEmitter.UPDATE_SEARCH_VALUE, e)"
|
@change="e => bubblesEmitter(HeaderEmitter.UPDATE_SEARCH_VALUE, e)"
|
||||||
@keyup.enter="emits('emitter', HeaderEmitter.SEARCH)" />
|
@keyup.enter="bubblesEmitter(HeaderEmitter.SEARCH)" />
|
||||||
</div>
|
</div>
|
||||||
<!-- 过滤条件 -->
|
<!-- 过滤条件 -->
|
||||||
<a-popover position="br" trigger="click" content-class="card-filter-wrapper">
|
<a-popover position="br" trigger="click" content-class="card-filter-wrapper">
|
||||||
@@ -78,14 +78,14 @@
|
|||||||
<div v-if="!handleVisible?.disableSearch"
|
<div v-if="!handleVisible?.disableSearch"
|
||||||
class="click-icon-wrapper card-header-icon-wrapper"
|
class="click-icon-wrapper card-header-icon-wrapper"
|
||||||
title="搜索"
|
title="搜索"
|
||||||
@click="emits('emitter', HeaderEmitter.SEARCH)">
|
@click="bubblesEmitter(HeaderEmitter.SEARCH)">
|
||||||
<icon-search />
|
<icon-search />
|
||||||
</div>
|
</div>
|
||||||
<!-- 重置 -->
|
<!-- 重置 -->
|
||||||
<div v-if="!handleVisible?.disableReset"
|
<div v-if="!handleVisible?.disableReset"
|
||||||
class="click-icon-wrapper card-header-icon-wrapper"
|
class="click-icon-wrapper card-header-icon-wrapper"
|
||||||
title="重置"
|
title="重置"
|
||||||
@click="emits('emitter', HeaderEmitter.RESET)">
|
@click="bubblesEmitter(HeaderEmitter.RESET)">
|
||||||
<icon-refresh />
|
<icon-refresh />
|
||||||
</div>
|
</div>
|
||||||
</a-space>
|
</a-space>
|
||||||
@@ -106,12 +106,15 @@
|
|||||||
import type { CardProps } from '../types/props';
|
import type { CardProps } from '../types/props';
|
||||||
import { ref, computed } from 'vue';
|
import { ref, computed } from 'vue';
|
||||||
import { useAppStore } from '@/store';
|
import { useAppStore } from '@/store';
|
||||||
import { triggerMouseEvent } from '@/utils';
|
import { triggerMouseEvent } from '@/utils/event';
|
||||||
import { HeaderEmitter } from '../types/emits';
|
import { HeaderEmitter } from '../types/emits';
|
||||||
|
import useEmitter from '@/hooks/emitter';
|
||||||
|
|
||||||
const props = defineProps<CardProps>();
|
const props = defineProps<CardProps>();
|
||||||
const emits = defineEmits(['emitter']);
|
const emits = defineEmits(['emitter']);
|
||||||
|
|
||||||
|
const { bubblesEmitter } = useEmitter(emits);
|
||||||
|
|
||||||
const appStore = useAppStore();
|
const appStore = useAppStore();
|
||||||
|
|
||||||
const filterRef = ref();
|
const filterRef = ref();
|
||||||
@@ -130,21 +133,21 @@
|
|||||||
},
|
},
|
||||||
set(e) {
|
set(e) {
|
||||||
if (e) {
|
if (e) {
|
||||||
emits('emitter', HeaderEmitter.UPDATE_SEARCH_VALUE, e);
|
bubblesEmitter(HeaderEmitter.UPDATE_SEARCH_VALUE, e);
|
||||||
} else {
|
} else {
|
||||||
emits('emitter', HeaderEmitter.UPDATE_SEARCH_VALUE, null);
|
bubblesEmitter(HeaderEmitter.UPDATE_SEARCH_VALUE, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
// 重置过滤
|
// 重置过滤
|
||||||
const filterReset = () => {
|
const filterReset = () => {
|
||||||
emits('emitter', HeaderEmitter.RESET);
|
bubblesEmitter(HeaderEmitter.RESET);
|
||||||
};
|
};
|
||||||
|
|
||||||
// 搜索
|
// 搜索
|
||||||
const filterSearch = () => {
|
const filterSearch = () => {
|
||||||
emits('emitter', HeaderEmitter.SEARCH);
|
bubblesEmitter(HeaderEmitter.SEARCH);
|
||||||
triggerMouseEvent(filterRef);
|
triggerMouseEvent(filterRef);
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -156,7 +159,7 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
.card-list-header {
|
.card-list-header {
|
||||||
margin: -17px -16px 0 -16px;
|
margin: -17px -16px 0 -15px;
|
||||||
padding: 16px 16px 12px 16px;
|
padding: 16px 16px 12px 16px;
|
||||||
position: fixed;
|
position: fixed;
|
||||||
background: var(--color-fill-2);
|
background: var(--color-fill-2);
|
||||||
@@ -165,7 +168,7 @@
|
|||||||
transition: none;
|
transition: none;
|
||||||
|
|
||||||
&-wrapper {
|
&-wrapper {
|
||||||
background: var(--color-bg-4);
|
background: var(--color-bg-2);
|
||||||
padding: 0 12px;
|
padding: 0 12px;
|
||||||
border-radius: 4px;
|
border-radius: 4px;
|
||||||
|
|
||||||
|
|||||||
@@ -10,8 +10,8 @@
|
|||||||
:hoverable="true"
|
:hoverable="true"
|
||||||
:body-style="cardBodyStyle as Record<string, any>"
|
:body-style="cardBodyStyle as Record<string, any>"
|
||||||
@contextmenu.prevent="() => false"
|
@contextmenu.prevent="() => false"
|
||||||
@click="emits('emitter', CardEmitter.CLICK, item, index)"
|
@click="bubblesEmitter(CardEmitter.CLICK, item, index)"
|
||||||
@dblclick="emits('emitter', CardEmitter.DBL_CLICK, item, index)">
|
@dblclick="bubblesEmitter(CardEmitter.DBL_CLICK, item, index)">
|
||||||
<!-- 标题 -->
|
<!-- 标题 -->
|
||||||
<template #title>
|
<template #title>
|
||||||
<slot name="title" />
|
<slot name="title" />
|
||||||
@@ -83,14 +83,16 @@
|
|||||||
import type { CardRecord } from '@/types/card';
|
import type { CardRecord } from '@/types/card';
|
||||||
import type { CardProps } from '../types/props';
|
import type { CardProps } from '../types/props';
|
||||||
import { CardEmitter } from '../types/emits';
|
import { CardEmitter } from '../types/emits';
|
||||||
|
import useEmitter from '@/hooks/emitter';
|
||||||
|
|
||||||
const props = defineProps<CardProps & {
|
const props = defineProps<CardProps & {
|
||||||
index: number,
|
index: number,
|
||||||
item: CardRecord
|
item: CardRecord
|
||||||
}>();
|
}>();
|
||||||
|
|
||||||
const emits = defineEmits(['emitter']);
|
const emits = defineEmits(['emitter']);
|
||||||
|
|
||||||
|
const { bubblesEmitter } = useEmitter(emits);
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style lang="less" scoped>
|
<style lang="less" scoped>
|
||||||
|
|||||||
@@ -1,8 +1,7 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="card-list-layout">
|
<div class="card-list-layout">
|
||||||
<!-- 头部部分-固定 -->
|
<!-- 头部部分-固定 -->
|
||||||
<card-header v-bind="props"
|
<card-header v-bind="props" @emitter="dispatchEmitter">
|
||||||
@emitter="dispatchEmitter">
|
|
||||||
<!-- 左侧侧操作槽位 -->
|
<!-- 左侧侧操作槽位 -->
|
||||||
<template #leftHandle>
|
<template #leftHandle>
|
||||||
<slot name="leftHandle" />
|
<slot name="leftHandle" />
|
||||||
@@ -80,8 +79,7 @@
|
|||||||
import CardItem from './components/card-item.vue';
|
import CardItem from './components/card-item.vue';
|
||||||
import { Emitter } from './types/emits';
|
import { Emitter } from './types/emits';
|
||||||
import { CardProps } from './types/props';
|
import { CardProps } from './types/props';
|
||||||
|
import useEmitter from '@/hooks/emitter';
|
||||||
const emits = defineEmits(Emitter);
|
|
||||||
|
|
||||||
const props = withDefaults(defineProps<CardProps>(), {
|
const props = withDefaults(defineProps<CardProps>(), {
|
||||||
key: 'id',
|
key: 'id',
|
||||||
@@ -107,10 +105,8 @@
|
|||||||
list: () => []
|
list: () => []
|
||||||
});
|
});
|
||||||
|
|
||||||
// 调度事件
|
const emits = defineEmits(Emitter);
|
||||||
const dispatchEmitter = (event: string, ...args: any) => {
|
const { dispatchEmitter } = useEmitter(emits);
|
||||||
emits(event, ...args);
|
|
||||||
};
|
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
|
|||||||
26
orion-ops-ui/src/hooks/emitter.ts
Normal file
26
orion-ops-ui/src/hooks/emitter.ts
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
const emitter = 'emitter';
|
||||||
|
|
||||||
|
export default function useEmitter(emits: any) {
|
||||||
|
// 事件向上冒泡
|
||||||
|
const bubblesEmitter = (event: string, ...args: any[]) => {
|
||||||
|
if (args) {
|
||||||
|
emits(emitter, event, ...args);
|
||||||
|
} else {
|
||||||
|
emits(emitter, event);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// 处理冒泡事件
|
||||||
|
const dispatchEmitter = (event: string, ...args: any[]) => {
|
||||||
|
if (args) {
|
||||||
|
emits(event, ...args);
|
||||||
|
} else {
|
||||||
|
emits(event);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
return {
|
||||||
|
bubblesEmitter,
|
||||||
|
dispatchEmitter
|
||||||
|
};
|
||||||
|
}
|
||||||
33
orion-ops-ui/src/store/modules/cache/index.ts
vendored
33
orion-ops-ui/src/store/modules/cache/index.ts
vendored
@@ -1,5 +1,8 @@
|
|||||||
import type { CacheState } from './types';
|
import type { CacheState } from './types';
|
||||||
|
import type { AxiosResponse } from 'axios';
|
||||||
import { defineStore } from 'pinia';
|
import { defineStore } from 'pinia';
|
||||||
|
import { getUserList } from '@/api/user/user';
|
||||||
|
import { getRoleList } from '@/api/user/role';
|
||||||
|
|
||||||
export type CacheType = 'users' | 'menus' | 'roles'
|
export type CacheType = 'users' | 'menus' | 'roles'
|
||||||
| 'host' | 'hostGroups' | 'hostTags' | 'hostKeys' | 'hostIdentities'
|
| 'host' | 'hostGroups' | 'hostTags' | 'hostKeys' | 'hostIdentities'
|
||||||
@@ -7,7 +10,6 @@ export type CacheType = 'users' | 'menus' | 'roles'
|
|||||||
|
|
||||||
export default defineStore('cache', {
|
export default defineStore('cache', {
|
||||||
state: (): CacheState => ({
|
state: (): CacheState => ({
|
||||||
users: [],
|
|
||||||
menus: [],
|
menus: [],
|
||||||
roles: [],
|
roles: [],
|
||||||
hosts: [],
|
hosts: [],
|
||||||
@@ -29,13 +31,40 @@ export default defineStore('cache', {
|
|||||||
// 清空
|
// 清空
|
||||||
reset(...names: CacheType[]) {
|
reset(...names: CacheType[]) {
|
||||||
for (let name of names) {
|
for (let name of names) {
|
||||||
this[name] = [];
|
this[name] = undefined;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
// 清除全部
|
// 清除全部
|
||||||
clear() {
|
clear() {
|
||||||
this.$reset();
|
this.$reset();
|
||||||
|
},
|
||||||
|
|
||||||
|
// 加载数据
|
||||||
|
async load<T>(name: CacheType, loader: () => Promise<AxiosResponse<T>>, onErrorValue = []) {
|
||||||
|
// 尝试直接从缓存中获取数据
|
||||||
|
if (this[name]) {
|
||||||
|
return this[name] as T;
|
||||||
|
}
|
||||||
|
// 加载数据
|
||||||
|
try {
|
||||||
|
const { data } = await loader();
|
||||||
|
this[name] = data;
|
||||||
|
return this[name] as T;
|
||||||
|
} catch (e) {
|
||||||
|
return onErrorValue as T;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
// 获取用户列表
|
||||||
|
async loadUsers() {
|
||||||
|
return await this.load('users', getUserList);
|
||||||
|
},
|
||||||
|
|
||||||
|
// 获取角色列表
|
||||||
|
async loadRoles() {
|
||||||
|
return await this.load('roles', getRoleList);
|
||||||
|
},
|
||||||
|
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
18
orion-ops-ui/src/store/modules/cache/types.ts
vendored
18
orion-ops-ui/src/store/modules/cache/types.ts
vendored
@@ -9,15 +9,15 @@ import type { HostIdentityQueryResponse } from '@/api/asset/host-identity';
|
|||||||
import type { DictKeyQueryResponse } from '@/api/system/dict-key';
|
import type { DictKeyQueryResponse } from '@/api/system/dict-key';
|
||||||
|
|
||||||
export interface CacheState {
|
export interface CacheState {
|
||||||
users: UserQueryResponse[];
|
users?: UserQueryResponse[];
|
||||||
menus: MenuQueryResponse[];
|
menus?: MenuQueryResponse[];
|
||||||
roles: RoleQueryResponse[];
|
roles?: RoleQueryResponse[];
|
||||||
hostTags: TagQueryResponse[];
|
hostTags?: TagQueryResponse[];
|
||||||
hosts: HostQueryResponse[];
|
hosts?: HostQueryResponse[];
|
||||||
hostGroups: HostGroupQueryResponse[];
|
hostGroups?: HostGroupQueryResponse[];
|
||||||
hostKeys: HostKeyQueryResponse[];
|
hostKeys?: HostKeyQueryResponse[];
|
||||||
hostIdentities: HostIdentityQueryResponse[];
|
hostIdentities?: HostIdentityQueryResponse[];
|
||||||
dictKeys: DictKeyQueryResponse[];
|
dictKeys?: DictKeyQueryResponse[];
|
||||||
|
|
||||||
[key: string]: unknown;
|
[key: string]: unknown;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,3 +1,6 @@
|
|||||||
|
// 添加事件监听器
|
||||||
|
import { Ref } from 'vue';
|
||||||
|
|
||||||
export function addEventListen(
|
export function addEventListen(
|
||||||
target: Window | HTMLElement,
|
target: Window | HTMLElement,
|
||||||
event: string,
|
event: string,
|
||||||
@@ -12,6 +15,7 @@ export function addEventListen(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 移除事件监听器
|
||||||
export function removeEventListen(
|
export function removeEventListen(
|
||||||
target: Window | HTMLElement,
|
target: Window | HTMLElement,
|
||||||
event: string,
|
event: string,
|
||||||
@@ -25,3 +29,13 @@ export function removeEventListen(
|
|||||||
target.removeEventListener(event, handler, capture);
|
target.removeEventListener(event, handler, capture);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 触发鼠标事件
|
||||||
|
export const triggerMouseEvent = (ref: Ref, e = 'click') => {
|
||||||
|
const event = new MouseEvent(e, {
|
||||||
|
view: window,
|
||||||
|
bubbles: true,
|
||||||
|
cancelable: true,
|
||||||
|
});
|
||||||
|
ref.value.dispatchEvent(event);
|
||||||
|
};
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
import type { Ref } from 'vue';
|
|
||||||
import { Md5 } from 'ts-md5';
|
import { Md5 } from 'ts-md5';
|
||||||
|
|
||||||
type TargetContext = '_self' | '_parent' | '_blank' | '_top';
|
type TargetContext = '_self' | '_parent' | '_blank' | '_top';
|
||||||
@@ -31,18 +30,6 @@ export const regexUrl = new RegExp(
|
|||||||
'i'
|
'i'
|
||||||
);
|
);
|
||||||
|
|
||||||
/**
|
|
||||||
* 触发鼠标事件
|
|
||||||
*/
|
|
||||||
export const triggerMouseEvent = (ref: Ref, e = 'click') => {
|
|
||||||
const event = new MouseEvent(e, {
|
|
||||||
view: window,
|
|
||||||
bubbles: true,
|
|
||||||
cancelable: true,
|
|
||||||
});
|
|
||||||
ref.value.dispatchEvent(event);
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* md5
|
* md5
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -31,7 +31,6 @@
|
|||||||
import type { TabRouterItem } from '@/components/view/tab-router/types';
|
import type { TabRouterItem } from '@/components/view/tab-router/types';
|
||||||
import { computed, onMounted, ref } from 'vue';
|
import { computed, onMounted, ref } from 'vue';
|
||||||
import { useCacheStore } from '@/store';
|
import { useCacheStore } from '@/store';
|
||||||
import { getRoleList } from '@/api/user/role';
|
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
|
|
||||||
@@ -59,9 +58,14 @@
|
|||||||
const loadRoleList = async () => {
|
const loadRoleList = async () => {
|
||||||
setLoading(true);
|
setLoading(true);
|
||||||
try {
|
try {
|
||||||
const { data } = await getRoleList();
|
const roles = await cacheStore.loadRoles();
|
||||||
// 设置到缓存
|
rolesRouter.value = roles.map(s => {
|
||||||
cacheStore.set('roles', data);
|
return {
|
||||||
|
key: s.id,
|
||||||
|
text: `${s.name} (${s.code})`,
|
||||||
|
code: s.code
|
||||||
|
};
|
||||||
|
});
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
Message.error('角色列表加载失败');
|
Message.error('角色列表加载失败');
|
||||||
} finally {
|
} finally {
|
||||||
@@ -69,18 +73,9 @@
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// 加载主机
|
// 加载角色列表
|
||||||
onMounted(async () => {
|
onMounted(() => {
|
||||||
if (!cacheStore.roles.length) {
|
loadRoleList();
|
||||||
await loadRoleList();
|
|
||||||
}
|
|
||||||
rolesRouter.value = cacheStore.roles.map(s => {
|
|
||||||
return {
|
|
||||||
key: s.id,
|
|
||||||
text: `${s.name} (${s.code})`,
|
|
||||||
code: s.code
|
|
||||||
};
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -31,7 +31,6 @@
|
|||||||
import type { TabRouterItem } from '@/components/view/tab-router/types';
|
import type { TabRouterItem } from '@/components/view/tab-router/types';
|
||||||
import { computed, onMounted, ref } from 'vue';
|
import { computed, onMounted, ref } from 'vue';
|
||||||
import { useCacheStore } from '@/store';
|
import { useCacheStore } from '@/store';
|
||||||
import { getUserList } from '@/api/user/user';
|
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
|
|
||||||
@@ -59,9 +58,13 @@
|
|||||||
const loadUserList = async () => {
|
const loadUserList = async () => {
|
||||||
setLoading(true);
|
setLoading(true);
|
||||||
try {
|
try {
|
||||||
const { data } = await getUserList();
|
const users = await cacheStore.loadUsers();
|
||||||
// 设置到缓存
|
usersRouter.value = users.map(s => {
|
||||||
cacheStore.set('users', data);
|
return {
|
||||||
|
key: s.id,
|
||||||
|
text: `${s.nickname} (${s.username})`
|
||||||
|
};
|
||||||
|
});
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
Message.error('用户列表加载失败');
|
Message.error('用户列表加载失败');
|
||||||
} finally {
|
} finally {
|
||||||
@@ -69,17 +72,9 @@
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// 加载主机
|
// 加载用户列表
|
||||||
onMounted(async () => {
|
onMounted(() => {
|
||||||
if (!cacheStore.users.length) {
|
loadUserList();
|
||||||
await loadUserList();
|
|
||||||
}
|
|
||||||
usersRouter.value = cacheStore.users.map(s => {
|
|
||||||
return {
|
|
||||||
key: s.id,
|
|
||||||
text: `${s.nickname} (${s.username})`
|
|
||||||
};
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -69,7 +69,7 @@
|
|||||||
import { reactive, ref } from 'vue';
|
import { reactive, ref } from 'vue';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
import { useDictStore } from '@/store';
|
import { useDictStore } from '@/store';
|
||||||
import UserSelector from '@/components/user/role/user-selector.vue';
|
import UserSelector from '@/components/user/user/user-selector.vue';
|
||||||
import { operatorLogModuleKey, operatorLogTypeKey, operatorRiskLevelKey, operatorLogResultKey } from '../types/const';
|
import { operatorLogModuleKey, operatorLogTypeKey, operatorRiskLevelKey, operatorLogResultKey } from '../types/const';
|
||||||
import { labelFilter } from '@/types/form';
|
import { labelFilter } from '@/types/form';
|
||||||
|
|
||||||
|
|||||||
@@ -34,7 +34,6 @@
|
|||||||
import { ref, onBeforeMount, onUnmounted } from 'vue';
|
import { ref, onBeforeMount, onUnmounted } from 'vue';
|
||||||
import { useCacheStore, useDictStore } from '@/store';
|
import { useCacheStore, useDictStore } from '@/store';
|
||||||
import { dictKeys } from './types/const';
|
import { dictKeys } from './types/const';
|
||||||
import { getUserList } from '@/api/user/user';
|
|
||||||
import OperatorLogQueryHeader from './components/operator-log-query-header.vue';
|
import OperatorLogQueryHeader from './components/operator-log-query-header.vue';
|
||||||
import OperatorLogTable from './components/operator-log-table.vue';
|
import OperatorLogTable from './components/operator-log-table.vue';
|
||||||
import JsonViewModal from '@/components/view/json/json-view-modal.vue';
|
import JsonViewModal from '@/components/view/json/json-view-modal.vue';
|
||||||
@@ -45,18 +44,10 @@
|
|||||||
const table = ref();
|
const table = ref();
|
||||||
const view = ref();
|
const view = ref();
|
||||||
|
|
||||||
// 加载全部用户列表
|
|
||||||
const fetchUserList = async () => {
|
|
||||||
const { data } = await getUserList();
|
|
||||||
cacheStore.set('users', data);
|
|
||||||
};
|
|
||||||
|
|
||||||
onBeforeMount(async () => {
|
onBeforeMount(async () => {
|
||||||
// 加载字典值
|
// 加载字典值
|
||||||
const dictStore = useDictStore();
|
const dictStore = useDictStore();
|
||||||
await dictStore.loadKeys(dictKeys);
|
await dictStore.loadKeys(dictKeys);
|
||||||
// 加载用户列表
|
|
||||||
await fetchUserList();
|
|
||||||
render.value = true;
|
render.value = true;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -29,7 +29,7 @@
|
|||||||
</a-form-item>
|
</a-form-item>
|
||||||
<!-- 角色 -->
|
<!-- 角色 -->
|
||||||
<a-form-item field="roles" label="角色">
|
<a-form-item field="roles" label="角色">
|
||||||
<user-role-selector v-model="formModel.roleIdList"
|
<role-selector v-model="formModel.roleIdList"
|
||||||
:loading="roleLoading"
|
:loading="roleLoading"
|
||||||
:multiple="true" />
|
:multiple="true" />
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
@@ -50,8 +50,7 @@
|
|||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
import useVisible from '@/hooks/visible';
|
import useVisible from '@/hooks/visible';
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
import UserRoleSelector from '@/components/user/role/user-role-selector.vue';
|
import RoleSelector from '@/components/user/role/role-selector.vue';
|
||||||
import { getRoleList } from '@/api/user/role';
|
|
||||||
import { useCacheStore } from '@/store';
|
import { useCacheStore } from '@/store';
|
||||||
import { getUserRoleIdList, grantUserRole } from '@/api/user/user';
|
import { getUserRoleIdList, grantUserRole } from '@/api/user/user';
|
||||||
|
|
||||||
@@ -84,11 +83,6 @@
|
|||||||
const loadRoles = async () => {
|
const loadRoles = async () => {
|
||||||
try {
|
try {
|
||||||
setRoleLoading(true);
|
setRoleLoading(true);
|
||||||
// 获取全部角色
|
|
||||||
if (!cacheStore.roles?.length) {
|
|
||||||
const { data } = await getRoleList();
|
|
||||||
cacheStore.set('roles', data);
|
|
||||||
}
|
|
||||||
// 加载用户角色
|
// 加载用户角色
|
||||||
const { data: roleIdList } = await getUserRoleIdList(formModel.value.id as number);
|
const { data: roleIdList } = await getUserRoleIdList(formModel.value.id as number);
|
||||||
formModel.value.roleIdList = roleIdList;
|
formModel.value.roleIdList = roleIdList;
|
||||||
|
|||||||
@@ -39,6 +39,7 @@
|
|||||||
const grantRoleModal = ref();
|
const grantRoleModal = ref();
|
||||||
|
|
||||||
onBeforeMount(async () => {
|
onBeforeMount(async () => {
|
||||||
|
// 加载字典值
|
||||||
const dictStore = useDictStore();
|
const dictStore = useDictStore();
|
||||||
await dictStore.loadKeys(dictKeys);
|
await dictStore.loadKeys(dictKeys);
|
||||||
render.value = true;
|
render.value = true;
|
||||||
|
|||||||
Reference in New Issue
Block a user