Commit 215d8bab380728164d7fe2958c2d2d1151fce892

Authored by Vben
1 parent 700306bb

refactor: refactor store

Showing 80 changed files with 1546 additions and 1497 deletions
build/generate/generateModifyVars.ts
@@ -28,6 +28,7 @@ export function generateModifyVars(dark = false) { @@ -28,6 +28,7 @@ export function generateModifyVars(dark = false) {
28 'success-color': '#55D187', // Success color 28 'success-color': '#55D187', // Success color
29 'error-color': '#ED6F6F', // False color 29 'error-color': '#ED6F6F', // False color
30 'warning-color': '#EFBD47', // Warning color 30 'warning-color': '#EFBD47', // Warning color
  31 + 'border-color-base': '#EEEEEE',
31 'font-size-base': '14px', // Main font size 32 'font-size-base': '14px', // Main font size
32 'border-radius-base': '2px', // Component/float fillet 33 'border-radius-base': '2px', // Component/float fillet
33 'link-color': primary, // Link color 34 'link-color': primary, // Link color
index.html
@@ -16,9 +16,11 @@ @@ -16,9 +16,11 @@
16 <script> 16 <script>
17 (() => { 17 (() => {
18 var htmlRoot = document.getElementById('htmlRoot'); 18 var htmlRoot = document.getElementById('htmlRoot');
19 - const theme = window.localStorage.getItem('__APP__DARK__MODE__');  
20 - if (!htmlRoot || !theme) return;  
21 - htmlRoot.setAttribute('data-theme', theme); 19 + var theme = window.localStorage.getItem('__APP__DARK__MODE__');
  20 + if (htmlRoot && theme) {
  21 + htmlRoot.setAttribute('data-theme', theme);
  22 + theme = htmlRoot = null;
  23 + }
22 })(); 24 })();
23 </script> 25 </script>
24 <div id="app"> 26 <div id="app">
package.json
@@ -32,7 +32,7 @@ @@ -32,7 +32,7 @@
32 }, 32 },
33 "dependencies": { 33 "dependencies": {
34 "@iconify/iconify": "^2.0.0-rc.6", 34 "@iconify/iconify": "^2.0.0-rc.6",
35 - "@vueuse/core": "^4.8.0", 35 + "@vueuse/core": "^4.8.1",
36 "@zxcvbn-ts/core": "^0.3.0", 36 "@zxcvbn-ts/core": "^0.3.0",
37 "ant-design-vue": "^2.1.2", 37 "ant-design-vue": "^2.1.2",
38 "axios": "^0.21.1", 38 "axios": "^0.21.1",
@@ -43,6 +43,7 @@ @@ -43,6 +43,7 @@
43 "mockjs": "^1.1.0", 43 "mockjs": "^1.1.0",
44 "nprogress": "^0.2.0", 44 "nprogress": "^0.2.0",
45 "path-to-regexp": "^6.2.0", 45 "path-to-regexp": "^6.2.0",
  46 + "pinia": "^2.0.0-alpha.12",
46 "print-js": "^1.6.0", 47 "print-js": "^1.6.0",
47 "qrcode": "^1.4.4", 48 "qrcode": "^1.4.4",
48 "sortablejs": "^1.13.0", 49 "sortablejs": "^1.13.0",
@@ -52,8 +53,6 @@ @@ -52,8 +53,6 @@
52 "vue-i18n": "9.0.0", 53 "vue-i18n": "9.0.0",
53 "vue-router": "^4.0.6", 54 "vue-router": "^4.0.6",
54 "vue-types": "^3.0.2", 55 "vue-types": "^3.0.2",
55 - "vuex": "^4.0.0",  
56 - "vuex-module-decorators": "^1.0.1",  
57 "xlsx": "^0.16.9" 56 "xlsx": "^0.16.9"
58 }, 57 },
59 "devDependencies": { 58 "devDependencies": {
@@ -81,7 +80,7 @@ @@ -81,7 +80,7 @@
81 "conventional-changelog-cli": "^2.1.1", 80 "conventional-changelog-cli": "^2.1.1",
82 "cross-env": "^7.0.3", 81 "cross-env": "^7.0.3",
83 "dotenv": "^8.2.0", 82 "dotenv": "^8.2.0",
84 - "eslint": "^7.23.0", 83 + "eslint": "^7.24.0",
85 "eslint-config-prettier": "^8.1.0", 84 "eslint-config-prettier": "^8.1.0",
86 "eslint-define-config": "^1.0.7", 85 "eslint-define-config": "^1.0.7",
87 "eslint-plugin-prettier": "^3.3.1", 86 "eslint-plugin-prettier": "^3.3.1",
@@ -115,13 +114,14 @@ @@ -115,13 +114,14 @@
115 "vite-plugin-style-import": "^0.9.2", 114 "vite-plugin-style-import": "^0.9.2",
116 "vite-plugin-svg-icons": "^0.4.1", 115 "vite-plugin-svg-icons": "^0.4.1",
117 "vite-plugin-theme": "^0.6.3", 116 "vite-plugin-theme": "^0.6.3",
118 - "vite-plugin-windicss": "0.12.5", 117 + "vite-plugin-windicss": "0.13.1",
119 "vue-eslint-parser": "^7.6.0" 118 "vue-eslint-parser": "^7.6.0"
120 }, 119 },
121 "resolutions": { 120 "resolutions": {
122 "//": "Used to install imagemin dependencies, because imagemin may not be installed in China.If it is abroad, you can delete it", 121 "//": "Used to install imagemin dependencies, because imagemin may not be installed in China.If it is abroad, you can delete it",
123 "bin-wrapper": "npm:bin-wrapper-china", 122 "bin-wrapper": "npm:bin-wrapper-china",
124 - "rollup": "^2.44.0" 123 + "rollup": "^2.45.1",
  124 + "esbuild": "^0.11.6"
125 }, 125 },
126 "repository": { 126 "repository": {
127 "type": "git", 127 "type": "git",
src/components/Application/src/AppProvider.vue
@@ -3,22 +3,24 @@ @@ -3,22 +3,24 @@
3 3
4 import { createAppProviderContext } from './useAppContext'; 4 import { createAppProviderContext } from './useAppContext';
5 5
6 - import designSetting from '/@/settings/designSetting'; 6 + import { prefixCls } from '/@/settings/designSetting';
7 import { createBreakpointListen } from '/@/hooks/event/useBreakpoint'; 7 import { createBreakpointListen } from '/@/hooks/event/useBreakpoint';
8 import { propTypes } from '/@/utils/propTypes'; 8 import { propTypes } from '/@/utils/propTypes';
9 - import { appStore } from '/@/store/modules/app'; 9 + import { useAppStore } from '/@/store/modules/app';
10 import { MenuModeEnum, MenuTypeEnum } from '/@/enums/menuEnum'; 10 import { MenuModeEnum, MenuTypeEnum } from '/@/enums/menuEnum';
11 11
12 export default defineComponent({ 12 export default defineComponent({
13 name: 'AppProvider', 13 name: 'AppProvider',
14 inheritAttrs: false, 14 inheritAttrs: false,
15 props: { 15 props: {
16 - prefixCls: propTypes.string.def(designSetting.prefixCls), 16 + prefixCls: propTypes.string.def(prefixCls),
17 }, 17 },
18 setup(props, { slots }) { 18 setup(props, { slots }) {
19 const isMobile = ref(false); 19 const isMobile = ref(false);
20 const isSetState = ref(false); 20 const isSetState = ref(false);
21 21
  22 + const appStore = useAppStore();
  23 +
22 createBreakpointListen(({ screenMap, sizeEnum, width }) => { 24 createBreakpointListen(({ screenMap, sizeEnum, width }) => {
23 const lgWidth = screenMap.get(sizeEnum.LG); 25 const lgWidth = screenMap.get(sizeEnum.LG);
24 if (lgWidth) { 26 if (lgWidth) {
@@ -42,20 +44,20 @@ @@ -42,20 +44,20 @@
42 split: menuSplit, 44 split: menuSplit,
43 }, 45 },
44 } = appStore.getProjectConfig; 46 } = appStore.getProjectConfig;
45 - appStore.commitProjectConfigState({ 47 + appStore.setProjectConfig({
46 menuSetting: { 48 menuSetting: {
47 type: MenuTypeEnum.SIDEBAR, 49 type: MenuTypeEnum.SIDEBAR,
48 mode: MenuModeEnum.INLINE, 50 mode: MenuModeEnum.INLINE,
49 split: false, 51 split: false,
50 }, 52 },
51 }); 53 });
52 - appStore.commitBeforeMiniState({ menuMode, menuCollapsed, menuType, menuSplit }); 54 + appStore.setBeforeMiniInfo({ menuMode, menuCollapsed, menuType, menuSplit });
53 } 55 }
54 } else { 56 } else {
55 if (unref(isSetState)) { 57 if (unref(isSetState)) {
56 isSetState.value = false; 58 isSetState.value = false;
57 - const { menuMode, menuCollapsed, menuType, menuSplit } = appStore.getBeforeMiniState;  
58 - appStore.commitProjectConfigState({ 59 + const { menuMode, menuCollapsed, menuType, menuSplit } = appStore.getBeforeMiniInfo;
  60 + appStore.setProjectConfig({
59 menuSetting: { 61 menuSetting: {
60 type: menuType, 62 type: menuType,
61 mode: menuMode, 63 mode: menuMode,
src/components/Application/src/search/AppSearchKeyItem.vue
1 <template> 1 <template>
2 <span :class="$attrs.class"> 2 <span :class="$attrs.class">
3 - <Icon :icon="icon" /> 3 + <g-icon :icon="icon" />
4 </span> 4 </span>
5 </template> 5 </template>
6 <script lang="ts"> 6 <script lang="ts">
7 import { defineComponent } from 'vue'; 7 import { defineComponent } from 'vue';
8 - import { Icon } from '/@/components/Icon';  
9 - import { propTypes } from '/@/utils/propTypes';  
10 -  
11 export default defineComponent({ 8 export default defineComponent({
12 - components: { Icon },  
13 props: { 9 props: {
14 - icon: propTypes.string, 10 + icon: String,
15 }, 11 },
16 }); 12 });
17 </script> 13 </script>
src/components/SimpleMenu/src/SimpleMenu.vue
@@ -6,7 +6,6 @@ @@ -6,7 +6,6 @@
6 :class="prefixCls" 6 :class="prefixCls"
7 :activeSubMenuNames="activeSubMenuNames" 7 :activeSubMenuNames="activeSubMenuNames"
8 @select="handleSelect" 8 @select="handleSelect"
9 - @open-change="handleOpenChange"  
10 > 9 >
11 <template v-for="item in items" :key="item.path"> 10 <template v-for="item in items" :key="item.path">
12 <SimpleSubMenu 11 <SimpleSubMenu
@@ -140,17 +139,11 @@ @@ -140,17 +139,11 @@
140 menuState.activeName = key; 139 menuState.activeName = key;
141 } 140 }
142 141
143 - function handleOpenChange(v) {  
144 - console.log('======================');  
145 - console.log(v);  
146 - console.log('======================');  
147 - }  
148 return { 142 return {
149 prefixCls, 143 prefixCls,
150 getBindValues, 144 getBindValues,
151 handleSelect, 145 handleSelect,
152 getOpenKeys, 146 getOpenKeys,
153 - handleOpenChange,  
154 ...toRefs(menuState), 147 ...toRefs(menuState),
155 }; 148 };
156 }, 149 },
src/hooks/setting/useHeaderSetting.ts
@@ -2,94 +2,89 @@ import type { HeaderSetting } from &#39;/#/config&#39;; @@ -2,94 +2,89 @@ import type { HeaderSetting } from &#39;/#/config&#39;;
2 2
3 import { computed, unref } from 'vue'; 3 import { computed, unref } from 'vue';
4 4
5 -import { appStore } from '/@/store/modules/app'; 5 +import { useAppStore } from '/@/store/modules/app';
6 6
7 import { useMenuSetting } from '/@/hooks/setting/useMenuSetting'; 7 import { useMenuSetting } from '/@/hooks/setting/useMenuSetting';
8 import { useRootSetting } from '/@/hooks/setting/useRootSetting'; 8 import { useRootSetting } from '/@/hooks/setting/useRootSetting';
9 import { useFullContent } from '/@/hooks/web/useFullContent'; 9 import { useFullContent } from '/@/hooks/web/useFullContent';
10 -  
11 import { MenuModeEnum } from '/@/enums/menuEnum'; 10 import { MenuModeEnum } from '/@/enums/menuEnum';
12 11
13 -const { getFullContent } = useFullContent();  
14 -const {  
15 - getMenuMode,  
16 - getSplit,  
17 - getShowHeaderTrigger,  
18 - getIsSidebarType,  
19 - getIsMixSidebar,  
20 - getIsTopMenu,  
21 -} = useMenuSetting();  
22 -const { getShowBreadCrumb, getShowLogo } = useRootSetting();  
23 -  
24 -const getShowMixHeaderRef = computed(() => !unref(getIsSidebarType) && unref(getShowHeader)); 12 +export function useHeaderSetting() {
  13 + const { getFullContent } = useFullContent();
  14 + const appStore = useAppStore();
25 15
26 -const getShowFullHeaderRef = computed(() => {  
27 - return (  
28 - !unref(getFullContent) &&  
29 - unref(getShowMixHeaderRef) &&  
30 - unref(getShowHeader) &&  
31 - !unref(getIsTopMenu) &&  
32 - !unref(getIsMixSidebar)  
33 - );  
34 -}); 16 + const getShowFullHeaderRef = computed(() => {
  17 + return (
  18 + !unref(getFullContent) &&
  19 + unref(getShowMixHeaderRef) &&
  20 + unref(getShowHeader) &&
  21 + !unref(getIsTopMenu) &&
  22 + !unref(getIsMixSidebar)
  23 + );
  24 + });
35 25
36 -const getShowInsetHeaderRef = computed(() => {  
37 - const need = !unref(getFullContent) && unref(getShowHeader);  
38 - return (  
39 - (need && !unref(getShowMixHeaderRef)) ||  
40 - (need && unref(getIsTopMenu)) ||  
41 - (need && unref(getIsMixSidebar))  
42 - );  
43 -}); 26 + const getUnFixedAndFull = computed(() => !unref(getFixed) && !unref(getShowFullHeaderRef));
44 27
45 -// Get header configuration  
46 -const getHeaderSetting = computed(() => appStore.getProjectConfig.headerSetting); 28 + const getShowInsetHeaderRef = computed(() => {
  29 + const need = !unref(getFullContent) && unref(getShowHeader);
  30 + return (
  31 + (need && !unref(getShowMixHeaderRef)) ||
  32 + (need && unref(getIsTopMenu)) ||
  33 + (need && unref(getIsMixSidebar))
  34 + );
  35 + });
47 36
48 -const getShowDoc = computed(() => unref(getHeaderSetting).showDoc); 37 + const {
  38 + getMenuMode,
  39 + getSplit,
  40 + getShowHeaderTrigger,
  41 + getIsSidebarType,
  42 + getIsMixSidebar,
  43 + getIsTopMenu,
  44 + } = useMenuSetting();
  45 + const { getShowBreadCrumb, getShowLogo } = useRootSetting();
49 46
50 -const getHeaderTheme = computed(() => unref(getHeaderSetting).theme); 47 + const getShowMixHeaderRef = computed(() => !unref(getIsSidebarType) && unref(getShowHeader));
51 48
52 -const getShowHeader = computed(() => unref(getHeaderSetting).show); 49 + const getShowDoc = computed(() => appStore.getHeaderSetting.showDoc);
53 50
54 -const getFixed = computed(() => unref(getHeaderSetting).fixed); 51 + const getHeaderTheme = computed(() => appStore.getHeaderSetting.theme);
55 52
56 -const getHeaderBgColor = computed(() => unref(getHeaderSetting).bgColor); 53 + const getShowHeader = computed(() => appStore.getHeaderSetting.show);
57 54
58 -const getShowSearch = computed(() => unref(getHeaderSetting).showSearch); 55 + const getFixed = computed(() => appStore.getHeaderSetting.fixed);
59 56
60 -const getUseLockPage = computed(() => unref(getHeaderSetting).useLockPage); 57 + const getHeaderBgColor = computed(() => appStore.getHeaderSetting.bgColor);
61 58
62 -const getShowFullScreen = computed(() => unref(getHeaderSetting).showFullScreen); 59 + const getShowSearch = computed(() => appStore.getHeaderSetting.showSearch);
63 60
64 -const getShowNotice = computed(() => unref(getHeaderSetting).showNotice); 61 + const getUseLockPage = computed(() => appStore.getHeaderSetting.useLockPage);
65 62
66 -const getUnFixedAndFull = computed(() => !unref(getFixed) && !unref(getShowFullHeaderRef)); 63 + const getShowFullScreen = computed(() => appStore.getHeaderSetting.showFullScreen);
67 64
68 -const getShowBread = computed(() => {  
69 - return (  
70 - unref(getMenuMode) !== MenuModeEnum.HORIZONTAL && unref(getShowBreadCrumb) && !unref(getSplit)  
71 - );  
72 -}); 65 + const getShowNotice = computed(() => appStore.getHeaderSetting.showNotice);
73 66
74 -const getShowHeaderLogo = computed(() => {  
75 - return unref(getShowLogo) && !unref(getIsSidebarType) && !unref(getIsMixSidebar);  
76 -}); 67 + const getShowBread = computed(() => {
  68 + return (
  69 + unref(getMenuMode) !== MenuModeEnum.HORIZONTAL && unref(getShowBreadCrumb) && !unref(getSplit)
  70 + );
  71 + });
77 72
78 -const getShowContent = computed(() => {  
79 - return unref(getShowBread) || unref(getShowHeaderTrigger);  
80 -}); 73 + const getShowHeaderLogo = computed(() => {
  74 + return unref(getShowLogo) && !unref(getIsSidebarType) && !unref(getIsMixSidebar);
  75 + });
81 76
82 -// Set header configuration  
83 -function setHeaderSetting(headerSetting: Partial<HeaderSetting>): void {  
84 - appStore.commitProjectConfigState({ headerSetting });  
85 -} 77 + const getShowContent = computed(() => {
  78 + return unref(getShowBread) || unref(getShowHeaderTrigger);
  79 + });
86 80
87 -export function useHeaderSetting() { 81 + // Set header configuration
  82 + function setHeaderSetting(headerSetting: Partial<HeaderSetting>) {
  83 + appStore.setProjectConfig({ headerSetting });
  84 + }
88 return { 85 return {
89 setHeaderSetting, 86 setHeaderSetting,
90 87
91 - getHeaderSetting,  
92 -  
93 getShowDoc, 88 getShowDoc,
94 getShowSearch, 89 getShowSearch,
95 getHeaderTheme, 90 getHeaderTheme,
src/hooks/setting/useMenuSetting.ts
@@ -2,7 +2,7 @@ import type { MenuSetting } from &#39;/#/config&#39;; @@ -2,7 +2,7 @@ import type { MenuSetting } from &#39;/#/config&#39;;
2 2
3 import { computed, unref, ref } from 'vue'; 3 import { computed, unref, ref } from 'vue';
4 4
5 -import { appStore } from '/@/store/modules/app'; 5 +import { useAppStore } from '/@/store/modules/app';
6 6
7 import { SIDE_BAR_MINI_WIDTH, SIDE_BAR_SHOW_TIT_MINI_WIDTH } from '/@/enums/appEnum'; 7 import { SIDE_BAR_MINI_WIDTH, SIDE_BAR_SHOW_TIT_MINI_WIDTH } from '/@/enums/appEnum';
8 import { MenuModeEnum, MenuTypeEnum, TriggerEnum } from '/@/enums/menuEnum'; 8 import { MenuModeEnum, MenuTypeEnum, TriggerEnum } from '/@/enums/menuEnum';
@@ -10,127 +10,129 @@ import { useFullContent } from &#39;/@/hooks/web/useFullContent&#39;; @@ -10,127 +10,129 @@ import { useFullContent } from &#39;/@/hooks/web/useFullContent&#39;;
10 10
11 const mixSideHasChildren = ref(false); 11 const mixSideHasChildren = ref(false);
12 12
13 -// Get menu configuration  
14 -const getMenuSetting = computed(() => appStore.getProjectConfig.menuSetting); 13 +export function useMenuSetting() {
  14 + const { getFullContent: fullContent } = useFullContent();
  15 + const appStore = useAppStore();
  16 +
  17 + const getShowSidebar = computed(() => {
  18 + return (
  19 + unref(getSplit) ||
  20 + (unref(getShowMenu) && unref(getMenuMode) !== MenuModeEnum.HORIZONTAL && !unref(fullContent))
  21 + );
  22 + });
15 23
16 -const getCollapsed = computed(() => unref(getMenuSetting).collapsed); 24 + const getCollapsed = computed(() => appStore.getMenuSetting.collapsed);
17 25
18 -const getMenuType = computed(() => unref(getMenuSetting).type); 26 + const getMenuType = computed(() => appStore.getMenuSetting.type);
19 27
20 -const getMenuMode = computed(() => unref(getMenuSetting).mode); 28 + const getMenuMode = computed(() => appStore.getMenuSetting.mode);
21 29
22 -const getMenuFixed = computed(() => unref(getMenuSetting).fixed); 30 + const getMenuFixed = computed(() => appStore.getMenuSetting.fixed);
23 31
24 -const getShowMenu = computed(() => unref(getMenuSetting).show); 32 + const getShowMenu = computed(() => appStore.getMenuSetting.show);
25 33
26 -const getMenuHidden = computed(() => unref(getMenuSetting).hidden); 34 + const getMenuHidden = computed(() => appStore.getMenuSetting.hidden);
27 35
28 -const getMenuWidth = computed(() => unref(getMenuSetting).menuWidth); 36 + const getMenuWidth = computed(() => appStore.getMenuSetting.menuWidth);
29 37
30 -const getTrigger = computed(() => unref(getMenuSetting).trigger); 38 + const getTrigger = computed(() => appStore.getMenuSetting.trigger);
31 39
32 -const getMenuTheme = computed(() => unref(getMenuSetting).theme); 40 + const getMenuTheme = computed(() => appStore.getMenuSetting.theme);
33 41
34 -const getSplit = computed(() => unref(getMenuSetting).split); 42 + const getSplit = computed(() => appStore.getMenuSetting.split);
35 43
36 -const getMenuBgColor = computed(() => unref(getMenuSetting).bgColor); 44 + const getMenuBgColor = computed(() => appStore.getMenuSetting.bgColor);
37 45
38 -const getMixSideTrigger = computed(() => unref(getMenuSetting).mixSideTrigger); 46 + const getMixSideTrigger = computed(() => appStore.getMenuSetting.mixSideTrigger);
39 47
40 -const getCanDrag = computed(() => unref(getMenuSetting).canDrag); 48 + const getCanDrag = computed(() => appStore.getMenuSetting.canDrag);
41 49
42 -const getAccordion = computed(() => unref(getMenuSetting).accordion); 50 + const getAccordion = computed(() => appStore.getMenuSetting.accordion);
43 51
44 -const getMixSideFixed = computed(() => unref(getMenuSetting).mixSideFixed); 52 + const getMixSideFixed = computed(() => appStore.getMenuSetting.mixSideFixed);
45 53
46 -const getTopMenuAlign = computed(() => unref(getMenuSetting).topMenuAlign); 54 + const getTopMenuAlign = computed(() => appStore.getMenuSetting.topMenuAlign);
47 55
48 -const getCloseMixSidebarOnChange = computed(() => unref(getMenuSetting).closeMixSidebarOnChange); 56 + const getCloseMixSidebarOnChange = computed(
  57 + () => appStore.getMenuSetting.closeMixSidebarOnChange
  58 + );
49 59
50 -const getIsSidebarType = computed(() => unref(getMenuType) === MenuTypeEnum.SIDEBAR); 60 + const getIsSidebarType = computed(() => unref(getMenuType) === MenuTypeEnum.SIDEBAR);
51 61
52 -const getIsTopMenu = computed(() => unref(getMenuType) === MenuTypeEnum.TOP_MENU); 62 + const getIsTopMenu = computed(() => unref(getMenuType) === MenuTypeEnum.TOP_MENU);
53 63
54 -const getCollapsedShowTitle = computed(() => unref(getMenuSetting).collapsedShowTitle); 64 + const getCollapsedShowTitle = computed(() => appStore.getMenuSetting.collapsedShowTitle);
55 65
56 -const getShowTopMenu = computed(() => {  
57 - return unref(getMenuMode) === MenuModeEnum.HORIZONTAL || unref(getSplit);  
58 -}); 66 + const getShowTopMenu = computed(() => {
  67 + return unref(getMenuMode) === MenuModeEnum.HORIZONTAL || unref(getSplit);
  68 + });
59 69
60 -const getShowHeaderTrigger = computed(() => {  
61 - if (unref(getMenuType) === MenuTypeEnum.TOP_MENU || !unref(getShowMenu) || unref(getMenuHidden)) {  
62 - return false;  
63 - } 70 + const getShowHeaderTrigger = computed(() => {
  71 + if (
  72 + unref(getMenuType) === MenuTypeEnum.TOP_MENU ||
  73 + !unref(getShowMenu) ||
  74 + unref(getMenuHidden)
  75 + ) {
  76 + return false;
  77 + }
64 78
65 - return unref(getTrigger) === TriggerEnum.HEADER;  
66 -}); 79 + return unref(getTrigger) === TriggerEnum.HEADER;
  80 + });
67 81
68 -const getIsHorizontal = computed(() => {  
69 - return unref(getMenuMode) === MenuModeEnum.HORIZONTAL;  
70 -}); 82 + const getIsHorizontal = computed(() => {
  83 + return unref(getMenuMode) === MenuModeEnum.HORIZONTAL;
  84 + });
71 85
72 -const getIsMixSidebar = computed(() => {  
73 - return unref(getMenuType) === MenuTypeEnum.MIX_SIDEBAR;  
74 -}); 86 + const getIsMixSidebar = computed(() => {
  87 + return unref(getMenuType) === MenuTypeEnum.MIX_SIDEBAR;
  88 + });
75 89
76 -const getIsMixMode = computed(() => {  
77 - return unref(getMenuMode) === MenuModeEnum.INLINE && unref(getMenuType) === MenuTypeEnum.MIX;  
78 -}); 90 + const getIsMixMode = computed(() => {
  91 + return unref(getMenuMode) === MenuModeEnum.INLINE && unref(getMenuType) === MenuTypeEnum.MIX;
  92 + });
79 93
80 -const getRealWidth = computed(() => {  
81 - if (unref(getIsMixSidebar)) {  
82 - return unref(getCollapsed) && !unref(getMixSideFixed)  
83 - ? unref(getMiniWidthNumber)  
84 - : unref(getMenuWidth);  
85 - }  
86 - return unref(getCollapsed) ? unref(getMiniWidthNumber) : unref(getMenuWidth);  
87 -});  
88 -  
89 -const getMiniWidthNumber = computed(() => {  
90 - const { collapsedShowTitle } = unref(getMenuSetting);  
91 - return collapsedShowTitle ? SIDE_BAR_SHOW_TIT_MINI_WIDTH : SIDE_BAR_MINI_WIDTH;  
92 -});  
93 -  
94 -const getCalcContentWidth = computed(() => {  
95 - const width =  
96 - unref(getIsTopMenu) || !unref(getShowMenu) || (unref(getSplit) && unref(getMenuHidden))  
97 - ? 0  
98 - : unref(getIsMixSidebar)  
99 - ? (unref(getCollapsed) ? SIDE_BAR_MINI_WIDTH : SIDE_BAR_SHOW_TIT_MINI_WIDTH) +  
100 - (unref(getMixSideFixed) && unref(mixSideHasChildren) ? unref(getRealWidth) : 0)  
101 - : unref(getRealWidth);  
102 -  
103 - return `calc(100% - ${unref(width)}px)`;  
104 -});  
105 -  
106 -const { getFullContent: fullContent } = useFullContent();  
107 -  
108 -const getShowSidebar = computed(() => {  
109 - return (  
110 - unref(getSplit) ||  
111 - (unref(getShowMenu) && unref(getMenuMode) !== MenuModeEnum.HORIZONTAL && !unref(fullContent))  
112 - );  
113 -}); 94 + const getRealWidth = computed(() => {
  95 + if (unref(getIsMixSidebar)) {
  96 + return unref(getCollapsed) && !unref(getMixSideFixed)
  97 + ? unref(getMiniWidthNumber)
  98 + : unref(getMenuWidth);
  99 + }
  100 + return unref(getCollapsed) ? unref(getMiniWidthNumber) : unref(getMenuWidth);
  101 + });
114 102
115 -// Set menu configuration  
116 -function setMenuSetting(menuSetting: Partial<MenuSetting>): void {  
117 - appStore.commitProjectConfigState({ menuSetting });  
118 -} 103 + const getMiniWidthNumber = computed(() => {
  104 + const { collapsedShowTitle } = appStore.getMenuSetting;
  105 + return collapsedShowTitle ? SIDE_BAR_SHOW_TIT_MINI_WIDTH : SIDE_BAR_MINI_WIDTH;
  106 + });
  107 +
  108 + const getCalcContentWidth = computed(() => {
  109 + const width =
  110 + unref(getIsTopMenu) || !unref(getShowMenu) || (unref(getSplit) && unref(getMenuHidden))
  111 + ? 0
  112 + : unref(getIsMixSidebar)
  113 + ? (unref(getCollapsed) ? SIDE_BAR_MINI_WIDTH : SIDE_BAR_SHOW_TIT_MINI_WIDTH) +
  114 + (unref(getMixSideFixed) && unref(mixSideHasChildren) ? unref(getRealWidth) : 0)
  115 + : unref(getRealWidth);
119 116
120 -function toggleCollapsed() {  
121 - setMenuSetting({  
122 - collapsed: !unref(getCollapsed), 117 + return `calc(100% - ${unref(width)}px)`;
123 }); 118 });
124 -}  
125 119
126 -export function useMenuSetting() { 120 + // Set menu configuration
  121 + function setMenuSetting(menuSetting: Partial<MenuSetting>): void {
  122 + appStore.setProjectConfig({ menuSetting });
  123 + }
  124 +
  125 + function toggleCollapsed() {
  126 + setMenuSetting({
  127 + collapsed: !unref(getCollapsed),
  128 + });
  129 + }
127 return { 130 return {
128 setMenuSetting, 131 setMenuSetting,
129 132
130 toggleCollapsed, 133 toggleCollapsed,
131 134
132 getMenuFixed, 135 getMenuFixed,
133 - getMenuSetting,  
134 getRealWidth, 136 getRealWidth,
135 getMenuType, 137 getMenuType,
136 getMenuMode, 138 getMenuMode,
src/hooks/setting/useMultipleTabSetting.ts
1 import type { MultiTabsSetting } from '/#/config'; 1 import type { MultiTabsSetting } from '/#/config';
2 2
3 -import { computed, unref } from 'vue'; 3 +import { computed } from 'vue';
4 4
5 -import { appStore } from '/@/store/modules/app'; 5 +import { useAppStore } from '/@/store/modules/app';
6 6
7 -const getMultipleTabSetting = computed(() => appStore.getProjectConfig.multiTabsSetting);  
8 -  
9 -const getShowMultipleTab = computed(() => unref(getMultipleTabSetting).show); 7 +export function useMultipleTabSetting() {
  8 + const appStore = useAppStore();
10 9
11 -const getShowQuick = computed(() => unref(getMultipleTabSetting).showQuick); 10 + const getShowMultipleTab = computed(() => appStore.getMultiTabsSetting.show);
12 11
13 -const getShowRedo = computed(() => unref(getMultipleTabSetting).showRedo); 12 + const getShowQuick = computed(() => appStore.getMultiTabsSetting.showQuick);
14 13
15 -const getShowFold = computed(() => unref(getMultipleTabSetting).showFold); 14 + const getShowRedo = computed(() => appStore.getMultiTabsSetting.showRedo);
16 15
17 -function setMultipleTabSetting(multiTabsSetting: Partial<MultiTabsSetting>) {  
18 - appStore.commitProjectConfigState({ multiTabsSetting });  
19 -} 16 + const getShowFold = computed(() => appStore.getMultiTabsSetting.showFold);
20 17
21 -export function useMultipleTabSetting() { 18 + function setMultipleTabSetting(multiTabsSetting: Partial<MultiTabsSetting>) {
  19 + appStore.setProjectConfig({ multiTabsSetting });
  20 + }
22 return { 21 return {
23 setMultipleTabSetting, 22 setMultipleTabSetting,
24 -  
25 - getMultipleTabSetting,  
26 getShowMultipleTab, 23 getShowMultipleTab,
27 getShowQuick, 24 getShowQuick,
28 getShowRedo, 25 getShowRedo,
src/hooks/setting/useRootSetting.ts
1 import type { ProjectConfig } from '/#/config'; 1 import type { ProjectConfig } from '/#/config';
2 2
3 -import { computed, unref } from 'vue'; 3 +import { computed } from 'vue';
4 4
5 -import { appStore } from '/@/store/modules/app';  
6 -import { ContentEnum } from '/@/enums/appEnum';  
7 -import { ThemeEnum } from '../../enums/appEnum'; 5 +import { useAppStore } from '/@/store/modules/app';
  6 +import { ContentEnum, ThemeEnum } from '/@/enums/appEnum';
8 7
9 type RootSetting = Omit< 8 type RootSetting = Omit<
10 ProjectConfig, 9 ProjectConfig,
11 'locale' | 'headerSetting' | 'menuSetting' | 'multiTabsSetting' 10 'locale' | 'headerSetting' | 'menuSetting' | 'multiTabsSetting'
12 >; 11 >;
13 12
14 -const getRootSetting = computed((): RootSetting => appStore.getProjectConfig); 13 +export function useRootSetting() {
  14 + const appStore = useAppStore();
15 15
16 -const getPageLoading = computed(() => appStore.getPageLoading); 16 + const getPageLoading = computed(() => appStore.getPageLoading);
17 17
18 -const getOpenKeepAlive = computed(() => unref(getRootSetting).openKeepAlive); 18 + const getOpenKeepAlive = computed(() => appStore.getProjectConfig.openKeepAlive);
19 19
20 -const getSettingButtonPosition = computed(() => unref(getRootSetting).settingButtonPosition); 20 + const getSettingButtonPosition = computed(() => appStore.getProjectConfig.settingButtonPosition);
21 21
22 -const getCanEmbedIFramePage = computed(() => unref(getRootSetting).canEmbedIFramePage); 22 + const getCanEmbedIFramePage = computed(() => appStore.getProjectConfig.canEmbedIFramePage);
23 23
24 -const getPermissionMode = computed(() => unref(getRootSetting).permissionMode); 24 + const getPermissionMode = computed(() => appStore.getProjectConfig.permissionMode);
25 25
26 -const getShowLogo = computed(() => unref(getRootSetting).showLogo); 26 + const getShowLogo = computed(() => appStore.getProjectConfig.showLogo);
27 27
28 -const getContentMode = computed(() => unref(getRootSetting).contentMode); 28 + const getContentMode = computed(() => appStore.getProjectConfig.contentMode);
29 29
30 -const getUseOpenBackTop = computed(() => unref(getRootSetting).useOpenBackTop); 30 + const getUseOpenBackTop = computed(() => appStore.getProjectConfig.useOpenBackTop);
31 31
32 -const getShowSettingButton = computed(() => unref(getRootSetting).showSettingButton); 32 + const getShowSettingButton = computed(() => appStore.getProjectConfig.showSettingButton);
33 33
34 -const getUseErrorHandle = computed(() => unref(getRootSetting).useErrorHandle); 34 + const getUseErrorHandle = computed(() => appStore.getProjectConfig.useErrorHandle);
35 35
36 -const getShowFooter = computed(() => unref(getRootSetting).showFooter); 36 + const getShowFooter = computed(() => appStore.getProjectConfig.showFooter);
37 37
38 -const getShowBreadCrumb = computed(() => unref(getRootSetting).showBreadCrumb); 38 + const getShowBreadCrumb = computed(() => appStore.getProjectConfig.showBreadCrumb);
39 39
40 -const getThemeColor = computed(() => unref(getRootSetting).themeColor); 40 + const getThemeColor = computed(() => appStore.getProjectConfig.themeColor);
41 41
42 -const getShowBreadCrumbIcon = computed(() => unref(getRootSetting).showBreadCrumbIcon); 42 + const getShowBreadCrumbIcon = computed(() => appStore.getProjectConfig.showBreadCrumbIcon);
43 43
44 -const getFullContent = computed(() => unref(getRootSetting).fullContent); 44 + const getFullContent = computed(() => appStore.getProjectConfig.fullContent);
45 45
46 -const getColorWeak = computed(() => unref(getRootSetting).colorWeak); 46 + const getColorWeak = computed(() => appStore.getProjectConfig.colorWeak);
47 47
48 -const getGrayMode = computed(() => unref(getRootSetting).grayMode); 48 + const getGrayMode = computed(() => appStore.getProjectConfig.grayMode);
49 49
50 -const getLockTime = computed(() => unref(getRootSetting).lockTime); 50 + const getLockTime = computed(() => appStore.getProjectConfig.lockTime);
51 51
52 -const getShowDarkModeToggle = computed(() => unref(getRootSetting).showDarkModeToggle); 52 + const getShowDarkModeToggle = computed(() => appStore.getProjectConfig.showDarkModeToggle);
53 53
54 -const getDarkMode = computed(() => appStore.getDarkMode); 54 + const getDarkMode = computed(() => appStore.getDarkMode);
55 55
56 -const getLayoutContentMode = computed(() =>  
57 - unref(getRootSetting).contentMode === ContentEnum.FULL ? ContentEnum.FULL : ContentEnum.FIXED  
58 -); 56 + const getLayoutContentMode = computed(() =>
  57 + appStore.getProjectConfig.contentMode === ContentEnum.FULL
  58 + ? ContentEnum.FULL
  59 + : ContentEnum.FIXED
  60 + );
59 61
60 -function setRootSetting(setting: Partial<RootSetting>) {  
61 - appStore.commitProjectConfigState(setting);  
62 -} 62 + function setRootSetting(setting: Partial<RootSetting>) {
  63 + appStore.setProjectConfig(setting);
  64 + }
63 65
64 -function setDarkMode(mode: ThemeEnum) {  
65 - appStore.commitDarkMode(mode);  
66 -}  
67 -  
68 -export function useRootSetting() { 66 + function setDarkMode(mode: ThemeEnum) {
  67 + appStore.setDarkMode(mode);
  68 + }
69 return { 69 return {
70 setRootSetting, 70 setRootSetting,
71 71
@@ -73,7 +73,6 @@ export function useRootSetting() { @@ -73,7 +73,6 @@ export function useRootSetting() {
73 getFullContent, 73 getFullContent,
74 getColorWeak, 74 getColorWeak,
75 getGrayMode, 75 getGrayMode,
76 - getRootSetting,  
77 getLayoutContentMode, 76 getLayoutContentMode,
78 getPageLoading, 77 getPageLoading,
79 getOpenKeepAlive, 78 getOpenKeepAlive,
src/hooks/setting/useTransitionSetting.ts
1 import type { TransitionSetting } from '/#/config'; 1 import type { TransitionSetting } from '/#/config';
2 2
3 -import { computed, unref } from 'vue'; 3 +import { computed } from 'vue';
4 4
5 -import { appStore } from '/@/store/modules/app'; 5 +import { useAppStore } from '/@/store/modules/app';
6 6
7 -const getTransitionSetting = computed(() => appStore.getProjectConfig.transitionSetting);  
8 -  
9 -const getEnableTransition = computed(() => unref(getTransitionSetting)?.enable); 7 +export function useTransitionSetting() {
  8 + const appStore = useAppStore();
10 9
11 -const getOpenNProgress = computed(() => unref(getTransitionSetting)?.openNProgress); 10 + const getEnableTransition = computed(() => appStore.getTransitionSetting?.enable);
12 11
13 -const getOpenPageLoading = computed((): boolean => {  
14 - return !!unref(getTransitionSetting)?.openPageLoading;  
15 -}); 12 + const getOpenNProgress = computed(() => appStore.getTransitionSetting?.openNProgress);
16 13
17 -const getBasicTransition = computed(() => unref(getTransitionSetting)?.basicTransition); 14 + const getOpenPageLoading = computed((): boolean => {
  15 + return !!appStore.getTransitionSetting?.openPageLoading;
  16 + });
18 17
19 -function setTransitionSetting(transitionSetting: Partial<TransitionSetting>) {  
20 - appStore.commitProjectConfigState({ transitionSetting });  
21 -} 18 + const getBasicTransition = computed(() => appStore.getTransitionSetting?.basicTransition);
22 19
23 -export function useTransitionSetting() { 20 + function setTransitionSetting(transitionSetting: Partial<TransitionSetting>) {
  21 + appStore.setProjectConfig({ transitionSetting });
  22 + }
24 return { 23 return {
25 setTransitionSetting, 24 setTransitionSetting,
26 25
27 - getTransitionSetting,  
28 getEnableTransition, 26 getEnableTransition,
29 getOpenNProgress, 27 getOpenNProgress,
30 getOpenPageLoading, 28 getOpenPageLoading,
src/plugins/echarts/index.ts renamed to src/hooks/web/useEcharts/echarts.ts
src/hooks/web/useECharts.ts renamed to src/hooks/web/useEcharts/index.ts
  1 +import type { EChartsOption } from 'echarts';
  2 +import type { Ref } from 'vue';
  3 +
1 import { useTimeoutFn } from '/@/hooks/core/useTimeout'; 4 import { useTimeoutFn } from '/@/hooks/core/useTimeout';
2 import { tryOnUnmounted } from '@vueuse/core'; 5 import { tryOnUnmounted } from '@vueuse/core';
3 -import { unref, Ref, nextTick, watch, computed, ref } from 'vue';  
4 -import type { EChartsOption } from 'echarts'; 6 +import { unref, nextTick, watch, computed, ref } from 'vue';
5 import { useDebounce } from '/@/hooks/core/useDebounce'; 7 import { useDebounce } from '/@/hooks/core/useDebounce';
6 import { useEventListener } from '/@/hooks/event/useEventListener'; 8 import { useEventListener } from '/@/hooks/event/useEventListener';
7 import { useBreakpoint } from '/@/hooks/event/useBreakpoint'; 9 import { useBreakpoint } from '/@/hooks/event/useBreakpoint';
8 10
9 -import echarts from '/@/plugins/echarts';  
10 -import { useRootSetting } from '../setting/useRootSetting'; 11 +import echarts from './echarts';
  12 +import { useRootSetting } from '/@/hooks/setting/useRootSetting';
11 13
12 export function useECharts( 14 export function useECharts(
13 elRef: Ref<HTMLDivElement>, 15 elRef: Ref<HTMLDivElement>,
src/hooks/web/useFullContent.ts
1 import { computed, unref } from 'vue'; 1 import { computed, unref } from 'vue';
2 2
3 -import { appStore } from '/@/store/modules/app'; 3 +import { useAppStore } from '/@/store/modules/app';
4 4
5 import router from '/@/router'; 5 import router from '/@/router';
6 6
@@ -8,6 +8,7 @@ import router from &#39;/@/router&#39;; @@ -8,6 +8,7 @@ import router from &#39;/@/router&#39;;
8 * @description: Full screen display content 8 * @description: Full screen display content
9 */ 9 */
10 export const useFullContent = () => { 10 export const useFullContent = () => {
  11 + const appStore = useAppStore();
11 const { currentRoute } = router; 12 const { currentRoute } = router;
12 13
13 // Whether to display the content in full screen without displaying the menu 14 // Whether to display the content in full screen without displaying the menu
src/hooks/web/useLockPage.ts
1 import { computed, onUnmounted, unref, watchEffect } from 'vue'; 1 import { computed, onUnmounted, unref, watchEffect } from 'vue';
2 import { useThrottle } from '/@/hooks/core/useThrottle'; 2 import { useThrottle } from '/@/hooks/core/useThrottle';
3 3
4 -import { appStore } from '/@/store/modules/app';  
5 -import { lockStore } from '/@/store/modules/lock';  
6 -import { userStore } from '/@/store/modules/user'; 4 +import { useAppStore } from '/@/store/modules/app';
  5 +import { useLockStore } from '/@/store/modules/lock';
  6 +
  7 +import { useUserStore } from '/@/store/modules/user';
7 import { useRootSetting } from '../setting/useRootSetting'; 8 import { useRootSetting } from '../setting/useRootSetting';
8 9
9 export function useLockPage() { 10 export function useLockPage() {
10 const { getLockTime } = useRootSetting(); 11 const { getLockTime } = useRootSetting();
  12 + const lockStore = useLockStore();
  13 + const userStore = useUserStore();
  14 + const appStore = useAppStore();
  15 +
11 let timeId: TimeoutHandle; 16 let timeId: TimeoutHandle;
12 17
13 function clear(): void { 18 function clear(): void {
@@ -16,7 +21,7 @@ export function useLockPage() { @@ -16,7 +21,7 @@ export function useLockPage() {
16 21
17 function resetCalcLockTimeout(): void { 22 function resetCalcLockTimeout(): void {
18 // not login 23 // not login
19 - if (!userStore.getTokenState) { 24 + if (!userStore.getToken) {
20 clear(); 25 clear();
21 return; 26 return;
22 } 27 }
@@ -33,14 +38,14 @@ export function useLockPage() { @@ -33,14 +38,14 @@ export function useLockPage() {
33 } 38 }
34 39
35 function lockPage(): void { 40 function lockPage(): void {
36 - lockStore.commitLockInfoState({ 41 + lockStore.setLockInfo({
37 isLock: true, 42 isLock: true,
38 pwd: undefined, 43 pwd: undefined,
39 }); 44 });
40 } 45 }
41 46
42 watchEffect((onClean) => { 47 watchEffect((onClean) => {
43 - if (userStore.getTokenState) { 48 + if (userStore.getToken) {
44 resetCalcLockTimeout(); 49 resetCalcLockTimeout();
45 } else { 50 } else {
46 clear(); 51 clear();
src/hooks/web/usePage.ts
1 -import type { RouteLocationRaw } from 'vue-router'; 1 +import type { RouteLocationRaw, Router } from 'vue-router';
2 2
3 import { PageEnum } from '/@/enums/pageEnum'; 3 import { PageEnum } from '/@/enums/pageEnum';
4 import { isString } from '/@/utils/is'; 4 import { isString } from '/@/utils/is';
5 import { unref } from 'vue'; 5 import { unref } from 'vue';
6 6
7 -import router from '/@/router'; 7 +import { useRouter } from 'vue-router';
8 8
9 export type RouteLocationRawEx = Omit<RouteLocationRaw, 'path'> & { path: PageEnum }; 9 export type RouteLocationRawEx = Omit<RouteLocationRaw, 'path'> & { path: PageEnum };
10 10
@@ -13,10 +13,16 @@ function handleError(e: Error) { @@ -13,10 +13,16 @@ function handleError(e: Error) {
13 } 13 }
14 14
15 // page switch 15 // page switch
16 -export function useGo() {  
17 - const { push, replace } = router; 16 +export function useGo(_router?: Router) {
  17 + let router;
  18 + if (!_router) {
  19 + router = useRouter();
  20 + }
  21 + const { push, replace } = _router || router;
18 function go(opt: PageEnum | RouteLocationRawEx | string = PageEnum.BASE_HOME, isReplace = false) { 22 function go(opt: PageEnum | RouteLocationRawEx | string = PageEnum.BASE_HOME, isReplace = false) {
19 - if (!opt) return; 23 + if (!opt) {
  24 + return;
  25 + }
20 if (isString(opt)) { 26 if (isString(opt)) {
21 isReplace ? replace(opt).catch(handleError) : push(opt).catch(handleError); 27 isReplace ? replace(opt).catch(handleError) : push(opt).catch(handleError);
22 } else { 28 } else {
@@ -30,8 +36,12 @@ export function useGo() { @@ -30,8 +36,12 @@ export function useGo() {
30 /** 36 /**
31 * @description: redo current page 37 * @description: redo current page
32 */ 38 */
33 -export const useRedo = () => {  
34 - const { push, currentRoute } = router; 39 +export const useRedo = (_router?: Router) => {
  40 + let router;
  41 + if (!_router) {
  42 + router = useRouter();
  43 + }
  44 + const { push, currentRoute } = _router || router;
35 const { query, params } = currentRoute.value; 45 const { query, params } = currentRoute.value;
36 function redo(): Promise<boolean> { 46 function redo(): Promise<boolean> {
37 return new Promise((resolve) => { 47 return new Promise((resolve) => {
src/hooks/web/usePermission.ts
1 import type { RouteRecordRaw } from 'vue-router'; 1 import type { RouteRecordRaw } from 'vue-router';
2 2
3 -import { appStore } from '/@/store/modules/app';  
4 -import { permissionStore } from '/@/store/modules/permission';  
5 -import { userStore } from '/@/store/modules/user'; 3 +import { useAppStore } from '/@/store/modules/app';
  4 +import { usePermissionStore } from '/@/store/modules/permission';
  5 +import { useUserStore } from '/@/store/modules/user';
6 6
7 import { useTabs } from './useTabs'; 7 import { useTabs } from './useTabs';
8 8
@@ -15,15 +15,20 @@ import { RoleEnum } from &#39;/@/enums/roleEnum&#39;; @@ -15,15 +15,20 @@ import { RoleEnum } from &#39;/@/enums/roleEnum&#39;;
15 15
16 import { intersection } from 'lodash-es'; 16 import { intersection } from 'lodash-es';
17 import { isArray } from '/@/utils/is'; 17 import { isArray } from '/@/utils/is';
18 -import { tabStore } from '/@/store/modules/tab'; 18 +import { useMultipleTabStore } from '/@/store/modules/multipleTab';
19 19
20 // User permissions related operations 20 // User permissions related operations
21 export function usePermission() { 21 export function usePermission() {
  22 + const userStore = useUserStore();
  23 + const appStore = useAppStore();
  24 + const permissionStore = usePermissionStore();
  25 + const { closeAll } = useTabs(router);
  26 +
22 /** 27 /**
23 * Change permission mode 28 * Change permission mode
24 */ 29 */
25 async function togglePermissionMode() { 30 async function togglePermissionMode() {
26 - appStore.commitProjectConfigState({ 31 + appStore.setProjectConfig({
27 permissionMode: 32 permissionMode:
28 projectSetting.permissionMode === PermissionModeEnum.BACK 33 projectSetting.permissionMode === PermissionModeEnum.BACK
29 ? PermissionModeEnum.ROLE 34 ? PermissionModeEnum.ROLE
@@ -37,14 +42,14 @@ export function usePermission() { @@ -37,14 +42,14 @@ export function usePermission() {
37 * @param id 42 * @param id
38 */ 43 */
39 async function resume(id?: string | number) { 44 async function resume(id?: string | number) {
40 - tabStore.commitClearCache(); 45 + const tabStore = useMultipleTabStore();
  46 + tabStore.clearCacheTabs();
41 resetRouter(); 47 resetRouter();
42 const routes = await permissionStore.buildRoutesAction(id); 48 const routes = await permissionStore.buildRoutesAction(id);
43 routes.forEach((route) => { 49 routes.forEach((route) => {
44 router.addRoute((route as unknown) as RouteRecordRaw); 50 router.addRoute((route as unknown) as RouteRecordRaw);
45 }); 51 });
46 - permissionStore.commitLastBuildMenuTimeState();  
47 - const { closeAll } = useTabs(); 52 + permissionStore.setLastBuildMenuTime();
48 closeAll(); 53 closeAll();
49 } 54 }
50 55
@@ -53,22 +58,24 @@ export function usePermission() { @@ -53,22 +58,24 @@ export function usePermission() {
53 */ 58 */
54 function hasPermission(value?: RoleEnum | RoleEnum[] | string | string[], def = true): boolean { 59 function hasPermission(value?: RoleEnum | RoleEnum[] | string | string[], def = true): boolean {
55 const permMode = projectSetting.permissionMode; 60 const permMode = projectSetting.permissionMode;
  61 +
56 if (PermissionModeEnum.ROLE === permMode) { 62 if (PermissionModeEnum.ROLE === permMode) {
57 // Visible by default 63 // Visible by default
58 if (!value) { 64 if (!value) {
59 return def; 65 return def;
60 } 66 }
61 if (!isArray(value)) { 67 if (!isArray(value)) {
62 - return userStore.getRoleListState?.includes(value as RoleEnum); 68 + return userStore.getRoleList?.includes(value as RoleEnum);
63 } 69 }
64 - return (intersection(value, userStore.getRoleListState) as RoleEnum[]).length > 0; 70 + return (intersection(value, userStore.getRoleList) as RoleEnum[]).length > 0;
65 } 71 }
  72 +
66 if (PermissionModeEnum.BACK === permMode) { 73 if (PermissionModeEnum.BACK === permMode) {
67 // Visible by default 74 // Visible by default
68 if (!value) { 75 if (!value) {
69 return def; 76 return def;
70 } 77 }
71 - const allCodeList = permissionStore.getPermCodeListState; 78 + const allCodeList = permissionStore.getPermCodeList;
72 if (!isArray(value)) { 79 if (!isArray(value)) {
73 return allCodeList.includes(value as string); 80 return allCodeList.includes(value as string);
74 } 81 }
@@ -90,7 +97,7 @@ export function usePermission() { @@ -90,7 +97,7 @@ export function usePermission() {
90 if (!isArray(roles)) { 97 if (!isArray(roles)) {
91 roles = [roles]; 98 roles = [roles];
92 } 99 }
93 - userStore.commitRoleListState(roles); 100 + userStore.setRoleList(roles);
94 await resume(); 101 await resume();
95 } 102 }
96 103
src/hooks/web/useTabs.ts
1 -import { tabStore } from '/@/store/modules/tab';  
2 -import { appStore } from '/@/store/modules/app';  
3 -import type { RouteLocationNormalized } from 'vue-router'; 1 +import type { RouteLocationNormalized, Router } from 'vue-router';
4 2
5 -export function useTabs() {  
6 - function canIUseFn(): boolean {  
7 - const { multiTabsSetting: { show } = {} } = appStore.getProjectConfig; 3 +import { useRouter } from 'vue-router';
  4 +import { unref } from 'vue';
  5 +
  6 +import { useMultipleTabStore } from '/@/store/modules/multipleTab';
  7 +import { useAppStore } from '/@/store/modules/app';
  8 +
  9 +enum TableActionEnum {
  10 + REFRESH,
  11 + CLOSE_ALL,
  12 + CLOSE_LEFT,
  13 + CLOSE_RIGHT,
  14 + CLOSE_OTHER,
  15 + CLOSE_CURRENT,
  16 + CLOSE,
  17 +}
  18 +
  19 +export function useTabs(_router: Router) {
  20 + const appStore = useAppStore();
  21 +
  22 + function canIUseTabs(): boolean {
  23 + const { show } = appStore.getMultiTabsSetting;
8 if (!show) { 24 if (!show) {
9 throw new Error('The multi-tab page is currently not open, please open it in the settings๏ผ'); 25 throw new Error('The multi-tab page is currently not open, please open it in the settings๏ผ');
10 } 26 }
11 return !!show; 27 return !!show;
12 } 28 }
13 29
  30 + const tabStore = useMultipleTabStore();
  31 + const router = _router || useRouter();
  32 +
  33 + const { currentRoute } = router;
  34 +
  35 + function getCurrentTab() {
  36 + const route = unref(currentRoute);
  37 + return tabStore.getTabList.find((item) => item.path === route.path)!;
  38 + }
  39 +
  40 + async function handleTabAction(action: TableActionEnum, tab?: RouteLocationNormalized) {
  41 + const canIUse = canIUseTabs;
  42 + if (!canIUse) {
  43 + return;
  44 + }
  45 + const currentTab = getCurrentTab();
  46 + switch (action) {
  47 + case TableActionEnum.REFRESH:
  48 + await tabStore.refreshPage(router);
  49 + break;
  50 +
  51 + case TableActionEnum.CLOSE_ALL:
  52 + await tabStore.closeAllTab(router);
  53 + break;
  54 +
  55 + case TableActionEnum.CLOSE_LEFT:
  56 + await tabStore.closeLeftTabs(currentTab, router);
  57 + break;
  58 +
  59 + case TableActionEnum.CLOSE_RIGHT:
  60 + await tabStore.closeRightTabs(currentTab, router);
  61 + break;
  62 +
  63 + case TableActionEnum.CLOSE_OTHER:
  64 + await tabStore.closeOtherTabs(currentTab, router);
  65 + break;
  66 +
  67 + case TableActionEnum.CLOSE_CURRENT:
  68 + case TableActionEnum.CLOSE:
  69 + await tabStore.closeTab(tab || currentTab, router);
  70 + break;
  71 + }
  72 + }
  73 +
14 return { 74 return {
15 - refreshPage: async () => {  
16 - if (canIUseFn()) {  
17 - await tabStore.commitRedoPage();  
18 - } 75 + refreshPage: () => handleTabAction(TableActionEnum.REFRESH),
  76 + closeAll: () => handleTabAction(TableActionEnum.CLOSE_ALL),
  77 + closeLeft: () => handleTabAction(TableActionEnum.CLOSE_LEFT),
  78 + closeRight: () => handleTabAction(TableActionEnum.CLOSE_RIGHT),
  79 + closeOther: () => handleTabAction(TableActionEnum.CLOSE_OTHER),
  80 + closeCurrent: () => handleTabAction(TableActionEnum.CLOSE_CURRENT),
  81 + close: (tab?: RouteLocationNormalized) => {
  82 + handleTabAction(TableActionEnum.CLOSE, tab);
19 }, 83 },
20 - closeAll: () => canIUseFn() && tabStore.closeAllTabAction(),  
21 - closeLeft: () => canIUseFn() && tabStore.closeLeftTabAction(tabStore.getCurrentTab),  
22 - closeRight: () => canIUseFn() && tabStore.closeRightTabAction(tabStore.getCurrentTab),  
23 - closeOther: () => canIUseFn() && tabStore.closeOtherTabAction(tabStore.getCurrentTab),  
24 - closeCurrent: () => canIUseFn() && tabStore.closeTabAction(tabStore.getCurrentTab),  
25 - close: (tab?: RouteLocationNormalized) =>  
26 - canIUseFn() && tabStore.closeTabAction(tab || tabStore.getCurrentTab),  
27 }; 84 };
28 } 85 }
src/layouts/default/header/components/ErrorAction.vue
@@ -5,7 +5,7 @@ @@ -5,7 +5,7 @@
5 :mouseEnterDelay="0.5" 5 :mouseEnterDelay="0.5"
6 @click="handleToErrorList" 6 @click="handleToErrorList"
7 > 7 >
8 - <Badge :count="getCount" :offset="[0, 10]" dot :overflowCount="99"> 8 + <Badge :count="getCount" :offset="[0, 10]" :overflowCount="99">
9 <Icon icon="ion:bug-outline" /> 9 <Icon icon="ion:bug-outline" />
10 </Badge> 10 </Badge>
11 </Tooltip> 11 </Tooltip>
@@ -16,7 +16,7 @@ @@ -16,7 +16,7 @@
16 import Icon from '/@/components/Icon'; 16 import Icon from '/@/components/Icon';
17 17
18 import { useI18n } from '/@/hooks/web/useI18n'; 18 import { useI18n } from '/@/hooks/web/useI18n';
19 - import { errorStore } from '/@/store/modules/error'; 19 + import { useErrorLogStore } from '/@/store/modules/errorLog';
20 import { PageEnum } from '/@/enums/pageEnum'; 20 import { PageEnum } from '/@/enums/pageEnum';
21 21
22 import { useRouter } from 'vue-router'; 22 import { useRouter } from 'vue-router';
@@ -28,14 +28,13 @@ @@ -28,14 +28,13 @@
28 setup() { 28 setup() {
29 const { t } = useI18n(); 29 const { t } = useI18n();
30 const { push } = useRouter(); 30 const { push } = useRouter();
  31 + const errorLogStore = useErrorLogStore();
31 32
32 - const getCount = computed(() => {  
33 - return errorStore.getErrorListCountState;  
34 - }); 33 + const getCount = computed(() => errorLogStore.getErrorLogListCount);
35 34
36 function handleToErrorList() { 35 function handleToErrorList() {
37 push(PageEnum.ERROR_LOG_PAGE).then(() => { 36 push(PageEnum.ERROR_LOG_PAGE).then(() => {
38 - errorStore.commitErrorListCountState(0); 37 + errorLogStore.setErrorLogListCount(0);
39 }); 38 });
40 } 39 }
41 40
src/layouts/default/header/components/lock/LockModal.vue
@@ -31,8 +31,8 @@ @@ -31,8 +31,8 @@
31 import { BasicModal, useModalInner } from '/@/components/Modal/index'; 31 import { BasicModal, useModalInner } from '/@/components/Modal/index';
32 import { BasicForm, useForm } from '/@/components/Form/index'; 32 import { BasicForm, useForm } from '/@/components/Form/index';
33 33
34 - import { userStore } from '/@/store/modules/user';  
35 - import { lockStore } from '/@/store/modules/lock'; 34 + import { useUserStore } from '/@/store/modules/user';
  35 + import { useLockStore } from '/@/store/modules/lock';
36 import headerImg from '/@/assets/images/header.jpg'; 36 import headerImg from '/@/assets/images/header.jpg';
37 export default defineComponent({ 37 export default defineComponent({
38 name: 'LockModal', 38 name: 'LockModal',
@@ -41,10 +41,10 @@ @@ -41,10 +41,10 @@
41 setup() { 41 setup() {
42 const { t } = useI18n(); 42 const { t } = useI18n();
43 const { prefixCls } = useDesign('header-lock-modal'); 43 const { prefixCls } = useDesign('header-lock-modal');
  44 + const userStore = useUserStore();
  45 + const lockStore = useLockStore();
44 46
45 - const getRealName = computed(() => {  
46 - return userStore.getUserInfoState?.realName;  
47 - }); 47 + const getRealName = computed(() => userStore.getUserInfo?.realName);
48 const [register, { closeModal }] = useModalInner(); 48 const [register, { closeModal }] = useModalInner();
49 49
50 const [registerForm, { validateFields, resetFields }] = useForm({ 50 const [registerForm, { validateFields, resetFields }] = useForm({
@@ -64,7 +64,7 @@ @@ -64,7 +64,7 @@
64 const password: string | undefined = values.password; 64 const password: string | undefined = values.password;
65 closeModal(); 65 closeModal();
66 66
67 - lockStore.commitLockInfoState({ 67 + lockStore.setLockInfo({
68 isLock: true, 68 isLock: true,
69 pwd: password, 69 pwd: password,
70 }); 70 });
src/layouts/default/header/components/user-dropdown/index.vue
@@ -41,7 +41,7 @@ @@ -41,7 +41,7 @@
41 41
42 import { DOC_URL } from '/@/settings/siteSetting'; 42 import { DOC_URL } from '/@/settings/siteSetting';
43 43
44 - import { userStore } from '/@/store/modules/user'; 44 + import { useUserStore } from '/@/store/modules/user';
45 import { useHeaderSetting } from '/@/hooks/setting/useHeaderSetting'; 45 import { useHeaderSetting } from '/@/hooks/setting/useHeaderSetting';
46 import { useI18n } from '/@/hooks/web/useI18n'; 46 import { useI18n } from '/@/hooks/web/useI18n';
47 import { useDesign } from '/@/hooks/web/useDesign'; 47 import { useDesign } from '/@/hooks/web/useDesign';
@@ -71,9 +71,10 @@ @@ -71,9 +71,10 @@
71 const { prefixCls } = useDesign('header-user-dropdown'); 71 const { prefixCls } = useDesign('header-user-dropdown');
72 const { t } = useI18n(); 72 const { t } = useI18n();
73 const { getShowDoc } = useHeaderSetting(); 73 const { getShowDoc } = useHeaderSetting();
  74 + const userStore = useUserStore();
74 75
75 const getUserInfo = computed(() => { 76 const getUserInfo = computed(() => {
76 - const { realName = '', desc } = userStore.getUserInfoState || {}; 77 + const { realName = '', desc } = userStore.getUserInfo || {};
77 return { realName, desc }; 78 return { realName, desc };
78 }); 79 });
79 80
src/layouts/default/index.vue
@@ -42,13 +42,9 @@ @@ -42,13 +42,9 @@
42 }, 42 },
43 setup() { 43 setup() {
44 const { prefixCls } = useDesign('default-layout'); 44 const { prefixCls } = useDesign('default-layout');
45 -  
46 const { getIsMobile } = useAppInject(); 45 const { getIsMobile } = useAppInject();
47 -  
48 const { getShowFullHeaderRef } = useHeaderSetting(); 46 const { getShowFullHeaderRef } = useHeaderSetting();
49 -  
50 const { getShowSidebar, getIsMixSidebar } = useMenuSetting(); 47 const { getShowSidebar, getIsMixSidebar } = useMenuSetting();
51 -  
52 const layoutClass = computed(() => ({ 'ant-layout-has-sider': unref(getIsMixSidebar) })); 48 const layoutClass = computed(() => ({ 'ant-layout-has-sider': unref(getIsMixSidebar) }));
53 49
54 return { 50 return {
src/layouts/default/menu/useLayoutMenu.ts
@@ -9,7 +9,7 @@ import { useThrottle } from &#39;/@/hooks/core/useThrottle&#39;; @@ -9,7 +9,7 @@ import { useThrottle } from &#39;/@/hooks/core/useThrottle&#39;;
9 import { useMenuSetting } from '/@/hooks/setting/useMenuSetting'; 9 import { useMenuSetting } from '/@/hooks/setting/useMenuSetting';
10 10
11 import { getChildrenMenus, getCurrentParentPath, getMenus, getShallowMenus } from '/@/router/menus'; 11 import { getChildrenMenus, getCurrentParentPath, getMenus, getShallowMenus } from '/@/router/menus';
12 -import { permissionStore } from '/@/store/modules/permission'; 12 +import { usePermissionStore } from '/@/store/modules/permission';
13 import { useAppInject } from '/@/hooks/web/useAppInject'; 13 import { useAppInject } from '/@/hooks/web/useAppInject';
14 14
15 export function useSplitMenu(splitType: Ref<MenuSplitTyeEnum>) { 15 export function useSplitMenu(splitType: Ref<MenuSplitTyeEnum>) {
@@ -17,6 +17,7 @@ export function useSplitMenu(splitType: Ref&lt;MenuSplitTyeEnum&gt;) { @@ -17,6 +17,7 @@ export function useSplitMenu(splitType: Ref&lt;MenuSplitTyeEnum&gt;) {
17 const menusRef = ref<Menu[]>([]); 17 const menusRef = ref<Menu[]>([]);
18 const { currentRoute } = useRouter(); 18 const { currentRoute } = useRouter();
19 const { getIsMobile } = useAppInject(); 19 const { getIsMobile } = useAppInject();
  20 + const permissionStore = usePermissionStore();
20 const { setMenuSetting, getIsHorizontal, getSplit } = useMenuSetting(); 21 const { setMenuSetting, getIsHorizontal, getSplit } = useMenuSetting();
21 22
22 const [throttleHandleSplitLeftMenu] = useThrottle(handleSplitLeftMenu, 50); 23 const [throttleHandleSplitLeftMenu] = useThrottle(handleSplitLeftMenu, 50);
@@ -55,7 +56,7 @@ export function useSplitMenu(splitType: Ref&lt;MenuSplitTyeEnum&gt;) { @@ -55,7 +56,7 @@ export function useSplitMenu(splitType: Ref&lt;MenuSplitTyeEnum&gt;) {
55 56
56 // Menu changes 57 // Menu changes
57 watch( 58 watch(
58 - [() => permissionStore.getLastBuildMenuTimeState, () => permissionStore.getBackMenuListState], 59 + [() => permissionStore.getLastBuildMenuTime, () => permissionStore.getBackMenuList],
59 () => { 60 () => {
60 genMenus(); 61 genMenus();
61 }, 62 },
src/layouts/default/setting/components/SettingFooter.vue
@@ -21,32 +21,36 @@ @@ -21,32 +21,36 @@
21 21
22 import { CopyOutlined, RedoOutlined } from '@ant-design/icons-vue'; 22 import { CopyOutlined, RedoOutlined } from '@ant-design/icons-vue';
23 23
24 - import { appStore } from '/@/store/modules/app';  
25 - import { permissionStore } from '/@/store/modules/permission';  
26 - import { tabStore } from '/@/store/modules/tab';  
27 - import { userStore } from '/@/store/modules/user'; 24 + import { useAppStore } from '/@/store/modules/app';
  25 + import { usePermissionStore } from '/@/store/modules/permission';
  26 + import { useMultipleTabStore } from '/@/store/modules/multipleTab';
  27 + import { useUserStore } from '/@/store/modules/user';
28 28
29 import { useDesign } from '/@/hooks/web/useDesign'; 29 import { useDesign } from '/@/hooks/web/useDesign';
30 import { useI18n } from '/@/hooks/web/useI18n'; 30 import { useI18n } from '/@/hooks/web/useI18n';
31 import { useMessage } from '/@/hooks/web/useMessage'; 31 import { useMessage } from '/@/hooks/web/useMessage';
32 import { useCopyToClipboard } from '/@/hooks/web/useCopyToClipboard'; 32 import { useCopyToClipboard } from '/@/hooks/web/useCopyToClipboard';
33 - import { useRootSetting } from '/@/hooks/setting/useRootSetting';  
34 33
35 import { updateColorWeak } from '/@/logics/theme/updateColorWeak'; 34 import { updateColorWeak } from '/@/logics/theme/updateColorWeak';
36 import { updateGrayMode } from '/@/logics/theme/updateGrayMode'; 35 import { updateGrayMode } from '/@/logics/theme/updateGrayMode';
37 -  
38 import defaultSetting from '/@/settings/projectSetting'; 36 import defaultSetting from '/@/settings/projectSetting';
  37 +
39 export default defineComponent({ 38 export default defineComponent({
40 name: 'SettingFooter', 39 name: 'SettingFooter',
41 components: { CopyOutlined, RedoOutlined }, 40 components: { CopyOutlined, RedoOutlined },
42 setup() { 41 setup() {
43 - const { getRootSetting } = useRootSetting(); 42 + const permissionStore = usePermissionStore();
44 const { prefixCls } = useDesign('setting-footer'); 43 const { prefixCls } = useDesign('setting-footer');
45 const { t } = useI18n(); 44 const { t } = useI18n();
46 const { createSuccessModal, createMessage } = useMessage(); 45 const { createSuccessModal, createMessage } = useMessage();
  46 + const tabStore = useMultipleTabStore();
  47 + const userStore = useUserStore();
  48 + const appStore = useAppStore();
47 49
48 function handleCopy() { 50 function handleCopy() {
49 - const { isSuccessRef } = useCopyToClipboard(JSON.stringify(unref(getRootSetting), null, 2)); 51 + const { isSuccessRef } = useCopyToClipboard(
  52 + JSON.stringify(unref(appStore.getProjectConfig), null, 2)
  53 + );
50 unref(isSuccessRef) && 54 unref(isSuccessRef) &&
51 createSuccessModal({ 55 createSuccessModal({
52 title: t('layout.setting.operatingTitle'), 56 title: t('layout.setting.operatingTitle'),
@@ -55,7 +59,7 @@ @@ -55,7 +59,7 @@
55 } 59 }
56 function handleResetSetting() { 60 function handleResetSetting() {
57 try { 61 try {
58 - appStore.commitProjectConfigState(defaultSetting); 62 + appStore.setProjectConfig(defaultSetting);
59 const { colorWeak, grayMode } = defaultSetting; 63 const { colorWeak, grayMode } = defaultSetting;
60 // updateTheme(themeColor); 64 // updateTheme(themeColor);
61 updateColorWeak(colorWeak); 65 updateColorWeak(colorWeak);
@@ -68,10 +72,10 @@ @@ -68,10 +72,10 @@
68 72
69 function handleClearAndRedo() { 73 function handleClearAndRedo() {
70 localStorage.clear(); 74 localStorage.clear();
71 - appStore.resumeAllState();  
72 - permissionStore.commitResetState();  
73 - tabStore.commitResetState();  
74 - userStore.commitResetState(); 75 + appStore.resetAllState();
  76 + permissionStore.resetState();
  77 + tabStore.resetState();
  78 + userStore.resetState();
75 location.reload(); 79 location.reload();
76 } 80 }
77 return { 81 return {
src/layouts/default/setting/handler.ts
@@ -3,15 +3,16 @@ import { updateHeaderBgColor, updateSidebarBgColor } from &#39;/@/logics/theme/updat @@ -3,15 +3,16 @@ import { updateHeaderBgColor, updateSidebarBgColor } from &#39;/@/logics/theme/updat
3 import { updateColorWeak } from '/@/logics/theme/updateColorWeak'; 3 import { updateColorWeak } from '/@/logics/theme/updateColorWeak';
4 import { updateGrayMode } from '/@/logics/theme/updateGrayMode'; 4 import { updateGrayMode } from '/@/logics/theme/updateGrayMode';
5 5
6 -import { appStore } from '/@/store/modules/app'; 6 +import { useAppStore } from '/@/store/modules/app';
7 import { ProjectConfig } from '/#/config'; 7 import { ProjectConfig } from '/#/config';
8 import { changeTheme } from '/@/logics/theme'; 8 import { changeTheme } from '/@/logics/theme';
9 import { updateDarkTheme } from '/@/logics/theme/dark'; 9 import { updateDarkTheme } from '/@/logics/theme/dark';
10 import { useRootSetting } from '/@/hooks/setting/useRootSetting'; 10 import { useRootSetting } from '/@/hooks/setting/useRootSetting';
11 11
12 export function baseHandler(event: HandlerEnum, value: any) { 12 export function baseHandler(event: HandlerEnum, value: any) {
  13 + const appStore = useAppStore();
13 const config = handler(event, value); 14 const config = handler(event, value);
14 - appStore.commitProjectConfigState(config); 15 + appStore.setProjectConfig(config);
15 if (event === HandlerEnum.CHANGE_THEME) { 16 if (event === HandlerEnum.CHANGE_THEME) {
16 updateHeaderBgColor(); 17 updateHeaderBgColor();
17 updateSidebarBgColor(); 18 updateSidebarBgColor();
@@ -19,6 +20,8 @@ export function baseHandler(event: HandlerEnum, value: any) { @@ -19,6 +20,8 @@ export function baseHandler(event: HandlerEnum, value: any) {
19 } 20 }
20 21
21 export function handler(event: HandlerEnum, value: any): DeepPartial<ProjectConfig> { 22 export function handler(event: HandlerEnum, value: any): DeepPartial<ProjectConfig> {
  23 + const appStore = useAppStore();
  24 +
22 const { getThemeColor, getDarkMode } = useRootSetting(); 25 const { getThemeColor, getDarkMode } = useRootSetting();
23 switch (event) { 26 switch (event) {
24 case HandlerEnum.CHANGE_LAYOUT: 27 case HandlerEnum.CHANGE_LAYOUT:
@@ -50,7 +53,7 @@ export function handler(event: HandlerEnum, value: any): DeepPartial&lt;ProjectConf @@ -50,7 +53,7 @@ export function handler(event: HandlerEnum, value: any): DeepPartial&lt;ProjectConf
50 } 53 }
51 updateDarkTheme(value); 54 updateDarkTheme(value);
52 55
53 - return { darkMode: value }; 56 + return {};
54 57
55 case HandlerEnum.MENU_HAS_DRAG: 58 case HandlerEnum.MENU_HAS_DRAG:
56 return { menuSetting: { canDrag: value } }; 59 return { menuSetting: { canDrag: value } };
@@ -97,7 +100,7 @@ export function handler(event: HandlerEnum, value: any): DeepPartial&lt;ProjectConf @@ -97,7 +100,7 @@ export function handler(event: HandlerEnum, value: any): DeepPartial&lt;ProjectConf
97 100
98 // ============transition================== 101 // ============transition==================
99 case HandlerEnum.OPEN_PAGE_LOADING: 102 case HandlerEnum.OPEN_PAGE_LOADING:
100 - appStore.commitPageLoadingState(false); 103 + appStore.setPageLoading(false);
101 return { transitionSetting: { openPageLoading: value } }; 104 return { transitionSetting: { openPageLoading: value } };
102 105
103 case HandlerEnum.ROUTER_TRANSITION: 106 case HandlerEnum.ROUTER_TRANSITION:
src/layouts/default/tabs/components/FoldButton.vue
@@ -5,38 +5,33 @@ @@ -5,38 +5,33 @@
5 </template> 5 </template>
6 <script lang="ts"> 6 <script lang="ts">
7 import { defineComponent, unref, computed } from 'vue'; 7 import { defineComponent, unref, computed } from 'vue';
  8 + import { Icon } from '/@/components/Icon';
  9 +
8 import { useDesign } from '/@/hooks/web/useDesign'; 10 import { useDesign } from '/@/hooks/web/useDesign';
9 import { useHeaderSetting } from '/@/hooks/setting/useHeaderSetting'; 11 import { useHeaderSetting } from '/@/hooks/setting/useHeaderSetting';
10 import { useMenuSetting } from '/@/hooks/setting/useMenuSetting'; 12 import { useMenuSetting } from '/@/hooks/setting/useMenuSetting';
11 13
12 - import Icon from '/@/components/Icon';  
13 -  
14 export default defineComponent({ 14 export default defineComponent({
15 name: 'FoldButton', 15 name: 'FoldButton',
16 components: { Icon }, 16 components: { Icon },
17 -  
18 setup() { 17 setup() {
19 const { prefixCls } = useDesign('multiple-tabs-content'); 18 const { prefixCls } = useDesign('multiple-tabs-content');
20 const { getShowMenu, setMenuSetting } = useMenuSetting(); 19 const { getShowMenu, setMenuSetting } = useMenuSetting();
21 const { getShowHeader, setHeaderSetting } = useHeaderSetting(); 20 const { getShowHeader, setHeaderSetting } = useHeaderSetting();
22 21
23 - const getIsUnFold = computed(() => {  
24 - return !unref(getShowMenu) && !unref(getShowHeader);  
25 - }); 22 + const getIsUnFold = computed(() => !unref(getShowMenu) && !unref(getShowHeader));
26 23
27 - const getIcon = computed(() => {  
28 - return unref(getIsUnFold) ? 'codicon:screen-normal' : 'codicon:screen-full';  
29 - }); 24 + const getIcon = computed(() =>
  25 + unref(getIsUnFold) ? 'codicon:screen-normal' : 'codicon:screen-full'
  26 + );
30 27
31 function handleFold() { 28 function handleFold() {
32 - const isScale = !unref(getShowMenu) && !unref(getShowHeader); 29 + const isUnFold = unref(getIsUnFold);
33 setMenuSetting({ 30 setMenuSetting({
34 - show: isScale,  
35 - hidden: !isScale,  
36 - });  
37 - setHeaderSetting({  
38 - show: isScale, 31 + show: isUnFold,
  32 + hidden: !isUnFold,
39 }); 33 });
  34 + setHeaderSetting({ show: isUnFold });
40 } 35 }
41 36
42 return { prefixCls, getIcon, handleFold }; 37 return { prefixCls, getIcon, handleFold };
src/layouts/default/tabs/components/QuickButton.vue deleted 100644 โ†’ 0
1 -<template>  
2 - <TabContent :type="TabContentEnum.EXTRA_TYPE" :tabItem="$route" />  
3 -</template>  
4 -<script lang="ts">  
5 - import { defineComponent } from 'vue';  
6 -  
7 - import { TabContentEnum } from '../types';  
8 -  
9 - import TabContent from './TabContent.vue';  
10 - export default defineComponent({  
11 - name: 'QuickButton',  
12 - components: {  
13 - TabContent,  
14 - },  
15 - setup() {  
16 - return {  
17 - TabContentEnum,  
18 - };  
19 - },  
20 - });  
21 -</script>  
src/layouts/default/tabs/components/TabContent.vue
1 <template> 1 <template>
2 <Dropdown :dropMenuList="getDropMenuList" :trigger="getTrigger" @menuEvent="handleMenuEvent"> 2 <Dropdown :dropMenuList="getDropMenuList" :trigger="getTrigger" @menuEvent="handleMenuEvent">
3 - <div :class="`${prefixCls}__info`" @contextmenu="handleContext" v-if="isTabs"> 3 + <div :class="`${prefixCls}__info`" @contextmenu="handleContext" v-if="getIsTabs">
4 <span class="ml-1">{{ getTitle }}</span> 4 <span class="ml-1">{{ getTitle }}</span>
5 </div> 5 </div>
6 -  
7 <span :class="`${prefixCls}__extra-quick`" v-else @click="handleContext"> 6 <span :class="`${prefixCls}__extra-quick`" v-else @click="handleContext">
8 <Icon icon="ion:chevron-down" /> 7 <Icon icon="ion:chevron-down" />
9 </span> 8 </span>
@@ -11,18 +10,18 @@ @@ -11,18 +10,18 @@
11 </template> 10 </template>
12 <script lang="ts"> 11 <script lang="ts">
13 import type { PropType } from 'vue'; 12 import type { PropType } from 'vue';
  13 + import type { RouteLocationNormalized } from 'vue-router';
14 14
15 - import { defineComponent, computed } from 'vue'; 15 + import { defineComponent, computed, unref } from 'vue';
16 import { Dropdown } from '/@/components/Dropdown/index'; 16 import { Dropdown } from '/@/components/Dropdown/index';
17 - import Icon from '/@/components/Icon'; 17 + import { Icon } from '/@/components/Icon';
18 18
19 - import { TabContentProps, TabContentEnum } from '../types'; 19 + import { TabContentProps } from '../types';
20 20
21 import { useDesign } from '/@/hooks/web/useDesign'; 21 import { useDesign } from '/@/hooks/web/useDesign';
22 - import { useTabDropdown } from '../useTabDropdown';  
23 import { useI18n } from '/@/hooks/web/useI18n'; 22 import { useI18n } from '/@/hooks/web/useI18n';
  23 + import { useTabDropdown } from '../useTabDropdown';
24 24
25 - import { RouteLocationNormalized } from 'vue-router';  
26 export default defineComponent({ 25 export default defineComponent({
27 name: 'TabContent', 26 name: 'TabContent',
28 components: { Dropdown, Icon }, 27 components: { Dropdown, Icon },
@@ -31,11 +30,7 @@ @@ -31,11 +30,7 @@
31 type: Object as PropType<RouteLocationNormalized>, 30 type: Object as PropType<RouteLocationNormalized>,
32 default: null, 31 default: null,
33 }, 32 },
34 -  
35 - type: {  
36 - type: Number as PropType<TabContentEnum>,  
37 - default: TabContentEnum.TAB_TYPE,  
38 - }, 33 + isExtra: Boolean,
39 }, 34 },
40 setup(props) { 35 setup(props) {
41 const { prefixCls } = useDesign('multiple-tabs-content'); 36 const { prefixCls } = useDesign('multiple-tabs-content');
@@ -43,27 +38,29 @@ @@ -43,27 +38,29 @@
43 38
44 const getTitle = computed(() => { 39 const getTitle = computed(() => {
45 const { tabItem: { meta } = {} } = props; 40 const { tabItem: { meta } = {} } = props;
46 - return meta && t(meta.title); 41 + return meta && t(meta.title as string);
47 }); 42 });
48 43
49 - const {  
50 - getDropMenuList,  
51 - handleMenuEvent,  
52 - handleContextMenu,  
53 - getTrigger,  
54 - isTabs,  
55 - } = useTabDropdown(props as TabContentProps); 44 + const getIsTabs = computed(() => !props.isExtra);
  45 +
  46 + const getTrigger = computed(() => (unref(getIsTabs) ? ['contextmenu'] : ['click']));
56 47
57 - function handleContext(e: ChangeEvent) { 48 + const { getDropMenuList, handleMenuEvent, handleContextMenu } = useTabDropdown(
  49 + props as TabContentProps,
  50 + getIsTabs
  51 + );
  52 +
  53 + function handleContext(e) {
58 props.tabItem && handleContextMenu(props.tabItem)(e); 54 props.tabItem && handleContextMenu(props.tabItem)(e);
59 } 55 }
  56 +
60 return { 57 return {
61 prefixCls, 58 prefixCls,
62 getDropMenuList, 59 getDropMenuList,
63 handleMenuEvent, 60 handleMenuEvent,
64 handleContext, 61 handleContext,
65 getTrigger, 62 getTrigger,
66 - isTabs, 63 + getIsTabs,
67 getTitle, 64 getTitle,
68 }; 65 };
69 }, 66 },
src/layouts/default/tabs/components/TabRedo.vue
1 <template> 1 <template>
2 - <Tooltip :title="t('common.redo')" placement="bottom" :mouseEnterDelay="0.5">  
3 - <span :class="`${prefixCls}__extra-redo`" @click="handleRedo">  
4 - <RedoOutlined :spin="loading" />  
5 - </span>  
6 - </Tooltip> 2 + <span :class="`${prefixCls}__extra-redo`" @click="handleRedo">
  3 + <RedoOutlined :spin="loading" />
  4 + </span>
7 </template> 5 </template>
8 <script lang="ts"> 6 <script lang="ts">
9 import { defineComponent, ref } from 'vue'; 7 import { defineComponent, ref } from 'vue';
10 import { RedoOutlined } from '@ant-design/icons-vue'; 8 import { RedoOutlined } from '@ant-design/icons-vue';
11 import { useDesign } from '/@/hooks/web/useDesign'; 9 import { useDesign } from '/@/hooks/web/useDesign';
12 - import { Tooltip } from 'ant-design-vue';  
13 - import { useI18n } from '/@/hooks/web/useI18n';  
14 import { useTabs } from '/@/hooks/web/useTabs'; 10 import { useTabs } from '/@/hooks/web/useTabs';
15 11
16 export default defineComponent({ 12 export default defineComponent({
17 name: 'TabRedo', 13 name: 'TabRedo',
18 - components: { RedoOutlined, Tooltip }, 14 + components: { RedoOutlined },
19 15
20 setup() { 16 setup() {
21 const loading = ref(false); 17 const loading = ref(false);
  18 +
22 const { prefixCls } = useDesign('multiple-tabs-content'); 19 const { prefixCls } = useDesign('multiple-tabs-content');
23 - const { t } = useI18n();  
24 const { refreshPage } = useTabs(); 20 const { refreshPage } = useTabs();
25 21
26 async function handleRedo() { 22 async function handleRedo() {
@@ -29,9 +25,9 @@ @@ -29,9 +25,9 @@
29 setTimeout(() => { 25 setTimeout(() => {
30 loading.value = false; 26 loading.value = false;
31 // Animation execution time 27 // Animation execution time
32 - }, 1000); 28 + }, 1200);
33 } 29 }
34 - return { prefixCls, t, handleRedo, loading }; 30 + return { prefixCls, handleRedo, loading };
35 }, 31 },
36 }); 32 });
37 </script> 33 </script>
src/layouts/default/tabs/index.less
@@ -8,13 +8,20 @@ html[data-theme=&#39;dark&#39;] { @@ -8,13 +8,20 @@ html[data-theme=&#39;dark&#39;] {
8 } 8 }
9 } 9 }
10 10
  11 +html[data-theme='light'] {
  12 + .@{prefix-cls} {
  13 + .ant-tabs-tab:not(.ant-tabs-tab-active) {
  14 + border: 1px solid #d9d9d9 !important;
  15 + }
  16 + }
  17 +}
  18 +
11 .@{prefix-cls} { 19 .@{prefix-cls} {
12 z-index: 10; 20 z-index: 10;
13 height: @multiple-height + 2; 21 height: @multiple-height + 2;
14 line-height: @multiple-height + 2; 22 line-height: @multiple-height + 2;
15 background: @component-background; 23 background: @component-background;
16 border-bottom: 1px solid @border-color-base; 24 border-bottom: 1px solid @border-color-base;
17 - box-shadow: 0 1px 2px 0 rgba(29, 35, 41, 0.05);  
18 25
19 .ant-tabs-small { 26 .ant-tabs-small {
20 height: @multiple-height; 27 height: @multiple-height;
src/layouts/default/tabs/index.vue
@@ -20,26 +20,26 @@ @@ -20,26 +20,26 @@
20 20
21 <template #tabBarExtraContent v-if="getShowRedo || getShowQuick"> 21 <template #tabBarExtraContent v-if="getShowRedo || getShowQuick">
22 <TabRedo v-if="getShowRedo" /> 22 <TabRedo v-if="getShowRedo" />
23 - <QuickButton v-if="getShowQuick" /> 23 + <TabContent isExtra :tabItem="$route" v-if="getShowQuick" />
24 <FoldButton v-if="getShowFold" /> 24 <FoldButton v-if="getShowFold" />
25 </template> 25 </template>
26 </Tabs> 26 </Tabs>
27 </div> 27 </div>
28 </template> 28 </template>
29 <script lang="ts"> 29 <script lang="ts">
  30 + import type { RouteLocationNormalized } from 'vue-router';
  31 +
30 import { defineComponent, computed, unref, ref } from 'vue'; 32 import { defineComponent, computed, unref, ref } from 'vue';
31 33
32 import { Tabs } from 'ant-design-vue'; 34 import { Tabs } from 'ant-design-vue';
33 import TabContent from './components/TabContent.vue'; 35 import TabContent from './components/TabContent.vue';
34 - import QuickButton from './components/QuickButton.vue';  
35 import FoldButton from './components/FoldButton.vue'; 36 import FoldButton from './components/FoldButton.vue';
36 import TabRedo from './components/TabRedo.vue'; 37 import TabRedo from './components/TabRedo.vue';
37 - import type { RouteLocationNormalized } from 'vue-router';  
38 38
39 import { useGo } from '/@/hooks/web/usePage'; 39 import { useGo } from '/@/hooks/web/usePage';
40 40
41 - import { tabStore } from '/@/store/modules/tab';  
42 - import { userStore } from '/@/store/modules/user'; 41 + import { useMultipleTabStore } from '/@/store/modules/multipleTab';
  42 + import { useUserStore } from '/@/store/modules/user';
43 43
44 import { initAffixTabs, useTabsDrag } from './useMultipleTabs'; 44 import { initAffixTabs, useTabsDrag } from './useMultipleTabs';
45 import { useDesign } from '/@/hooks/web/useDesign'; 45 import { useDesign } from '/@/hooks/web/useDesign';
@@ -48,13 +48,12 @@ @@ -48,13 +48,12 @@
48 import { REDIRECT_NAME } from '/@/router/constant'; 48 import { REDIRECT_NAME } from '/@/router/constant';
49 import { listenerRouteChange } from '/@/logics/mitt/routeChange'; 49 import { listenerRouteChange } from '/@/logics/mitt/routeChange';
50 50
51 - import router from '/@/router'; 51 + import { useRouter } from 'vue-router';
52 52
53 export default defineComponent({ 53 export default defineComponent({
54 name: 'MultipleTabs', 54 name: 'MultipleTabs',
55 components: { 55 components: {
56 - QuickButton,  
57 - TabRedo: TabRedo, 56 + TabRedo,
58 FoldButton, 57 FoldButton,
59 Tabs, 58 Tabs,
60 TabPane: Tabs.TabPane, 59 TabPane: Tabs.TabPane,
@@ -65,12 +64,16 @@ @@ -65,12 +64,16 @@
65 const activeKeyRef = ref(''); 64 const activeKeyRef = ref('');
66 65
67 useTabsDrag(affixTextList); 66 useTabsDrag(affixTextList);
  67 + const tabStore = useMultipleTabStore();
  68 + const userStore = useUserStore();
  69 + const router = useRouter();
  70 +
68 const { prefixCls } = useDesign('multiple-tabs'); 71 const { prefixCls } = useDesign('multiple-tabs');
69 const go = useGo(); 72 const go = useGo();
70 const { getShowQuick, getShowRedo, getShowFold } = useMultipleTabSetting(); 73 const { getShowQuick, getShowRedo, getShowFold } = useMultipleTabSetting();
71 74
72 const getTabsState = computed(() => { 75 const getTabsState = computed(() => {
73 - return tabStore.getTabsState.filter((item) => !item.meta?.hideTab); 76 + return tabStore.getTabList.filter((item) => !item.meta?.hideTab);
74 }); 77 });
75 78
76 const unClose = computed(() => unref(getTabsState).length === 1); 79 const unClose = computed(() => unref(getTabsState).length === 1);
@@ -86,10 +89,11 @@ @@ -86,10 +89,11 @@
86 89
87 listenerRouteChange((route) => { 90 listenerRouteChange((route) => {
88 const { name } = route; 91 const { name } = route;
89 - if (name === REDIRECT_NAME || !route || !userStore.getTokenState) return; 92 + if (name === REDIRECT_NAME || !route || !userStore.getToken) {
  93 + return;
  94 + }
90 95
91 const { path, fullPath, meta = {} } = route; 96 const { path, fullPath, meta = {} } = route;
92 -  
93 const { currentActiveMenu, hideTab } = meta; 97 const { currentActiveMenu, hideTab } = meta;
94 const isHide = !hideTab ? null : currentActiveMenu; 98 const isHide = !hideTab ? null : currentActiveMenu;
95 const p = isHide || fullPath || path; 99 const p = isHide || fullPath || path;
@@ -101,10 +105,11 @@ @@ -101,10 +105,11 @@
101 const findParentRoute = router 105 const findParentRoute = router
102 .getRoutes() 106 .getRoutes()
103 .find((item) => item.path === currentActiveMenu); 107 .find((item) => item.path === currentActiveMenu);
  108 +
104 findParentRoute && 109 findParentRoute &&
105 - tabStore.addTabAction((findParentRoute as unknown) as RouteLocationNormalized); 110 + tabStore.addTab((findParentRoute as unknown) as RouteLocationNormalized);
106 } else { 111 } else {
107 - tabStore.addTabAction(unref(route)); 112 + tabStore.addTab(unref(route));
108 } 113 }
109 }); 114 });
110 115
@@ -116,9 +121,11 @@ @@ -116,9 +121,11 @@
116 // Close the current tab 121 // Close the current tab
117 function handleEdit(targetKey: string) { 122 function handleEdit(targetKey: string) {
118 // Added operation to hide, currently only use delete operation 123 // Added operation to hide, currently only use delete operation
119 - if (unref(unClose)) return; 124 + if (unref(unClose)) {
  125 + return;
  126 + }
120 127
121 - tabStore.closeTabByKeyAction(targetKey); 128 + tabStore.closeTabByKey(targetKey, router);
122 } 129 }
123 return { 130 return {
124 prefixCls, 131 prefixCls,
src/layouts/default/tabs/types.ts
@@ -14,22 +14,12 @@ export interface TabContentProps { @@ -14,22 +14,12 @@ export interface TabContentProps {
14 trigger?: ('click' | 'hover' | 'contextmenu')[]; 14 trigger?: ('click' | 'hover' | 'contextmenu')[];
15 } 15 }
16 16
17 -/**  
18 - * @description: ๅณ้”ฎ๏ผšไธ‹ๆ‹‰่œๅ•ๆ–‡ๅญ—  
19 - */  
20 export enum MenuEventEnum { 17 export enum MenuEventEnum {
21 - // ๅˆทๆ–ฐ  
22 REFRESH_PAGE, 18 REFRESH_PAGE,
23 - // ๅ…ณ้—ญๅฝ“ๅ‰  
24 CLOSE_CURRENT, 19 CLOSE_CURRENT,
25 - // ๅ…ณ้—ญๅทฆไพง  
26 CLOSE_LEFT, 20 CLOSE_LEFT,
27 - // ๅ…ณ้—ญๅณไพง  
28 CLOSE_RIGHT, 21 CLOSE_RIGHT,
29 - // ๅ…ณ้—ญๅ…ถไป–  
30 CLOSE_OTHER, 22 CLOSE_OTHER,
31 - // ๅ…ณ้—ญๆ‰€ๆœ‰  
32 CLOSE_ALL, 23 CLOSE_ALL,
33 - // ๆ”พๅคง  
34 SCALE, 24 SCALE,
35 } 25 }
src/layouts/default/tabs/useMultipleTabs.ts
1 import { toRaw, ref, nextTick } from 'vue'; 1 import { toRaw, ref, nextTick } from 'vue';
2 -import { RouteLocationNormalized } from 'vue-router'; 2 +import type { RouteLocationNormalized } from 'vue-router';
3 import { useDesign } from '/@/hooks/web/useDesign'; 3 import { useDesign } from '/@/hooks/web/useDesign';
4 import { useSortable } from '/@/hooks/web/useSortable'; 4 import { useSortable } from '/@/hooks/web/useSortable';
5 -import router from '/@/router';  
6 -import { tabStore } from '/@/store/modules/tab'; 5 +import { useMultipleTabStore } from '/@/store/modules/multipleTab';
7 import { isNullAndUnDef } from '/@/utils/is'; 6 import { isNullAndUnDef } from '/@/utils/is';
8 import projectSetting from '/@/settings/projectSetting'; 7 import projectSetting from '/@/settings/projectSetting';
  8 +import { useRouter } from 'vue-router';
9 9
10 export function initAffixTabs(): string[] { 10 export function initAffixTabs(): string[] {
11 const affixList = ref<RouteLocationNormalized[]>([]); 11 const affixList = ref<RouteLocationNormalized[]>([]);
  12 +
  13 + const tabStore = useMultipleTabStore();
  14 + const router = useRouter();
12 /** 15 /**
13 * @description: Filter all fixed routes 16 * @description: Filter all fixed routes
14 */ 17 */
@@ -30,7 +33,7 @@ export function initAffixTabs(): string[] { @@ -30,7 +33,7 @@ export function initAffixTabs(): string[] {
30 const affixTabs = filterAffixTabs((router.getRoutes() as unknown) as RouteLocationNormalized[]); 33 const affixTabs = filterAffixTabs((router.getRoutes() as unknown) as RouteLocationNormalized[]);
31 affixList.value = affixTabs; 34 affixList.value = affixTabs;
32 for (const tab of affixTabs) { 35 for (const tab of affixTabs) {
33 - tabStore.addTabAction(({ 36 + tabStore.addTab(({
34 meta: tab.meta, 37 meta: tab.meta,
35 name: tab.name, 38 name: tab.name,
36 path: tab.path, 39 path: tab.path,
@@ -39,6 +42,7 @@ export function initAffixTabs(): string[] { @@ -39,6 +42,7 @@ export function initAffixTabs(): string[] {
39 } 42 }
40 43
41 let isAddAffix = false; 44 let isAddAffix = false;
  45 +
42 if (!isAddAffix) { 46 if (!isAddAffix) {
43 addAffixTabs(); 47 addAffixTabs();
44 isAddAffix = true; 48 isAddAffix = true;
@@ -47,8 +51,8 @@ export function initAffixTabs(): string[] { @@ -47,8 +51,8 @@ export function initAffixTabs(): string[] {
47 } 51 }
48 52
49 export function useTabsDrag(affixTextList: string[]) { 53 export function useTabsDrag(affixTextList: string[]) {
  54 + const tabStore = useMultipleTabStore();
50 const { multiTabsSetting } = projectSetting; 55 const { multiTabsSetting } = projectSetting;
51 -  
52 const { prefixCls } = useDesign('multiple-tabs'); 56 const { prefixCls } = useDesign('multiple-tabs');
53 nextTick(() => { 57 nextTick(() => {
54 if (!multiTabsSetting.canDrag) return; 58 if (!multiTabsSetting.canDrag) return;
@@ -66,7 +70,7 @@ export function useTabsDrag(affixTextList: string[]) { @@ -66,7 +70,7 @@ export function useTabsDrag(affixTextList: string[]) {
66 return; 70 return;
67 } 71 }
68 72
69 - tabStore.commitSortTabs({ oldIndex, newIndex }); 73 + tabStore.sortTabs(oldIndex, newIndex);
70 }, 74 },
71 }); 75 });
72 initSortable(); 76 initSortable();
src/layouts/default/tabs/useTabDropdown.ts
1 import type { TabContentProps } from './types'; 1 import type { TabContentProps } from './types';
2 import type { DropMenu } from '/@/components/Dropdown'; 2 import type { DropMenu } from '/@/components/Dropdown';
  3 +import type { ComputedRef } from 'vue';
3 4
4 import { computed, unref, reactive } from 'vue'; 5 import { computed, unref, reactive } from 'vue';
5 -import { TabContentEnum, MenuEventEnum } from './types';  
6 -import { tabStore } from '/@/store/modules/tab';  
7 -import router from '/@/router';  
8 -import { RouteLocationNormalized } from 'vue-router'; 6 +import { MenuEventEnum } from './types';
  7 +import { useMultipleTabStore } from '/@/store/modules/multipleTab';
  8 +import { RouteLocationNormalized, useRouter } from 'vue-router';
9 import { useTabs } from '/@/hooks/web/useTabs'; 9 import { useTabs } from '/@/hooks/web/useTabs';
10 import { useI18n } from '/@/hooks/web/useI18n'; 10 import { useI18n } from '/@/hooks/web/useI18n';
11 11
12 -const { t } = useI18n();  
13 -  
14 -export function useTabDropdown(tabContentProps: TabContentProps) { 12 +export function useTabDropdown(tabContentProps: TabContentProps, getIsTabs: ComputedRef<boolean>) {
15 const state = reactive({ 13 const state = reactive({
16 current: null as Nullable<RouteLocationNormalized>, 14 current: null as Nullable<RouteLocationNormalized>,
17 currentIndex: 0, 15 currentIndex: 0,
18 }); 16 });
19 17
20 - const { currentRoute } = router;  
21 -  
22 - const isTabs = computed(() => tabContentProps.type === TabContentEnum.TAB_TYPE); 18 + const { t } = useI18n();
  19 + const tabStore = useMultipleTabStore();
  20 + const { currentRoute } = useRouter();
  21 + const { refreshPage, closeAll, close, closeLeft, closeOther, closeRight } = useTabs();
23 22
24 - const getCurrentTab = computed( 23 + const getTargetTab = computed(
25 (): RouteLocationNormalized => { 24 (): RouteLocationNormalized => {
26 - return unref(isTabs) ? tabContentProps.tabItem : unref(currentRoute); 25 + return unref(getIsTabs) ? tabContentProps.tabItem : unref(currentRoute);
27 } 26 }
28 ); 27 );
29 28
@@ -31,8 +30,10 @@ export function useTabDropdown(tabContentProps: TabContentProps) { @@ -31,8 +30,10 @@ export function useTabDropdown(tabContentProps: TabContentProps) {
31 * @description: drop-down list 30 * @description: drop-down list
32 */ 31 */
33 const getDropMenuList = computed(() => { 32 const getDropMenuList = computed(() => {
34 - if (!unref(getCurrentTab)) return;  
35 - const { meta } = unref(getCurrentTab); 33 + if (!unref(getTargetTab)) {
  34 + return;
  35 + }
  36 + const { meta } = unref(getTargetTab);
36 const { path } = unref(currentRoute); 37 const { path } = unref(currentRoute);
37 38
38 // Refresh button 39 // Refresh button
@@ -42,11 +43,11 @@ export function useTabDropdown(tabContentProps: TabContentProps) { @@ -42,11 +43,11 @@ export function useTabDropdown(tabContentProps: TabContentProps) {
42 // Close left 43 // Close left
43 const closeLeftDisabled = index === 0; 44 const closeLeftDisabled = index === 0;
44 45
45 - const disabled = tabStore.getTabsState.length === 1; 46 + const disabled = tabStore.getTabList.length === 1;
46 47
47 // Close right 48 // Close right
48 const closeRightDisabled = 49 const closeRightDisabled =
49 - index === tabStore.getTabsState.length - 1 && tabStore.getLastDragEndIndexState >= 0; 50 + index === tabStore.getTabList.length - 1 && tabStore.getLastDragEndIndex >= 0;
50 const dropMenuList: DropMenu[] = [ 51 const dropMenuList: DropMenu[] = [
51 { 52 {
52 icon: 'ion:reload-sharp', 53 icon: 'ion:reload-sharp',
@@ -58,7 +59,7 @@ export function useTabDropdown(tabContentProps: TabContentProps) { @@ -58,7 +59,7 @@ export function useTabDropdown(tabContentProps: TabContentProps) {
58 icon: 'clarity:close-line', 59 icon: 'clarity:close-line',
59 event: MenuEventEnum.CLOSE_CURRENT, 60 event: MenuEventEnum.CLOSE_CURRENT,
60 text: t('layout.multipleTab.close'), 61 text: t('layout.multipleTab.close'),
61 - disabled: meta?.affix || disabled, 62 + disabled: !!meta?.affix || disabled,
62 divider: true, 63 divider: true,
63 }, 64 },
64 { 65 {
@@ -92,15 +93,13 @@ export function useTabDropdown(tabContentProps: TabContentProps) { @@ -92,15 +93,13 @@ export function useTabDropdown(tabContentProps: TabContentProps) {
92 return dropMenuList; 93 return dropMenuList;
93 }); 94 });
94 95
95 - const getTrigger = computed(() => {  
96 - return unref(isTabs) ? ['contextmenu'] : ['click'];  
97 - });  
98 -  
99 function handleContextMenu(tabItem: RouteLocationNormalized) { 96 function handleContextMenu(tabItem: RouteLocationNormalized) {
100 return (e: Event) => { 97 return (e: Event) => {
101 - if (!tabItem) return; 98 + if (!tabItem) {
  99 + return;
  100 + }
102 e?.preventDefault(); 101 e?.preventDefault();
103 - const index = tabStore.getTabsState.findIndex((tab) => tab.path === tabItem.path); 102 + const index = tabStore.getTabList.findIndex((tab) => tab.path === tabItem.path);
104 state.current = tabItem; 103 state.current = tabItem;
105 state.currentIndex = index; 104 state.currentIndex = index;
106 }; 105 };
@@ -108,12 +107,8 @@ export function useTabDropdown(tabContentProps: TabContentProps) { @@ -108,12 +107,8 @@ export function useTabDropdown(tabContentProps: TabContentProps) {
108 107
109 // Handle right click event 108 // Handle right click event
110 function handleMenuEvent(menu: DropMenu): void { 109 function handleMenuEvent(menu: DropMenu): void {
111 - const { refreshPage, closeAll, close, closeLeft, closeOther, closeRight } = useTabs();  
112 const { event } = menu; 110 const { event } = menu;
113 switch (event) { 111 switch (event) {
114 - case MenuEventEnum.SCALE:  
115 - scaleScreen();  
116 - break;  
117 case MenuEventEnum.REFRESH_PAGE: 112 case MenuEventEnum.REFRESH_PAGE:
118 // refresh page 113 // refresh page
119 refreshPage(); 114 refreshPage();
@@ -140,5 +135,5 @@ export function useTabDropdown(tabContentProps: TabContentProps) { @@ -140,5 +135,5 @@ export function useTabDropdown(tabContentProps: TabContentProps) {
140 break; 135 break;
141 } 136 }
142 } 137 }
143 - return { getDropMenuList, handleMenuEvent, handleContextMenu, getTrigger, isTabs }; 138 + return { getDropMenuList, handleMenuEvent, handleContextMenu };
144 } 139 }
src/layouts/iframe/useFrameKeepAlive.ts
@@ -2,18 +2,19 @@ import type { AppRouteRecordRaw } from &#39;/@/router/types&#39;; @@ -2,18 +2,19 @@ import type { AppRouteRecordRaw } from &#39;/@/router/types&#39;;
2 2
3 import { computed, toRaw, unref } from 'vue'; 3 import { computed, toRaw, unref } from 'vue';
4 4
5 -import { tabStore } from '/@/store/modules/tab'; 5 +import { useMultipleTabStore } from '/@/store/modules/multipleTab';
6 6
7 import { uniqBy } from 'lodash-es'; 7 import { uniqBy } from 'lodash-es';
8 8
9 import { useMultipleTabSetting } from '/@/hooks/setting/useMultipleTabSetting'; 9 import { useMultipleTabSetting } from '/@/hooks/setting/useMultipleTabSetting';
10 10
11 -import router from '/@/router'; 11 +import { useRouter } from 'vue-router';
12 12
13 export function useFrameKeepAlive() { 13 export function useFrameKeepAlive() {
  14 + const router = useRouter();
14 const { currentRoute } = router; 15 const { currentRoute } = router;
15 const { getShowMultipleTab } = useMultipleTabSetting(); 16 const { getShowMultipleTab } = useMultipleTabSetting();
16 - 17 + const tabStore = useMultipleTabStore();
17 const getFramePages = computed(() => { 18 const getFramePages = computed(() => {
18 const ret = 19 const ret =
19 getAllFramePages((toRaw(router.getRoutes()) as unknown) as AppRouteRecordRaw[]) || []; 20 getAllFramePages((toRaw(router.getRoutes()) as unknown) as AppRouteRecordRaw[]) || [];
@@ -21,7 +22,7 @@ export function useFrameKeepAlive() { @@ -21,7 +22,7 @@ export function useFrameKeepAlive() {
21 }); 22 });
22 23
23 const getOpenTabList = computed((): string[] => { 24 const getOpenTabList = computed((): string[] => {
24 - return tabStore.getTabsState.reduce((prev: string[], next) => { 25 + return tabStore.getTabList.reduce((prev: string[], next) => {
25 if (next.meta && Reflect.has(next.meta, 'frameSrc')) { 26 if (next.meta && Reflect.has(next.meta, 'frameSrc')) {
26 prev.push(next.name as string); 27 prev.push(next.name as string);
27 } 28 }
src/layouts/page/index.vue
@@ -35,13 +35,14 @@ @@ -35,13 +35,14 @@
35 import { useMultipleTabSetting } from '/@/hooks/setting/useMultipleTabSetting'; 35 import { useMultipleTabSetting } from '/@/hooks/setting/useMultipleTabSetting';
36 import { getTransitionName } from './transition'; 36 import { getTransitionName } from './transition';
37 37
38 - import { useStore } from 'vuex'; 38 + import { useMultipleTabStore } from '/@/store/modules/multipleTab';
39 39
40 export default defineComponent({ 40 export default defineComponent({
41 name: 'PageLayout', 41 name: 'PageLayout',
42 components: { FrameLayout }, 42 components: { FrameLayout },
43 setup() { 43 setup() {
44 const { getShowMultipleTab } = useMultipleTabSetting(); 44 const { getShowMultipleTab } = useMultipleTabSetting();
  45 + const tabStore = useMultipleTabStore();
45 46
46 const { getOpenKeepAlive, getCanEmbedIFramePage } = useRootSetting(); 47 const { getOpenKeepAlive, getCanEmbedIFramePage } = useRootSetting();
47 48
@@ -49,15 +50,11 @@ @@ -49,15 +50,11 @@
49 50
50 const openCache = computed(() => unref(getOpenKeepAlive) && unref(getShowMultipleTab)); 51 const openCache = computed(() => unref(getOpenKeepAlive) && unref(getShowMultipleTab));
51 52
52 - const { getters } = useStore();  
53 -  
54 const getCaches = computed((): string[] => { 53 const getCaches = computed((): string[] => {
55 if (!unref(getOpenKeepAlive)) { 54 if (!unref(getOpenKeepAlive)) {
56 return []; 55 return [];
57 } 56 }
58 - // TODO The useStore is used here mainly to solve the problem of circular dependency hot update  
59 - const cacheTabs = getters['app-tab/getCachedTabsState'];  
60 - return cacheTabs; 57 + return tabStore.getCachedTabList;
61 }); 58 });
62 59
63 return { 60 return {
src/locales/setupI18n.ts
@@ -3,14 +3,15 @@ import type { I18n, I18nOptions } from &#39;vue-i18n&#39;; @@ -3,14 +3,15 @@ import type { I18n, I18nOptions } from &#39;vue-i18n&#39;;
3 3
4 import { createI18n } from 'vue-i18n'; 4 import { createI18n } from 'vue-i18n';
5 5
6 -import { localeStore } from '/@/store/modules/locale';  
7 import { localeSetting } from '/@/settings/localeSetting'; 6 import { localeSetting } from '/@/settings/localeSetting';
  7 +import { useLocaleStoreWithOut } from '/@/store/modules/locale';
8 8
9 const { fallback, availableLocales } = localeSetting; 9 const { fallback, availableLocales } = localeSetting;
10 10
11 export let i18n: ReturnType<typeof createI18n>; 11 export let i18n: ReturnType<typeof createI18n>;
12 12
13 async function createI18nOptions(): Promise<I18nOptions> { 13 async function createI18nOptions(): Promise<I18nOptions> {
  14 + const localeStore = useLocaleStoreWithOut();
14 const locale = localeStore.getLocale; 15 const locale = localeStore.getLocale;
15 const defaultLocal = await import(`./lang/${locale}.ts`); 16 const defaultLocal = await import(`./lang/${locale}.ts`);
16 const message = defaultLocal.default?.message ?? {}; 17 const message = defaultLocal.default?.message ?? {};
src/locales/useLocale.ts
@@ -6,7 +6,7 @@ import type { LocaleType } from &#39;/#/config&#39;; @@ -6,7 +6,7 @@ import type { LocaleType } from &#39;/#/config&#39;;
6 import moment from 'moment'; 6 import moment from 'moment';
7 7
8 import { i18n } from './setupI18n'; 8 import { i18n } from './setupI18n';
9 -import { localeStore } from '/@/store/modules/locale'; 9 +import { useLocaleStoreWithOut } from '/@/store/modules/locale';
10 import { unref, computed } from 'vue'; 10 import { unref, computed } from 'vue';
11 11
12 interface LangModule { 12 interface LangModule {
@@ -18,6 +18,8 @@ interface LangModule { @@ -18,6 +18,8 @@ interface LangModule {
18 const loadLocalePool: LocaleType[] = []; 18 const loadLocalePool: LocaleType[] = [];
19 19
20 function setI18nLanguage(locale: LocaleType) { 20 function setI18nLanguage(locale: LocaleType) {
  21 + const localeStore = useLocaleStoreWithOut();
  22 +
21 if (i18n.mode === 'legacy') { 23 if (i18n.mode === 'legacy') {
22 i18n.global.locale = locale; 24 i18n.global.locale = locale;
23 } else { 25 } else {
@@ -28,6 +30,7 @@ function setI18nLanguage(locale: LocaleType) { @@ -28,6 +30,7 @@ function setI18nLanguage(locale: LocaleType) {
28 } 30 }
29 31
30 export function useLocale() { 32 export function useLocale() {
  33 + const localeStore = useLocaleStoreWithOut();
31 const getLocale = computed(() => localeStore.getLocale); 34 const getLocale = computed(() => localeStore.getLocale);
32 const getShowLocalePicker = computed(() => localeStore.getShowPicker); 35 const getShowLocalePicker = computed(() => localeStore.getShowPicker);
33 36
@@ -40,7 +43,9 @@ export function useLocale() { @@ -40,7 +43,9 @@ export function useLocale() {
40 async function changeLocale(locale: LocaleType) { 43 async function changeLocale(locale: LocaleType) {
41 const globalI18n = i18n.global; 44 const globalI18n = i18n.global;
42 const currentLocale = unref(globalI18n.locale); 45 const currentLocale = unref(globalI18n.locale);
43 - if (currentLocale === locale) return locale; 46 + if (currentLocale === locale) {
  47 + return locale;
  48 + }
44 49
45 if (loadLocalePool.includes(locale)) { 50 if (loadLocalePool.includes(locale)) {
46 setI18nLanguage(locale); 51 setI18nLanguage(locale);
src/logics/error-handle/index.ts
@@ -2,7 +2,10 @@ @@ -2,7 +2,10 @@
2 * Used to configure the global error handling function, which can monitor vue errors, script errors, static resource errors and Promise errors 2 * Used to configure the global error handling function, which can monitor vue errors, script errors, static resource errors and Promise errors
3 */ 3 */
4 4
5 -import { errorStore, ErrorInfo } from '/@/store/modules/error'; 5 +import type { ErrorLogInfo } from '/#/store';
  6 +
  7 +import { useErrorLogStoreWithOut } from '/@/store/modules/errorLog';
  8 +
6 import { ErrorTypeEnum } from '/@/enums/exceptionEnum'; 9 import { ErrorTypeEnum } from '/@/enums/exceptionEnum';
7 import { App } from 'vue'; 10 import { App } from 'vue';
8 import projectSetting from '/@/settings/projectSetting'; 11 import projectSetting from '/@/settings/projectSetting';
@@ -61,8 +64,9 @@ function formatComponentName(vm: any) { @@ -61,8 +64,9 @@ function formatComponentName(vm: any) {
61 */ 64 */
62 65
63 function vueErrorHandler(err: Error, vm: any, info: string) { 66 function vueErrorHandler(err: Error, vm: any, info: string) {
  67 + const errorLogStore = useErrorLogStoreWithOut();
64 const { name, path } = formatComponentName(vm); 68 const { name, path } = formatComponentName(vm);
65 - errorStore.commitErrorInfoState({ 69 + errorLogStore.addErrorLogInfo({
66 type: ErrorTypeEnum.VUE, 70 type: ErrorTypeEnum.VUE,
67 name, 71 name,
68 file: path, 72 file: path,
@@ -86,7 +90,7 @@ export function scriptErrorHandler( @@ -86,7 +90,7 @@ export function scriptErrorHandler(
86 if (event === 'Script error.' && !source) { 90 if (event === 'Script error.' && !source) {
87 return false; 91 return false;
88 } 92 }
89 - const errorInfo: Partial<ErrorInfo> = {}; 93 + const errorInfo: Partial<ErrorLogInfo> = {};
90 colno = colno || (window.event && (window.event as any).errorCharacter) || 0; 94 colno = colno || (window.event && (window.event as any).errorCharacter) || 0;
91 errorInfo.message = event as string; 95 errorInfo.message = event as string;
92 if (error?.stack) { 96 if (error?.stack) {
@@ -95,13 +99,14 @@ export function scriptErrorHandler( @@ -95,13 +99,14 @@ export function scriptErrorHandler(
95 errorInfo.stack = ''; 99 errorInfo.stack = '';
96 } 100 }
97 const name = source ? source.substr(source.lastIndexOf('/') + 1) : 'script'; 101 const name = source ? source.substr(source.lastIndexOf('/') + 1) : 'script';
98 - errorStore.commitErrorInfoState({ 102 + const errorLogStore = useErrorLogStoreWithOut();
  103 + errorLogStore.addErrorLogInfo({
99 type: ErrorTypeEnum.SCRIPT, 104 type: ErrorTypeEnum.SCRIPT,
100 name: name, 105 name: name,
101 file: source as string, 106 file: source as string,
102 detail: 'lineno' + lineno, 107 detail: 'lineno' + lineno,
103 url: window.location.href, 108 url: window.location.href,
104 - ...(errorInfo as Pick<ErrorInfo, 'message' | 'stack'>), 109 + ...(errorInfo as Pick<ErrorLogInfo, 'message' | 'stack'>),
105 }); 110 });
106 return true; 111 return true;
107 } 112 }
@@ -112,8 +117,9 @@ export function scriptErrorHandler( @@ -112,8 +117,9 @@ export function scriptErrorHandler(
112 function registerPromiseErrorHandler() { 117 function registerPromiseErrorHandler() {
113 window.addEventListener( 118 window.addEventListener(
114 'unhandledrejection', 119 'unhandledrejection',
115 - function (event: any) {  
116 - errorStore.commitErrorInfoState({ 120 + function (event) {
  121 + const errorLogStore = useErrorLogStoreWithOut();
  122 + errorLogStore.addErrorLogInfo({
117 type: ErrorTypeEnum.PROMISE, 123 type: ErrorTypeEnum.PROMISE,
118 name: 'Promise Error!', 124 name: 'Promise Error!',
119 file: 'none', 125 file: 'none',
@@ -136,10 +142,10 @@ function registerResourceErrorHandler() { @@ -136,10 +142,10 @@ function registerResourceErrorHandler() {
136 'error', 142 'error',
137 function (e: Event) { 143 function (e: Event) {
138 const target = e.target ? e.target : (e.srcElement as any); 144 const target = e.target ? e.target : (e.srcElement as any);
139 -  
140 - errorStore.commitErrorInfoState({ 145 + const errorLogStore = useErrorLogStoreWithOut();
  146 + errorLogStore.addErrorLogInfo({
141 type: ErrorTypeEnum.RESOURCE, 147 type: ErrorTypeEnum.RESOURCE,
142 - name: 'Resouce Error!', 148 + name: 'Resource Error!',
143 file: (e.target || ({} as any)).currentSrc, 149 file: (e.target || ({} as any)).currentSrc,
144 detail: JSON.stringify({ 150 detail: JSON.stringify({
145 tagName: target.localName, 151 tagName: target.localName,
@@ -147,7 +153,7 @@ function registerResourceErrorHandler() { @@ -147,7 +153,7 @@ function registerResourceErrorHandler() {
147 type: e.type, 153 type: e.type,
148 }), 154 }),
149 url: window.location.href, 155 url: window.location.href,
150 - stack: 'resouce is not found', 156 + stack: 'resource is not found',
151 message: (e.target || ({} as any)).localName + ' is load error', 157 message: (e.target || ({} as any)).localName + ' is load error',
152 }); 158 });
153 }, 159 },
@@ -161,7 +167,9 @@ function registerResourceErrorHandler() { @@ -161,7 +167,9 @@ function registerResourceErrorHandler() {
161 */ 167 */
162 export function setupErrorHandle(app: App) { 168 export function setupErrorHandle(app: App) {
163 const { useErrorHandle } = projectSetting; 169 const { useErrorHandle } = projectSetting;
164 - if (!useErrorHandle) return; 170 + if (!useErrorHandle) {
  171 + return;
  172 + }
165 // Vue exception monitoring; 173 // Vue exception monitoring;
166 app.config.errorHandler = vueErrorHandler; 174 app.config.errorHandler = vueErrorHandler;
167 175
src/logics/initAppConfig.ts
@@ -12,18 +12,20 @@ import { updateGrayMode } from &#39;/@/logics/theme/updateGrayMode&#39;; @@ -12,18 +12,20 @@ import { updateGrayMode } from &#39;/@/logics/theme/updateGrayMode&#39;;
12 import { updateDarkTheme } from '/@/logics/theme/dark'; 12 import { updateDarkTheme } from '/@/logics/theme/dark';
13 import { changeTheme } from '/@/logics/theme'; 13 import { changeTheme } from '/@/logics/theme';
14 14
15 -import { appStore } from '/@/store/modules/app';  
16 -import { localeStore } from '/@/store/modules/locale'; 15 +import { useAppStore } from '/@/store/modules/app';
  16 +import { useLocaleStore } from '/@/store/modules/locale';
17 17
18 import { getCommonStoragePrefix, getStorageShortName } from '/@/utils/env'; 18 import { getCommonStoragePrefix, getStorageShortName } from '/@/utils/env';
19 19
20 import { primaryColor } from '../../build/config/themeConfig'; 20 import { primaryColor } from '../../build/config/themeConfig';
21 import { Persistent } from '/@/utils/cache/persistent'; 21 import { Persistent } from '/@/utils/cache/persistent';
22 import { deepMerge } from '/@/utils'; 22 import { deepMerge } from '/@/utils';
23 -import { ThemeEnum } from '../enums/appEnum'; 23 +import { ThemeEnum } from '/@/enums/appEnum';
24 24
25 // Initial project configuration 25 // Initial project configuration
26 export function initAppConfigStore() { 26 export function initAppConfigStore() {
  27 + const localeStore = useLocaleStore();
  28 + const appStore = useAppStore();
27 let projCfg: ProjectConfig = Persistent.getLocal(PROJ_CFG_KEY) as ProjectConfig; 29 let projCfg: ProjectConfig = Persistent.getLocal(PROJ_CFG_KEY) as ProjectConfig;
28 projCfg = deepMerge(projectSetting, projCfg || {}); 30 projCfg = deepMerge(projectSetting, projCfg || {});
29 const darkMode = appStore.getDarkMode; 31 const darkMode = appStore.getDarkMode;
@@ -45,7 +47,7 @@ export function initAppConfigStore() { @@ -45,7 +47,7 @@ export function initAppConfigStore() {
45 } catch (error) { 47 } catch (error) {
46 console.log(error); 48 console.log(error);
47 } 49 }
48 - appStore.commitProjectConfigState(projCfg); 50 + appStore.setProjectConfig(projCfg);
49 51
50 // init dark mode 52 // init dark mode
51 updateDarkTheme(darkMode); 53 updateDarkTheme(darkMode);
src/logics/theme/updateBackground.ts
1 import { colorIsDark, lighten, darken } from '/@/utils/color'; 1 import { colorIsDark, lighten, darken } from '/@/utils/color';
2 -import { appStore } from '/@/store/modules/app'; 2 +import { useAppStore } from '/@/store/modules/app';
3 import { ThemeEnum } from '/@/enums/appEnum'; 3 import { ThemeEnum } from '/@/enums/appEnum';
4 import { setCssVar } from './util'; 4 import { setCssVar } from './util';
5 5
@@ -16,12 +16,13 @@ const SIDER_LIGHTEN_BG_COLOR = &#39;--sider-dark-lighten-bg-color&#39;; @@ -16,12 +16,13 @@ const SIDER_LIGHTEN_BG_COLOR = &#39;--sider-dark-lighten-bg-color&#39;;
16 * @param color 16 * @param color
17 */ 17 */
18 export function updateHeaderBgColor(color?: string) { 18 export function updateHeaderBgColor(color?: string) {
  19 + const appStore = useAppStore();
19 const darkMode = appStore.getDarkMode === ThemeEnum.DARK; 20 const darkMode = appStore.getDarkMode === ThemeEnum.DARK;
20 if (!color) { 21 if (!color) {
21 if (darkMode) { 22 if (darkMode) {
22 color = '#151515'; 23 color = '#151515';
23 } else { 24 } else {
24 - color = appStore.getProjectConfig.headerSetting.bgColor; 25 + color = appStore.getHeaderSetting.bgColor;
25 } 26 }
26 } 27 }
27 // bg color 28 // bg color
@@ -35,7 +36,7 @@ export function updateHeaderBgColor(color?: string) { @@ -35,7 +36,7 @@ export function updateHeaderBgColor(color?: string) {
35 // Determine the depth of the color value and automatically switch the theme 36 // Determine the depth of the color value and automatically switch the theme
36 const isDark = colorIsDark(color!); 37 const isDark = colorIsDark(color!);
37 38
38 - appStore.commitProjectConfigState({ 39 + appStore.setProjectConfig({
39 headerSetting: { 40 headerSetting: {
40 theme: isDark || darkMode ? ThemeEnum.DARK : ThemeEnum.LIGHT, 41 theme: isDark || darkMode ? ThemeEnum.DARK : ThemeEnum.LIGHT,
41 }, 42 },
@@ -47,13 +48,15 @@ export function updateHeaderBgColor(color?: string) { @@ -47,13 +48,15 @@ export function updateHeaderBgColor(color?: string) {
47 * @param color bg color 48 * @param color bg color
48 */ 49 */
49 export function updateSidebarBgColor(color?: string) { 50 export function updateSidebarBgColor(color?: string) {
  51 + const appStore = useAppStore();
  52 +
50 // if (!isHexColor(color)) return; 53 // if (!isHexColor(color)) return;
51 const darkMode = appStore.getDarkMode === ThemeEnum.DARK; 54 const darkMode = appStore.getDarkMode === ThemeEnum.DARK;
52 if (!color) { 55 if (!color) {
53 if (darkMode) { 56 if (darkMode) {
54 color = '#212121'; 57 color = '#212121';
55 } else { 58 } else {
56 - color = appStore.getProjectConfig.menuSetting.bgColor; 59 + color = appStore.getMenuSetting.bgColor;
57 } 60 }
58 } 61 }
59 setCssVar(SIDER_DARK_BG_COLOR, color); 62 setCssVar(SIDER_DARK_BG_COLOR, color);
@@ -64,7 +67,7 @@ export function updateSidebarBgColor(color?: string) { @@ -64,7 +67,7 @@ export function updateSidebarBgColor(color?: string) {
64 // Only when the background color is #fff, the theme of the menu will be changed to light 67 // Only when the background color is #fff, the theme of the menu will be changed to light
65 const isLight = ['#fff', '#ffffff'].includes(color!.toLowerCase()); 68 const isLight = ['#fff', '#ffffff'].includes(color!.toLowerCase());
66 69
67 - appStore.commitProjectConfigState({ 70 + appStore.setProjectConfig({
68 menuSetting: { 71 menuSetting: {
69 theme: isLight && !darkMode ? ThemeEnum.LIGHT : ThemeEnum.DARK, 72 theme: isLight && !darkMode ? ThemeEnum.LIGHT : ThemeEnum.DARK,
70 }, 73 },
src/main.ts
@@ -5,15 +5,13 @@ import { createApp } from &#39;vue&#39;; @@ -5,15 +5,13 @@ import { createApp } from &#39;vue&#39;;
5 import App from './App.vue'; 5 import App from './App.vue';
6 6
7 import router, { setupRouter } from '/@/router'; 7 import router, { setupRouter } from '/@/router';
  8 +import { setupRouterGuard } from '/@/router/guard';
8 import { setupStore } from '/@/store'; 9 import { setupStore } from '/@/store';
9 import { setupErrorHandle } from '/@/logics/error-handle'; 10 import { setupErrorHandle } from '/@/logics/error-handle';
10 import { setupGlobDirectives } from '/@/directives'; 11 import { setupGlobDirectives } from '/@/directives';
11 import { setupI18n } from '/@/locales/setupI18n'; 12 import { setupI18n } from '/@/locales/setupI18n';
12 import { registerGlobComp } from '/@/components/registerGlobComp'; 13 import { registerGlobComp } from '/@/components/registerGlobComp';
13 14
14 -// router-guard  
15 -import '/@/router/guard';  
16 -  
17 // Register icon Sprite 15 // Register icon Sprite
18 import 'vite-plugin-svg-icons/register'; 16 import 'vite-plugin-svg-icons/register';
19 17
@@ -27,6 +25,10 @@ if (import.meta.env.DEV) { @@ -27,6 +25,10 @@ if (import.meta.env.DEV) {
27 25
28 (async () => { 26 (async () => {
29 const app = createApp(App); 27 const app = createApp(App);
  28 +
  29 + // Configure vuex store
  30 + setupStore(app);
  31 +
30 // Register global components 32 // Register global components
31 registerGlobComp(app); 33 registerGlobComp(app);
32 34
@@ -36,8 +38,8 @@ if (import.meta.env.DEV) { @@ -36,8 +38,8 @@ if (import.meta.env.DEV) {
36 // Configure routing 38 // Configure routing
37 setupRouter(app); 39 setupRouter(app);
38 40
39 - // Configure vuex store  
40 - setupStore(app); 41 + // router-guard
  42 + setupRouterGuard();
41 43
42 // Register global directive 44 // Register global directive
43 setupGlobDirectives(app); 45 setupGlobDirectives(app);
src/router/constant.ts
@@ -20,13 +20,3 @@ export const getParentLayout = (_name?: string) =&gt; { @@ -20,13 +20,3 @@ export const getParentLayout = (_name?: string) =&gt; {
20 }); 20 });
21 }); 21 });
22 }; 22 };
23 -  
24 -// export const getParentLayout = (name: string) => {  
25 -// return () =>  
26 -// new Promise((resolve) => {  
27 -// resolve({  
28 -// ...ParentLayout,  
29 -// name,  
30 -// });  
31 -// });  
32 -// };  
src/router/guard/index.ts
@@ -9,11 +9,13 @@ import { createHttpGuard } from &#39;./httpGuard&#39;; @@ -9,11 +9,13 @@ import { createHttpGuard } from &#39;./httpGuard&#39;;
9 import { createPageGuard } from './pageGuard'; 9 import { createPageGuard } from './pageGuard';
10 import { createStateGuard } from './stateGuard'; 10 import { createStateGuard } from './stateGuard';
11 11
12 -createPageGuard(router);  
13 -createPageLoadingGuard(router);  
14 -createHttpGuard(router);  
15 -createScrollGuard(router);  
16 -createMessageGuard(router);  
17 -createProgressGuard(router);  
18 -createPermissionGuard(router);  
19 -createStateGuard(router); 12 +export function setupRouterGuard() {
  13 + createPageGuard(router);
  14 + createPageLoadingGuard(router);
  15 + createHttpGuard(router);
  16 + createScrollGuard(router);
  17 + createMessageGuard(router);
  18 + createProgressGuard(router);
  19 + createPermissionGuard(router);
  20 + createStateGuard(router);
  21 +}
src/router/guard/pageLoadingGuard.ts
1 import type { Router } from 'vue-router'; 1 import type { Router } from 'vue-router';
2 -import { appStore } from '/@/store/modules/app';  
3 -import { userStore } from '/@/store/modules/user'; 2 +import { useAppStoreWidthOut } from '/@/store/modules/app';
  3 +import { useUserStoreWidthOut } from '/@/store/modules/user';
4 import { useTransitionSetting } from '/@/hooks/setting/useTransitionSetting'; 4 import { useTransitionSetting } from '/@/hooks/setting/useTransitionSetting';
5 import { unref } from 'vue'; 5 import { unref } from 'vue';
6 6
7 -const { getOpenPageLoading } = useTransitionSetting();  
8 export function createPageLoadingGuard(router: Router) { 7 export function createPageLoadingGuard(router: Router) {
  8 + const userStore = useUserStoreWidthOut();
  9 + const appStore = useAppStoreWidthOut();
  10 + const { getOpenPageLoading } = useTransitionSetting();
9 router.beforeEach(async (to) => { 11 router.beforeEach(async (to) => {
10 - if (!userStore.getTokenState) { 12 + if (!userStore.getToken) {
11 return true; 13 return true;
12 } 14 }
13 if (to.meta.loaded) { 15 if (to.meta.loaded) {
@@ -24,7 +26,7 @@ export function createPageLoadingGuard(router: Router) { @@ -24,7 +26,7 @@ export function createPageLoadingGuard(router: Router) {
24 router.afterEach(async () => { 26 router.afterEach(async () => {
25 if (unref(getOpenPageLoading)) { 27 if (unref(getOpenPageLoading)) {
26 setTimeout(() => { 28 setTimeout(() => {
27 - appStore.commitPageLoadingState(false); 29 + appStore.setPageLoading(false);
28 }, 220); 30 }, 220);
29 } 31 }
30 return true; 32 return true;
src/router/guard/permissionGuard.ts
1 import type { Router, RouteRecordRaw } from 'vue-router'; 1 import type { Router, RouteRecordRaw } from 'vue-router';
2 2
3 -import { permissionStore } from '/@/store/modules/permission'; 3 +import { usePermissionStoreWidthOut } from '/@/store/modules/permission';
4 4
5 import { PageEnum } from '/@/enums/pageEnum'; 5 import { PageEnum } from '/@/enums/pageEnum';
6 -import { userStore } from '/@/store/modules/user'; 6 +import { useUserStoreWidthOut } from '/@/store/modules/user';
7 7
8 import { PAGE_NOT_FOUND_ROUTE } from '/@/router/routes/basic'; 8 import { PAGE_NOT_FOUND_ROUTE } from '/@/router/routes/basic';
9 9
@@ -12,6 +12,8 @@ const LOGIN_PATH = PageEnum.BASE_LOGIN; @@ -12,6 +12,8 @@ const LOGIN_PATH = PageEnum.BASE_LOGIN;
12 const whitePathList: PageEnum[] = [LOGIN_PATH]; 12 const whitePathList: PageEnum[] = [LOGIN_PATH];
13 13
14 export function createPermissionGuard(router: Router) { 14 export function createPermissionGuard(router: Router) {
  15 + const userStore = useUserStoreWidthOut();
  16 + const permissionStore = usePermissionStoreWidthOut();
15 router.beforeEach(async (to, from, next) => { 17 router.beforeEach(async (to, from, next) => {
16 // Jump to the 404 page after processing the login 18 // Jump to the 404 page after processing the login
17 if (from.path === LOGIN_PATH && to.name === PAGE_NOT_FOUND_ROUTE.name) { 19 if (from.path === LOGIN_PATH && to.name === PAGE_NOT_FOUND_ROUTE.name) {
@@ -25,7 +27,7 @@ export function createPermissionGuard(router: Router) { @@ -25,7 +27,7 @@ export function createPermissionGuard(router: Router) {
25 return; 27 return;
26 } 28 }
27 29
28 - const token = userStore.getTokenState; 30 + const token = userStore.getToken;
29 31
30 // token does not exist 32 // token does not exist
31 if (!token) { 33 if (!token) {
@@ -51,7 +53,7 @@ export function createPermissionGuard(router: Router) { @@ -51,7 +53,7 @@ export function createPermissionGuard(router: Router) {
51 next(redirectData); 53 next(redirectData);
52 return; 54 return;
53 } 55 }
54 - if (permissionStore.getIsDynamicAddedRouteState) { 56 + if (permissionStore.getIsDynamicAddedRoute) {
55 next(); 57 next();
56 return; 58 return;
57 } 59 }
@@ -64,7 +66,7 @@ export function createPermissionGuard(router: Router) { @@ -64,7 +66,7 @@ export function createPermissionGuard(router: Router) {
64 const redirectPath = (from.query.redirect || to.path) as string; 66 const redirectPath = (from.query.redirect || to.path) as string;
65 const redirect = decodeURIComponent(redirectPath); 67 const redirect = decodeURIComponent(redirectPath);
66 const nextData = to.path === redirect ? { ...to, replace: true } : { path: redirect }; 68 const nextData = to.path === redirect ? { ...to, replace: true } : { path: redirect };
67 - permissionStore.commitDynamicAddedRouteState(true); 69 + permissionStore.setDynamicAddedRoute(true);
68 next(nextData); 70 next(nextData);
69 }); 71 });
70 } 72 }
src/router/guard/progressGuard.ts
@@ -6,9 +6,8 @@ import nProgress from &#39;nprogress&#39;; @@ -6,9 +6,8 @@ import nProgress from &#39;nprogress&#39;;
6 6
7 import { unref } from 'vue'; 7 import { unref } from 'vue';
8 8
9 -const { getOpenNProgress } = useTransitionSetting();  
10 -  
11 export function createProgressGuard(router: Router) { 9 export function createProgressGuard(router: Router) {
  10 + const { getOpenNProgress } = useTransitionSetting();
12 router.beforeEach(async (to) => { 11 router.beforeEach(async (to) => {
13 if (to.meta.loaded) return true; 12 if (to.meta.loaded) return true;
14 unref(getOpenNProgress) && nProgress.start(); 13 unref(getOpenNProgress) && nProgress.start();
src/router/guard/stateGuard.ts
1 import type { Router } from 'vue-router'; 1 import type { Router } from 'vue-router';
2 -import { appStore } from '/@/store/modules/app';  
3 -import { tabStore } from '/@/store/modules/tab';  
4 -import { userStore } from '/@/store/modules/user';  
5 -import { permissionStore } from '/@/store/modules/permission'; 2 +import { useAppStore } from '/@/store/modules/app';
  3 +import { useMultipleTabStore } from '/@/store/modules/multipleTab';
  4 +import { useUserStore } from '/@/store/modules/user';
  5 +import { usePermissionStore } from '/@/store/modules/permission';
6 import { PageEnum } from '/@/enums/pageEnum'; 6 import { PageEnum } from '/@/enums/pageEnum';
7 import { removeTabChangeListener } from '/@/logics/mitt/routeChange'; 7 import { removeTabChangeListener } from '/@/logics/mitt/routeChange';
8 8
9 export function createStateGuard(router: Router) { 9 export function createStateGuard(router: Router) {
10 router.afterEach((to) => { 10 router.afterEach((to) => {
  11 + const tabStore = useMultipleTabStore();
  12 + const userStore = useUserStore();
  13 + const appStore = useAppStore();
  14 + const permissionStore = usePermissionStore();
11 // Just enter the login page and clear the authentication information 15 // Just enter the login page and clear the authentication information
12 if (to.path === PageEnum.BASE_LOGIN) { 16 if (to.path === PageEnum.BASE_LOGIN) {
13 - appStore.resumeAllState();  
14 - permissionStore.commitResetState();  
15 - tabStore.commitResetState();  
16 - userStore.commitResetState(); 17 + appStore.resetAllState();
  18 + permissionStore.resetState();
  19 + tabStore.resetState();
  20 + userStore.resetState();
17 removeTabChangeListener(); 21 removeTabChangeListener();
18 } 22 }
19 }); 23 });
src/router/menus/index.ts
1 import type { Menu, MenuModule } from '/@/router/types'; 1 import type { Menu, MenuModule } from '/@/router/types';
2 import type { RouteRecordNormalized } from 'vue-router'; 2 import type { RouteRecordNormalized } from 'vue-router';
3 3
4 -import { appStore } from '/@/store/modules/app';  
5 -import { permissionStore } from '/@/store/modules/permission'; 4 +import { useAppStoreWidthOut } from '/@/store/modules/app';
  5 +import { usePermissionStore } from '/@/store/modules/permission';
6 import { transformMenuModule, getAllParentPath } from '/@/router/helper/menuHelper'; 6 import { transformMenuModule, getAllParentPath } from '/@/router/helper/menuHelper';
7 import { filter } from '/@/utils/helper/treeHelper'; 7 import { filter } from '/@/utils/helper/treeHelper';
8 import { isUrl } from '/@/utils/is'; 8 import { isUrl } from '/@/utils/is';
@@ -24,6 +24,7 @@ Object.keys(modules).forEach((key) =&gt; { @@ -24,6 +24,7 @@ Object.keys(modules).forEach((key) =&gt; {
24 // ==========Helper=========== 24 // ==========Helper===========
25 // =========================== 25 // ===========================
26 const isBackMode = () => { 26 const isBackMode = () => {
  27 + const appStore = useAppStoreWidthOut();
27 return appStore.getProjectConfig.permissionMode === PermissionModeEnum.BACK; 28 return appStore.getProjectConfig.permissionMode === PermissionModeEnum.BACK;
28 }; 29 };
29 30
@@ -39,7 +40,8 @@ const staticMenus: Menu[] = []; @@ -39,7 +40,8 @@ const staticMenus: Menu[] = [];
39 })(); 40 })();
40 41
41 async function getAsyncMenus() { 42 async function getAsyncMenus() {
42 - return !isBackMode() ? staticMenus : permissionStore.getBackMenuListState; 43 + const permissionStore = usePermissionStore();
  44 + return !isBackMode() ? staticMenus : permissionStore.getBackMenuList;
43 } 45 }
44 46
45 export const getMenus = async (): Promise<Menu[]> => { 47 export const getMenus = async (): Promise<Menu[]> => {
src/settings/designSetting.ts
1 import { ThemeEnum } from '../enums/appEnum'; 1 import { ThemeEnum } from '../enums/appEnum';
2 -export default {  
3 - prefixCls: 'vben',  
4 -}; 2 +
  3 +export const prefixCls = 'vben';
5 4
6 export const darkMode = ThemeEnum.LIGHT; 5 export const darkMode = ThemeEnum.LIGHT;
7 6
src/settings/projectSetting.ts
@@ -61,7 +61,6 @@ const setting: ProjectConfig = { @@ -61,7 +61,6 @@ const setting: ProjectConfig = {
61 theme: ThemeEnum.LIGHT, 61 theme: ThemeEnum.LIGHT,
62 // Whether to enable the lock screen function 62 // Whether to enable the lock screen function
63 useLockPage: true, 63 useLockPage: true,
64 -  
65 // Whether to show the full screen button 64 // Whether to show the full screen button
66 showFullScreen: true, 65 showFullScreen: true,
67 // Whether to show the document button 66 // Whether to show the document button
src/settings/siteSetting.ts
1 // github repo url 1 // github repo url
2 export const GITHUB_URL = 'https://github.com/anncwb/vue-vben-admin'; 2 export const GITHUB_URL = 'https://github.com/anncwb/vue-vben-admin';
  3 +
3 // vue-vben-admin-next-doc 4 // vue-vben-admin-next-doc
4 export const DOC_URL = 'https://vvbin.cn/doc-next/'; 5 export const DOC_URL = 'https://vvbin.cn/doc-next/';
  6 +
5 // site url 7 // site url
6 export const SITE_URL = 'https://vvbin.cn/next/'; 8 export const SITE_URL = 'https://vvbin.cn/next/';
src/store/index.ts
1 import type { App } from 'vue'; 1 import type { App } from 'vue';
2 -import { createStore } from 'vuex';  
3 -import { config } from 'vuex-module-decorators';  
4 -import { isDevMode } from '/@/utils/env';  
5 -  
6 -config.rawError = true;  
7 -  
8 -const store = createStore({  
9 - strict: isDevMode(),  
10 -}); 2 +import { createPinia } from 'pinia';
  3 +const store = createPinia();
11 4
12 export function setupStore(app: App<Element>) { 5 export function setupStore(app: App<Element>) {
13 app.use(store); 6 app.use(store);
14 } 7 }
15 8
16 -export default store; 9 +export { store };
src/store/modules/app.ts
1 import type { ProjectConfig } from '/#/config'; 1 import type { ProjectConfig } from '/#/config';
2 -import type { BeforeMiniState } from '../types'; 2 +import type { BeforeMiniState } from '/#/store';
3 3
4 -import { VuexModule, getModule, Module, Mutation, Action } from 'vuex-module-decorators';  
5 -import store from '/@/store'; 4 +import { defineStore } from 'pinia';
  5 +import { store } from '/@/store';
6 6
7 -import { PROJ_CFG_KEY, APP_DARK_MODE_KEY_ } from '/@/enums/cacheEnum';  
8 -  
9 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper'; 7 +import { ThemeEnum } from '/@/enums/appEnum';
  8 +import { APP_DARK_MODE_KEY_, PROJ_CFG_KEY } from '/@/enums/cacheEnum';
10 import { Persistent } from '/@/utils/cache/persistent'; 9 import { Persistent } from '/@/utils/cache/persistent';
11 -import { deepMerge } from '/@/utils';  
12 -  
13 -import { resetRouter } from '/@/router';  
14 -import { ThemeEnum } from '../../enums/appEnum';  
15 -  
16 import { darkMode } from '/@/settings/designSetting'; 10 import { darkMode } from '/@/settings/designSetting';
  11 +import { resetRouter } from '/@/router';
  12 +import { deepMerge } from '/@/utils';
17 13
18 -export interface LockInfo {  
19 - pwd: string | undefined;  
20 - isLock: boolean;  
21 -}  
22 -  
23 -let timeId: TimeoutHandle;  
24 -const NAME = 'app';  
25 -hotModuleUnregisterModule(NAME);  
26 -@Module({ dynamic: true, namespaced: true, store, name: NAME })  
27 -export default class App extends VuexModule {  
28 - private darkMode;  
29 - 14 +interface AppState {
  15 + darkMode: ThemeEnum;
30 // Page loading status 16 // Page loading status
31 - private pageLoadingState = false;  
32 - 17 + pageLoading: boolean;
33 // project config 18 // project config
34 - private projectConfigState: ProjectConfig | null = Persistent.getLocal(PROJ_CFG_KEY);  
35 -  
36 - // set main overflow hidden  
37 - private lockMainScrollState = false;  
38 - 19 + projectConfig: ProjectConfig | null;
39 // When the window shrinks, remember some states, and restore these states when the window is restored 20 // When the window shrinks, remember some states, and restore these states when the window is restored
40 - private beforeMiniState: BeforeMiniState = {};  
41 -  
42 - get getPageLoading() {  
43 - return this.pageLoadingState;  
44 - }  
45 -  
46 - get getDarkMode() {  
47 - return this.darkMode || localStorage.getItem(APP_DARK_MODE_KEY_) || darkMode;  
48 - }  
49 -  
50 - get getBeforeMiniState() {  
51 - return this.beforeMiniState;  
52 - }  
53 -  
54 - get getLockMainScrollState() {  
55 - return this.lockMainScrollState;  
56 - }  
57 -  
58 - get getProjectConfig(): ProjectConfig {  
59 - return this.projectConfigState || ({} as ProjectConfig);  
60 - }  
61 -  
62 - @Mutation  
63 - commitPageLoadingState(loading: boolean): void {  
64 - this.pageLoadingState = loading;  
65 - }  
66 -  
67 - @Mutation  
68 - commitDarkMode(mode: ThemeEnum): void {  
69 - this.darkMode = mode;  
70 - localStorage.setItem(APP_DARK_MODE_KEY_, mode);  
71 - }  
72 -  
73 - @Mutation  
74 - commitBeforeMiniState(state: BeforeMiniState): void {  
75 - this.beforeMiniState = state;  
76 - }  
77 -  
78 - @Mutation  
79 - commitLockMainScrollState(lock: boolean): void {  
80 - this.lockMainScrollState = lock;  
81 - }  
82 -  
83 - @Mutation  
84 - commitProjectConfigState(proCfg: DeepPartial<ProjectConfig>): void {  
85 - this.projectConfigState = deepMerge(this.projectConfigState || {}, proCfg);  
86 - Persistent.setLocal(PROJ_CFG_KEY, this.projectConfigState);  
87 - }  
88 -  
89 - @Action  
90 - async resumeAllState() {  
91 - resetRouter();  
92 - Persistent.clearAll();  
93 - }  
94 -  
95 - @Action  
96 - public async setPageLoadingAction(loading: boolean): Promise<void> {  
97 - if (loading) {  
98 - clearTimeout(timeId);  
99 - // Prevent flicker  
100 - timeId = setTimeout(() => {  
101 - this.commitPageLoadingState(loading);  
102 - }, 50);  
103 - } else {  
104 - this.commitPageLoadingState(loading);  
105 - clearTimeout(timeId);  
106 - }  
107 - } 21 + beforeMiniInfo: BeforeMiniState;
  22 +}
  23 +let timeId: TimeoutHandle;
  24 +export const useAppStore = defineStore({
  25 + id: 'app',
  26 + state: (): AppState => ({
  27 + darkMode: ThemeEnum.LIGHT,
  28 + pageLoading: false,
  29 + projectConfig: Persistent.getLocal(PROJ_CFG_KEY),
  30 + beforeMiniInfo: {},
  31 + }),
  32 + getters: {
  33 + getPageLoading() {
  34 + return this.pageLoading;
  35 + },
  36 + getDarkMode() {
  37 + return this.darkMode || localStorage.getItem(APP_DARK_MODE_KEY_) || darkMode;
  38 + },
  39 +
  40 + getBeforeMiniInfo() {
  41 + return this.beforeMiniInfo;
  42 + },
  43 +
  44 + getProjectConfig(): ProjectConfig {
  45 + return this.projectConfig || ({} as ProjectConfig);
  46 + },
  47 +
  48 + getHeaderSetting() {
  49 + return this.getProjectConfig.headerSetting;
  50 + },
  51 + getMenuSetting() {
  52 + return this.getProjectConfig.menuSetting;
  53 + },
  54 + getTransitionSetting() {
  55 + return this.getProjectConfig.transitionSetting;
  56 + },
  57 + getMultiTabsSetting() {
  58 + return this.getProjectConfig.multiTabsSetting;
  59 + },
  60 + },
  61 + actions: {
  62 + setPageLoading(loading: boolean): void {
  63 + this.pageLoading = loading;
  64 + },
  65 +
  66 + setDarkMode(mode: ThemeEnum): void {
  67 + this.darkMode = mode;
  68 + localStorage.setItem(APP_DARK_MODE_KEY_, mode);
  69 + },
  70 +
  71 + setBeforeMiniInfo(state: BeforeMiniState): void {
  72 + this.beforeMiniInfo = state;
  73 + },
  74 +
  75 + setProjectConfig(config: DeepPartial<ProjectConfig>): void {
  76 + this.projectConfig = deepMerge(this.projectConfig || {}, config);
  77 + Persistent.setLocal(PROJ_CFG_KEY, this.projectConfig);
  78 + },
  79 +
  80 + async resetAllState() {
  81 + resetRouter();
  82 + Persistent.clearAll();
  83 + },
  84 + async setPageLoadingAction(loading: boolean): Promise<void> {
  85 + if (loading) {
  86 + clearTimeout(timeId);
  87 + // Prevent flicker
  88 + timeId = setTimeout(() => {
  89 + this.setPageLoading(loading);
  90 + }, 50);
  91 + } else {
  92 + this.setPageLoading(loading);
  93 + clearTimeout(timeId);
  94 + }
  95 + },
  96 + },
  97 +});
  98 +
  99 +// Need to be used outside the setup
  100 +export function useAppStoreWidthOut() {
  101 + return useAppStore(store);
108 } 102 }
109 -export const appStore = getModule<App>(App);  
src/store/modules/error.ts deleted 100644 โ†’ 0
1 -import store from '/@/store';  
2 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper';  
3 -import { VuexModule, getModule, Module, Mutation, Action } from 'vuex-module-decorators';  
4 -  
5 -import { formatToDateTime } from '/@/utils/dateUtil';  
6 -import { ErrorTypeEnum } from '/@/enums/exceptionEnum';  
7 -import projectSetting from '/@/settings/projectSetting';  
8 -  
9 -export interface ErrorInfo {  
10 - type: ErrorTypeEnum;  
11 - file: string;  
12 - name?: string;  
13 - message: string;  
14 - stack?: string;  
15 - detail: string;  
16 - url: string;  
17 - time?: string;  
18 -}  
19 -  
20 -export interface ErrorState {  
21 - errorInfoState: ErrorInfo[] | null;  
22 - errorListCountState: number;  
23 -}  
24 -  
25 -const NAME = 'app-error';  
26 -hotModuleUnregisterModule(NAME);  
27 -@Module({ dynamic: true, namespaced: true, store, name: NAME })  
28 -class Error extends VuexModule implements ErrorState {  
29 - // error log list  
30 - errorInfoState: ErrorInfo[] = [];  
31 -  
32 - // error log count  
33 - errorListCountState = 0;  
34 -  
35 - get getErrorInfoState() {  
36 - return this.errorInfoState;  
37 - }  
38 -  
39 - get getErrorListCountState() {  
40 - return this.errorListCountState;  
41 - }  
42 -  
43 - @Mutation  
44 - commitErrorInfoState(info: ErrorInfo): void {  
45 - const item = {  
46 - ...info,  
47 - time: formatToDateTime(new Date()),  
48 - };  
49 - this.errorInfoState = [item, ...this.errorInfoState];  
50 - this.errorListCountState += 1;  
51 - }  
52 -  
53 - @Mutation  
54 - commitErrorListCountState(count: number): void {  
55 - this.errorListCountState = count;  
56 - }  
57 -  
58 - @Action  
59 - setupErrorHandle(error: any) {  
60 - const { useErrorHandle } = projectSetting;  
61 - if (!useErrorHandle) return;  
62 -  
63 - const errInfo: Partial<ErrorInfo> = {  
64 - message: error.message,  
65 - type: ErrorTypeEnum.AJAX,  
66 - };  
67 - if (error.response) {  
68 - const {  
69 - config: { url = '', data: params = '', method = 'get', headers = {} } = {},  
70 - data = {},  
71 - } = error.response;  
72 - errInfo.url = url;  
73 - errInfo.name = 'Ajax Error!';  
74 - errInfo.file = '-';  
75 - errInfo.stack = JSON.stringify(data);  
76 - errInfo.detail = JSON.stringify({ params, method, headers });  
77 - }  
78 - this.commitErrorInfoState(errInfo as ErrorInfo);  
79 - }  
80 -}  
81 -export const errorStore = getModule<Error>(Error);  
src/store/modules/errorLog.ts 0 โ†’ 100644
  1 +import type { ErrorLogInfo } from '/#/store';
  2 +
  3 +import { defineStore } from 'pinia';
  4 +import { store } from '/@/store';
  5 +
  6 +import { formatToDateTime } from '/@/utils/dateUtil';
  7 +import projectSetting from '/@/settings/projectSetting';
  8 +
  9 +import { ErrorTypeEnum } from '/@/enums/exceptionEnum';
  10 +
  11 +export interface ErrorLogState {
  12 + errorLogInfoList: Nullable<ErrorLogInfo[]>;
  13 + errorLogListCount: number;
  14 +}
  15 +
  16 +export const useErrorLogStore = defineStore({
  17 + id: 'app-error-log',
  18 + state: (): ErrorLogState => ({
  19 + errorLogInfoList: null,
  20 + errorLogListCount: 0,
  21 + }),
  22 + getters: {
  23 + getErrorLogInfoList() {
  24 + return this.errorLogInfoList || [];
  25 + },
  26 + getErrorLogListCount() {
  27 + return this.errorLogListCount;
  28 + },
  29 + },
  30 + actions: {
  31 + addErrorLogInfo(info: ErrorLogInfo) {
  32 + const item = {
  33 + ...info,
  34 + time: formatToDateTime(new Date()),
  35 + };
  36 + this.errorLogInfoList = [item, ...(this.errorLogInfoList || [])];
  37 + this.errorLogListCount += 1;
  38 + },
  39 +
  40 + setErrorLogListCount(count: number): void {
  41 + this.errorLogListCount = count;
  42 + },
  43 +
  44 + /**
  45 + * Triggered after ajax request error
  46 + * @param error
  47 + * @returns
  48 + */
  49 + addAjaxErrorInfo(error) {
  50 + const { useErrorHandle } = projectSetting;
  51 + if (!useErrorHandle) {
  52 + return;
  53 + }
  54 + const errInfo: Partial<ErrorLogInfo> = {
  55 + message: error.message,
  56 + type: ErrorTypeEnum.AJAX,
  57 + };
  58 + if (error.response) {
  59 + const {
  60 + config: { url = '', data: params = '', method = 'get', headers = {} } = {},
  61 + data = {},
  62 + } = error.response;
  63 + errInfo.url = url;
  64 + errInfo.name = 'Ajax Error!';
  65 + errInfo.file = '-';
  66 + errInfo.stack = JSON.stringify(data);
  67 + errInfo.detail = JSON.stringify({ params, method, headers });
  68 + }
  69 + this.addErrorLogInfo(errInfo as ErrorLogInfo);
  70 + },
  71 + },
  72 +});
  73 +
  74 +// Need to be used outside the setup
  75 +export function useErrorLogStoreWithOut() {
  76 + return useErrorLogStore(store);
  77 +}
src/store/modules/locale.ts
1 -import store from '/@/store'; 1 +import type { LocaleSetting, LocaleType } from '/#/config';
2 2
3 -import { VuexModule, getModule, Module, Mutation, Action } from 'vuex-module-decorators'; 3 +import { defineStore } from 'pinia';
  4 +import { store } from '/@/store';
4 5
5 import { LOCALE_KEY } from '/@/enums/cacheEnum'; 6 import { LOCALE_KEY } from '/@/enums/cacheEnum';
6 -  
7 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper';  
8 -import { LocaleSetting, LocaleType } from '/#/config';  
9 import { createLocalStorage } from '/@/utils/cache'; 7 import { createLocalStorage } from '/@/utils/cache';
10 import { localeSetting } from '/@/settings/localeSetting'; 8 import { localeSetting } from '/@/settings/localeSetting';
11 9
12 const ls = createLocalStorage(); 10 const ls = createLocalStorage();
13 11
14 -const lsSetting = (ls.get(LOCALE_KEY) || localeSetting) as LocaleSetting;  
15 -  
16 -const NAME = 'app-locale';  
17 -hotModuleUnregisterModule(NAME);  
18 -@Module({ dynamic: true, namespaced: true, store, name: NAME })  
19 -class Locale extends VuexModule {  
20 - private info: LocaleSetting = lsSetting;  
21 -  
22 - get getShowPicker(): boolean {  
23 - return !!this.info?.showPicker;  
24 - } 12 +const lsLocaleSetting = (ls.get(LOCALE_KEY) || localeSetting) as LocaleSetting;
25 13
26 - get getLocale(): LocaleType {  
27 - return this.info?.locale;  
28 - }  
29 -  
30 - @Mutation  
31 - setLocaleInfo(info: Partial<LocaleSetting>): void {  
32 - this.info = { ...this.info, ...info };  
33 - ls.set(LOCALE_KEY, this.info);  
34 - } 14 +interface LocaleState {
  15 + localInfo: LocaleSetting;
  16 +}
35 17
36 - @Action  
37 - initLocale(): void {  
38 - this.setLocaleInfo({  
39 - ...localeSetting,  
40 - ...this.info,  
41 - });  
42 - } 18 +export const useLocaleStore = defineStore({
  19 + id: 'app-locale',
  20 + state: (): LocaleState => ({
  21 + localInfo: lsLocaleSetting,
  22 + }),
  23 + getters: {
  24 + getShowPicker() {
  25 + return !!this.localInfo?.showPicker;
  26 + },
  27 + getLocale(): LocaleType {
  28 + return this.localInfo?.locale ?? 'zh_CN';
  29 + },
  30 + },
  31 + actions: {
  32 + /**
  33 + * Set up multilingual information and cache
  34 + * @param info multilingual info
  35 + */
  36 + setLocaleInfo(info: Partial<LocaleSetting>) {
  37 + this.localInfo = { ...this.localInfo, ...info };
  38 + ls.set(LOCALE_KEY, this.localInfo);
  39 + },
  40 + /**
  41 + * Initialize multilingual information and load the existing configuration from the local cache
  42 + */
  43 + initLocale() {
  44 + this.setLocaleInfo({
  45 + ...localeSetting,
  46 + ...this.localInfo,
  47 + });
  48 + },
  49 + },
  50 +});
  51 +
  52 +// Need to be used outside the setup
  53 +export function useLocaleStoreWithOut() {
  54 + return useLocaleStore(store);
43 } 55 }
44 -export const localeStore = getModule<Locale>(Locale);  
src/store/modules/lock.ts
1 -import type { LockInfo } from '/@/store/types'; 1 +import type { LockInfo } from '/#/store';
2 2
3 -import { VuexModule, getModule, Module, Mutation, Action } from 'vuex-module-decorators';  
4 -import store from '/@/store'; 3 +import { defineStore } from 'pinia';
5 4
6 import { LOCK_INFO_KEY } from '/@/enums/cacheEnum'; 5 import { LOCK_INFO_KEY } from '/@/enums/cacheEnum';
7 -  
8 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper';  
9 import { Persistent } from '/@/utils/cache/persistent'; 6 import { Persistent } from '/@/utils/cache/persistent';
  7 +import { useUserStore } from './user';
10 8
11 -import { userStore } from './user';  
12 -  
13 -const NAME = 'app-lock';  
14 -hotModuleUnregisterModule(NAME);  
15 -@Module({ dynamic: true, namespaced: true, store, name: NAME })  
16 -class Lock extends VuexModule {  
17 - // lock info  
18 - private lockInfoState: LockInfo | null = Persistent.getLocal(LOCK_INFO_KEY);  
19 -  
20 - get getLockInfo(): LockInfo {  
21 - return this.lockInfoState || ({} as LockInfo);  
22 - }  
23 -  
24 - @Mutation  
25 - commitLockInfoState(info: LockInfo): void {  
26 - this.lockInfoState = Object.assign({}, this.lockInfoState, info);  
27 - Persistent.setLocal(LOCK_INFO_KEY, this.lockInfoState);  
28 - }  
29 -  
30 - @Mutation  
31 - resetLockInfo(): void {  
32 - Persistent.removeLocal(LOCK_INFO_KEY);  
33 - this.lockInfoState = null;  
34 - } 9 +interface LockState {
  10 + lockInfo: Nullable<LockInfo>;
  11 +}
35 12
36 - /**  
37 - * @description: unlock page  
38 - */  
39 - @Action  
40 - public async unLockAction({ password }: { password: string }) {  
41 - const tryLogin = async () => {  
42 - try {  
43 - const username = userStore.getUserInfoState.username;  
44 - const res = await userStore.login({ username, password, goHome: false, mode: 'none' });  
45 - if (res) {  
46 - this.resetLockInfo();  
47 - }  
48 - return res;  
49 - } catch (error) {  
50 - return false; 13 +export const useLockStore = defineStore({
  14 + id: 'app-lock',
  15 + state: (): LockState => ({
  16 + lockInfo: Persistent.getLocal(LOCK_INFO_KEY),
  17 + }),
  18 + getters: {
  19 + getLockInfo() {
  20 + return this.lockInfo;
  21 + },
  22 + },
  23 + actions: {
  24 + setLockInfo(info: LockInfo) {
  25 + this.lockInfo = Object.assign({}, this.lockInfo, info);
  26 + Persistent.setLocal(LOCK_INFO_KEY, this.lockInfo);
  27 + },
  28 + resetLockInfo() {
  29 + Persistent.removeLocal(LOCK_INFO_KEY);
  30 + this.lockInfo = null;
  31 + },
  32 + // Unlock
  33 + async unLock(password?: string) {
  34 + const userStore = useUserStore();
  35 + if (this.lockInfo?.pwd === password) {
  36 + this.resetLockInfo();
  37 + return true;
51 } 38 }
52 - };  
53 -  
54 - if (this.getLockInfo?.pwd === password) {  
55 - this.resetLockInfo();  
56 - return true;  
57 - }  
58 - return await tryLogin();  
59 - }  
60 -}  
61 -export const lockStore = getModule<Lock>(Lock); 39 + const tryLogin = async () => {
  40 + try {
  41 + const username = userStore.getUserInfo?.username;
  42 + const res = await userStore.login({
  43 + username,
  44 + password: password!,
  45 + goHome: false,
  46 + mode: 'none',
  47 + });
  48 + if (res) {
  49 + this.resetLockInfo();
  50 + }
  51 + return res;
  52 + } catch (error) {
  53 + return false;
  54 + }
  55 + };
  56 + return await tryLogin();
  57 + },
  58 + },
  59 +});
src/store/modules/multipleTab.ts 0 โ†’ 100644
  1 +import type { RouteLocationNormalized, RouteLocationRaw, Router } from 'vue-router';
  2 +
  3 +import { toRaw, unref } from 'vue';
  4 +import { defineStore } from 'pinia';
  5 +import { store } from '/@/store';
  6 +
  7 +import { useGo, useRedo } from '/@/hooks/web/usePage';
  8 +
  9 +import { PageEnum } from '/@/enums/pageEnum';
  10 +import { PAGE_NOT_FOUND_ROUTE, REDIRECT_ROUTE } from '/@/router/routes/basic';
  11 +import { getRawRoute } from '/@/utils';
  12 +
  13 +export interface MultipleTabState {
  14 + cacheTabList: Set<string>;
  15 + tabList: RouteLocationNormalized[];
  16 + lastDragEndIndex: number;
  17 +}
  18 +
  19 +function handleGotoPage(router: Router) {
  20 + const go = useGo(router);
  21 + go(unref(router.currentRoute).path, true);
  22 +}
  23 +
  24 +export const useMultipleTabStore = defineStore({
  25 + id: 'app-multiple-tab',
  26 + state: (): MultipleTabState => ({
  27 + // Tabs that need to be cached
  28 + cacheTabList: new Set(),
  29 + // multiple tab list
  30 + tabList: [],
  31 + // Index of the last moved tab
  32 + lastDragEndIndex: 0,
  33 + }),
  34 + getters: {
  35 + getTabList() {
  36 + return this.tabList;
  37 + },
  38 + getCachedTabList(): string[] {
  39 + return Array.from(this.cacheTabList);
  40 + },
  41 + getLastDragEndIndex(): number {
  42 + return this.lastDragEndIndex;
  43 + },
  44 + },
  45 + actions: {
  46 + /**
  47 + * Update the cache according to the currently opened tabs
  48 + */
  49 + async updateCacheTab() {
  50 + const cacheMap: Set<string> = new Set();
  51 +
  52 + for (const tab of this.tabList) {
  53 + const item = getRawRoute(tab);
  54 + // Ignore the cache
  55 + const needCache = !item.meta?.ignoreKeepAlive;
  56 + if (!needCache) {
  57 + return;
  58 + }
  59 + const name = item.name as string;
  60 + cacheMap.add(name);
  61 + }
  62 + this.cacheTabList = cacheMap;
  63 + },
  64 +
  65 + /**
  66 + * Refresh tabs
  67 + */
  68 + async refreshPage(router: Router) {
  69 + const { currentRoute } = router;
  70 + const route = unref(currentRoute);
  71 + const name = route.name;
  72 +
  73 + const findTab = this.getCachedTabList.find((item) => item === name);
  74 + if (findTab) {
  75 + this.cacheTabList.delete(findTab);
  76 + }
  77 + const redo = useRedo(router);
  78 + await redo();
  79 + },
  80 + clearCacheTabs(): void {
  81 + this.cacheTabList = new Set();
  82 + },
  83 + resetState(): void {
  84 + this.tabList = [];
  85 + this.clearCacheTabs();
  86 + },
  87 + goToPage(router: Router) {
  88 + const go = useGo(router);
  89 + const len = this.tabList.length;
  90 + const { path } = unref(router.currentRoute);
  91 +
  92 + let toPath: PageEnum | string = PageEnum.BASE_HOME;
  93 +
  94 + if (len > 0) {
  95 + const page = this.tabList[len - 1];
  96 + const p = page.fullPath || page.path;
  97 + if (p) {
  98 + toPath = p;
  99 + }
  100 + }
  101 + // Jump to the current page and report an error
  102 + path !== toPath && go(toPath as PageEnum, true);
  103 + },
  104 +
  105 + async addTab(route: RouteLocationNormalized) {
  106 + const { path, name, fullPath, params, query } = getRawRoute(route);
  107 + // 404 The page does not need to add a tab
  108 + if (
  109 + path === PageEnum.ERROR_PAGE ||
  110 + !name ||
  111 + [REDIRECT_ROUTE.name, PAGE_NOT_FOUND_ROUTE.name].includes(name as string)
  112 + ) {
  113 + return;
  114 + }
  115 +
  116 + let updateIndex = -1;
  117 + // Existing pages, do not add tabs repeatedly
  118 + const tabHasExits = this.tabList.some((tab, index) => {
  119 + updateIndex = index;
  120 + return (tab.fullPath || tab.path) === (fullPath || path);
  121 + });
  122 +
  123 + // If the tab already exists, perform the update operation
  124 + if (tabHasExits) {
  125 + const curTab = toRaw(this.tabList)[updateIndex];
  126 + if (!curTab) {
  127 + return;
  128 + }
  129 + curTab.params = params || curTab.params;
  130 + curTab.query = query || curTab.query;
  131 + curTab.fullPath = fullPath || curTab.fullPath;
  132 + this.tabList.splice(updateIndex, 1, curTab);
  133 + return;
  134 + }
  135 + // Add tab
  136 + this.tabList.push(route);
  137 + this.updateCacheTab();
  138 + },
  139 +
  140 + async closeTab(tab: RouteLocationNormalized, router: Router) {
  141 + const getToTarget = (tabItem: RouteLocationNormalized) => {
  142 + const { params, path, query } = tabItem;
  143 + return {
  144 + params: params || {},
  145 + path,
  146 + query: query || {},
  147 + };
  148 + };
  149 +
  150 + const close = (route: RouteLocationNormalized) => {
  151 + const { fullPath, meta: { affix } = {} } = route;
  152 + if (affix) {
  153 + return;
  154 + }
  155 + const index = this.tabList.findIndex((item) => item.fullPath === fullPath);
  156 + index !== -1 && this.tabList.splice(index, 1);
  157 + };
  158 +
  159 + const { currentRoute, replace } = router;
  160 +
  161 + const { path } = unref(currentRoute);
  162 + if (path !== tab.path) {
  163 + // Closed is not the activation tab
  164 + close(tab);
  165 + return;
  166 + }
  167 +
  168 + // Closed is activated atb
  169 + let toTarget: RouteLocationRaw = {};
  170 +
  171 + const index = this.tabList.findIndex((item) => item.path === path);
  172 +
  173 + // If the current is the leftmost tab
  174 + if (index === 0) {
  175 + // There is only one tab, then jump to the homepage, otherwise jump to the right tab
  176 + if (this.tabList.length === 1) {
  177 + toTarget = PageEnum.BASE_HOME;
  178 + } else {
  179 + // Jump to the right tab
  180 + const page = this.tabList[index + 1];
  181 + toTarget = getToTarget(page);
  182 + }
  183 + } else {
  184 + // Close the current tab
  185 + const page = this.tabList[index - 1];
  186 + toTarget = getToTarget(page);
  187 + }
  188 + close(currentRoute.value);
  189 + replace(toTarget);
  190 + },
  191 +
  192 + // Close according to key
  193 + async closeTabByKey(key: string, router: Router) {
  194 + const index = this.tabList.findIndex((item) => (item.fullPath || item.path) === key);
  195 + index !== -1 && this.closeTab(this.tabList[index], router);
  196 + },
  197 +
  198 + // Sort the tabs
  199 + async sortTabs(oldIndex: number, newIndex: number) {
  200 + const currentTab = this.tabList[oldIndex];
  201 + this.tabList.splice(oldIndex, 1);
  202 + this.tabList.splice(newIndex, 0, currentTab);
  203 + this.lastDragEndIndex = this.lastDragEndIndex + 1;
  204 + },
  205 +
  206 + // Close the tab on the right and jump
  207 + async closeLeftTabs(route: RouteLocationNormalized, router: Router) {
  208 + const index = this.tabList.findIndex((item) => item.path === route.path);
  209 +
  210 + if (index > 0) {
  211 + const leftTabs = this.tabList.slice(0, index);
  212 + const pathList: string[] = [];
  213 + for (const item of leftTabs) {
  214 + const affix = item?.meta?.affix ?? false;
  215 + if (!affix) {
  216 + pathList.push(item.fullPath);
  217 + }
  218 + }
  219 + this.bulkCloseTabs(pathList);
  220 + }
  221 + this.updateCacheTab();
  222 + handleGotoPage(router);
  223 + },
  224 +
  225 + // Close the tab on the left and jump
  226 + async closeRightTabs(route: RouteLocationNormalized, router: Router) {
  227 + const index = this.tabList.findIndex((item) => item.fullPath === route.fullPath);
  228 +
  229 + if (index >= 0 && index < this.tabList.length - 1) {
  230 + const rightTabs = this.tabList.slice(index + 1, this.tabList.length);
  231 +
  232 + const pathList: string[] = [];
  233 + for (const item of rightTabs) {
  234 + const affix = item?.meta?.affix ?? false;
  235 + if (!affix) {
  236 + pathList.push(item.fullPath);
  237 + }
  238 + }
  239 + this.bulkCloseTabs(pathList);
  240 + }
  241 + this.updateCacheTab();
  242 + handleGotoPage(router);
  243 + },
  244 +
  245 + async closeAllTab(router: Router) {
  246 + this.tabList = this.tabList.filter((item) => item?.meta?.affix ?? false);
  247 + this.clearCacheTabs();
  248 + this.goToPage(router);
  249 + },
  250 +
  251 + /**
  252 + * Close other tabs
  253 + */
  254 + async closeOtherTabs(route: RouteLocationNormalized, router: Router) {
  255 + const closePathList = this.tabList.map((item) => item.fullPath);
  256 +
  257 + const pathList: string[] = [];
  258 +
  259 + for (const path of closePathList) {
  260 + if (path !== route.fullPath) {
  261 + const closeItem = this.tabList.find((item) => item.path === path);
  262 + if (!closeItem) {
  263 + return;
  264 + }
  265 + const affix = closeItem?.meta?.affix ?? false;
  266 + if (!affix) {
  267 + pathList.push(closeItem.fullPath);
  268 + }
  269 + }
  270 + }
  271 + this.bulkCloseTabs(pathList);
  272 + this.updateCacheTab();
  273 + handleGotoPage(router);
  274 + },
  275 +
  276 + /**
  277 + * Close tabs in bulk
  278 + */
  279 + async bulkCloseTabs(pathList: string[]) {
  280 + this.tabList = this.tabList.filter((item) => !pathList.includes(item.fullPath));
  281 + },
  282 + },
  283 +});
  284 +
  285 +// Need to be used outside the setup
  286 +export function useMultipleTabWithOutStore() {
  287 + return useMultipleTabStore(store);
  288 +}
src/store/modules/permission.ts
1 import type { AppRouteRecordRaw, Menu } from '/@/router/types'; 1 import type { AppRouteRecordRaw, Menu } from '/@/router/types';
2 2
3 -import store from '/@/store'; 3 +import { defineStore } from 'pinia';
  4 +import { store } from '/@/store';
  5 +import { useI18n } from '/@/hooks/web/useI18n';
  6 +import { useUserStore } from './user';
  7 +import { useAppStoreWidthOut } from './app';
4 import { toRaw } from 'vue'; 8 import { toRaw } from 'vue';
5 -import { VuexModule, Mutation, Module, getModule, Action } from 'vuex-module-decorators'; 9 +import { transformObjToRoute, flatMultiLevelRoutes } from '/@/router/helper/routeHelper';
  10 +import { transformRouteToMenu } from '/@/router/helper/menuHelper';
6 11
7 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper'; 12 +import projectSetting from '/@/settings/projectSetting';
8 13
9 import { PermissionModeEnum } from '/@/enums/appEnum'; 14 import { PermissionModeEnum } from '/@/enums/appEnum';
10 15
11 -import { appStore } from '/@/store/modules/app';  
12 -import { userStore } from '/@/store/modules/user';  
13 -import projectSetting from '/@/settings/projectSetting';  
14 -  
15 import { asyncRoutes } from '/@/router/routes'; 16 import { asyncRoutes } from '/@/router/routes';
16 import { ERROR_LOG_ROUTE, PAGE_NOT_FOUND_ROUTE } from '/@/router/routes/basic'; 17 import { ERROR_LOG_ROUTE, PAGE_NOT_FOUND_ROUTE } from '/@/router/routes/basic';
17 -import { transformObjToRoute, flatMultiLevelRoutes } from '/@/router/helper/routeHelper';  
18 -import { transformRouteToMenu } from '/@/router/helper/menuHelper';  
19 18
20 import { filter } from '/@/utils/helper/treeHelper'; 19 import { filter } from '/@/utils/helper/treeHelper';
21 20
@@ -23,125 +22,127 @@ import { getMenuListById } from &#39;/@/api/sys/menu&#39;; @@ -23,125 +22,127 @@ import { getMenuListById } from &#39;/@/api/sys/menu&#39;;
23 import { getPermCodeByUserId } from '/@/api/sys/user'; 22 import { getPermCodeByUserId } from '/@/api/sys/user';
24 23
25 import { useMessage } from '/@/hooks/web/useMessage'; 24 import { useMessage } from '/@/hooks/web/useMessage';
26 -import { useI18n } from '/@/hooks/web/useI18n';  
27 25
28 -const NAME = 'app-permission';  
29 -hotModuleUnregisterModule(NAME);  
30 -@Module({ dynamic: true, namespaced: true, store, name: NAME })  
31 -class Permission extends VuexModule { 26 +interface PermissionState {
32 // Permission code list 27 // Permission code list
33 - private permCodeListState: string[] = [];  
34 - 28 + permCodeList: string[];
35 // Whether the route has been dynamically added 29 // Whether the route has been dynamically added
36 - private isDynamicAddedRouteState = false;  
37 - 30 + isDynamicAddedRoute: boolean;
38 // To trigger a menu update 31 // To trigger a menu update
39 - private lastBuildMenuTimeState = 0;  
40 - 32 + lastBuildMenuTime: number;
41 // Backstage menu list 33 // Backstage menu list
42 - private backMenuListState: Menu[] = [];  
43 -  
44 - get getPermCodeListState() {  
45 - return this.permCodeListState;  
46 - }  
47 -  
48 - get getBackMenuListState() {  
49 - return this.backMenuListState;  
50 - }  
51 -  
52 - get getLastBuildMenuTimeState() {  
53 - return this.lastBuildMenuTimeState;  
54 - }  
55 -  
56 - get getIsDynamicAddedRouteState() {  
57 - return this.isDynamicAddedRouteState;  
58 - }  
59 -  
60 - @Mutation  
61 - commitPermCodeListState(codeList: string[]): void {  
62 - this.permCodeListState = codeList;  
63 - }  
64 -  
65 - @Mutation  
66 - commitBackMenuListState(list: Menu[]): void {  
67 - this.backMenuListState = list;  
68 - }  
69 -  
70 - @Mutation  
71 - commitLastBuildMenuTimeState(): void {  
72 - this.lastBuildMenuTimeState = new Date().getTime();  
73 - }  
74 -  
75 - @Mutation  
76 - commitDynamicAddedRouteState(added: boolean): void {  
77 - this.isDynamicAddedRouteState = added;  
78 - }  
79 -  
80 - @Mutation  
81 - commitResetState(): void {  
82 - this.isDynamicAddedRouteState = false;  
83 - this.permCodeListState = [];  
84 - this.backMenuListState = [];  
85 - this.lastBuildMenuTimeState = 0;  
86 - }  
87 -  
88 - @Action  
89 - async changePermissionCode(userId: string) {  
90 - const codeList = await getPermCodeByUserId({ userId });  
91 - this.commitPermCodeListState(codeList);  
92 - }  
93 -  
94 - @Action  
95 - async buildRoutesAction(id?: number | string): Promise<AppRouteRecordRaw[]> {  
96 - const { t } = useI18n();  
97 - let routes: AppRouteRecordRaw[] = [];  
98 - const roleList = toRaw(userStore.getRoleListState);  
99 - const { permissionMode = projectSetting.permissionMode } = appStore.getProjectConfig;  
100 - // role permissions  
101 - if (permissionMode === PermissionModeEnum.ROLE) {  
102 - const routeFilter = (route: AppRouteRecordRaw) => {  
103 - const { meta } = route;  
104 - const { roles } = meta || {};  
105 - if (!roles) return true;  
106 - return roleList.some((role) => roles.includes(role));  
107 - };  
108 - routes = filter(asyncRoutes, routeFilter);  
109 - routes = routes.filter(routeFilter);  
110 - // Convert multi-level routing to level 2 routing  
111 - routes = flatMultiLevelRoutes(routes);  
112 - // If you are sure that you do not need to do background dynamic permissions, please comment the entire judgment below  
113 - } else if (permissionMode === PermissionModeEnum.BACK) {  
114 - const { createMessage } = useMessage();  
115 -  
116 - createMessage.loading({  
117 - content: t('sys.app.menuLoading'),  
118 - duration: 1,  
119 - });  
120 - // Here to get the background routing menu logic to modify by yourself  
121 - const paramId = id || userStore.getUserInfoState.userId;  
122 -  
123 - // !Simulate to obtain permission codes from the background,  
124 - // this function may only need to be executed once, and the actual project can be put at the right time by itself  
125 - try {  
126 - this.changePermissionCode('1');  
127 - } catch (error) {}  
128 - if (!paramId) {  
129 - throw new Error('paramId is undefined!'); 34 + backMenuList: Menu[];
  35 +}
  36 +export const usePermissionStore = defineStore({
  37 + id: 'app-permission',
  38 + state: (): PermissionState => ({
  39 + permCodeList: [],
  40 + // Whether the route has been dynamically added
  41 + isDynamicAddedRoute: false,
  42 + // To trigger a menu update
  43 + lastBuildMenuTime: 0,
  44 + // Backstage menu list
  45 + backMenuList: [],
  46 + }),
  47 + getters: {
  48 + getPermCodeList() {
  49 + return this.permCodeList;
  50 + },
  51 + getBackMenuList() {
  52 + return this.backMenuList;
  53 + },
  54 + getLastBuildMenuTime() {
  55 + return this.lastBuildMenuTime;
  56 + },
  57 + getIsDynamicAddedRoute() {
  58 + return this.isDynamicAddedRoute;
  59 + },
  60 + },
  61 + actions: {
  62 + setPermCodeList(codeList: string[]) {
  63 + this.permCodeList = codeList;
  64 + },
  65 +
  66 + setBackMenuList(list: Menu[]) {
  67 + this.backMenuList = list;
  68 + },
  69 +
  70 + setLastBuildMenuTime() {
  71 + this.lastBuildMenuTime = new Date().getTime();
  72 + },
  73 +
  74 + setDynamicAddedRoute(added: boolean) {
  75 + this.isDynamicAddedRoute = added;
  76 + },
  77 + resetState(): void {
  78 + this.isDynamicAddedRoute = false;
  79 + this.permCodeList = [];
  80 + this.backMenuList = [];
  81 + this.lastBuildMenuTime = 0;
  82 + },
  83 + async changePermissionCode(userId: string) {
  84 + const codeList = await getPermCodeByUserId({ userId });
  85 + this.setPermCodeList(codeList);
  86 + },
  87 + async buildRoutesAction(id?: number | string): Promise<AppRouteRecordRaw[]> {
  88 + const { t } = useI18n();
  89 + const userStore = useUserStore();
  90 + const appStore = useAppStoreWidthOut();
  91 +
  92 + let routes: AppRouteRecordRaw[] = [];
  93 + const roleList = toRaw(userStore.getRoleList);
  94 + const { permissionMode = projectSetting.permissionMode } = appStore.getProjectConfig;
  95 + // role permissions
  96 + if (permissionMode === PermissionModeEnum.ROLE) {
  97 + const routeFilter = (route: AppRouteRecordRaw) => {
  98 + const { meta } = route;
  99 + const { roles } = meta || {};
  100 + if (!roles) return true;
  101 + return roleList.some((role) => roles.includes(role));
  102 + };
  103 + routes = filter(asyncRoutes, routeFilter);
  104 + routes = routes.filter(routeFilter);
  105 + // Convert multi-level routing to level 2 routing
  106 + routes = flatMultiLevelRoutes(routes);
  107 + // If you are sure that you do not need to do background dynamic permissions, please comment the entire judgment below
  108 + } else if (permissionMode === PermissionModeEnum.BACK) {
  109 + const { createMessage } = useMessage();
  110 +
  111 + createMessage.loading({
  112 + content: t('sys.app.menuLoading'),
  113 + duration: 1,
  114 + });
  115 + // Here to get the background routing menu logic to modify by yourself
  116 + const paramId = id || userStore.getUserInfo?.userId;
  117 +
  118 + // !Simulate to obtain permission codes from the background,
  119 + // this function may only need to be executed once, and the actual project can be put at the right time by itself
  120 + try {
  121 + this.changePermissionCode('1');
  122 + } catch (error) {}
  123 +
  124 + if (!paramId) {
  125 + throw new Error('paramId is undefined!');
  126 + }
  127 + let routeList = (await getMenuListById({ id: paramId })) as AppRouteRecordRaw[];
  128 +
  129 + // Dynamically introduce components
  130 + routeList = transformObjToRoute(routeList);
  131 +
  132 + // Background routing to menu structure
  133 + const backMenuList = transformRouteToMenu(routeList);
  134 + this.setBackMenuList(backMenuList);
  135 +
  136 + routeList = flatMultiLevelRoutes(routeList);
  137 + routes = [PAGE_NOT_FOUND_ROUTE, ...routeList];
130 } 138 }
131 - let routeList = (await getMenuListById({ id: paramId })) as AppRouteRecordRaw[];  
132 -  
133 - // Dynamically introduce components  
134 - routeList = transformObjToRoute(routeList);  
135 -  
136 - // Background routing to menu structure  
137 - const backMenuList = transformRouteToMenu(routeList);  
138 - this.commitBackMenuListState(backMenuList);  
139 -  
140 - routeList = flatMultiLevelRoutes(routeList);  
141 - routes = [PAGE_NOT_FOUND_ROUTE, ...routeList];  
142 - }  
143 - routes.push(ERROR_LOG_ROUTE);  
144 - return routes;  
145 - } 139 + routes.push(ERROR_LOG_ROUTE);
  140 + return routes;
  141 + },
  142 + },
  143 +});
  144 +
  145 +// Need to be used outside the setup
  146 +export function usePermissionStoreWidthOut() {
  147 + return usePermissionStore(store);
146 } 148 }
147 -export const permissionStore = getModule<Permission>(Permission);  
src/store/modules/tab.ts deleted 100644 โ†’ 0
1 -import type { RouteLocationNormalized, RouteLocationRaw } from 'vue-router';  
2 -  
3 -import { toRaw, unref } from 'vue';  
4 -import { Action, Module, Mutation, VuexModule, getModule } from 'vuex-module-decorators';  
5 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper';  
6 -  
7 -import { PageEnum } from '/@/enums/pageEnum';  
8 -  
9 -import store from '/@/store';  
10 -import router from '/@/router';  
11 -import { PAGE_NOT_FOUND_ROUTE, REDIRECT_ROUTE } from '/@/router/routes/basic';  
12 -import { getRawRoute } from '/@/utils';  
13 -  
14 -import { useGo, useRedo } from '/@/hooks/web/usePage';  
15 -import { cloneDeep } from 'lodash-es';  
16 -  
17 -const NAME = 'app-tab';  
18 -  
19 -hotModuleUnregisterModule(NAME);  
20 -  
21 -function isGotoPage() {  
22 - const go = useGo();  
23 - go(unref(router.currentRoute).path, true);  
24 -}  
25 -  
26 -@Module({ namespaced: true, name: NAME, dynamic: true, store })  
27 -class Tab extends VuexModule {  
28 - cachedTabsState: Set<string> = new Set();  
29 -  
30 - // tab list  
31 - tabsState: RouteLocationNormalized[] = [];  
32 -  
33 - lastDragEndIndexState = 0;  
34 -  
35 - get getTabsState() {  
36 - return this.tabsState;  
37 - }  
38 -  
39 - get getCurrentTab(): RouteLocationNormalized {  
40 - const route = unref(router.currentRoute);  
41 - return this.tabsState.find((item) => item.path === route.path)!;  
42 - }  
43 -  
44 - get getCachedTabsState(): string[] {  
45 - return Array.from(this.cachedTabsState);  
46 - }  
47 -  
48 - get getLastDragEndIndexState(): number {  
49 - return this.lastDragEndIndexState;  
50 - }  
51 -  
52 - @Mutation  
53 - commitClearCache(): void {  
54 - this.cachedTabsState = new Set();  
55 - }  
56 -  
57 - @Mutation  
58 - goToPage() {  
59 - const go = useGo();  
60 - const len = this.tabsState.length;  
61 - const { path } = unref(router.currentRoute);  
62 -  
63 - let toPath: PageEnum | string = PageEnum.BASE_HOME;  
64 -  
65 - if (len > 0) {  
66 - const page = this.tabsState[len - 1];  
67 - const p = page.fullPath || page.path;  
68 - if (p) {  
69 - toPath = p;  
70 - }  
71 - }  
72 - // Jump to the current page and report an error  
73 - path !== toPath && go(toPath as PageEnum, true);  
74 - }  
75 -  
76 - @Mutation  
77 - commitCachedMapState(): void {  
78 - const cacheMap: Set<string> = new Set();  
79 -  
80 - this.tabsState.forEach((tab) => {  
81 - const item = getRawRoute(tab);  
82 - const needCache = !item.meta?.ignoreKeepAlive;  
83 - if (!needCache) return;  
84 - const name = item.name as string;  
85 - cacheMap.add(name);  
86 - });  
87 - this.cachedTabsState = cacheMap;  
88 - }  
89 -  
90 - @Mutation  
91 - commitTabRoutesState(route: RouteLocationNormalized) {  
92 - const { path, fullPath, params, query } = route;  
93 -  
94 - let updateIndex = -1;  
95 - // Existing pages, do not add tabs repeatedly  
96 - const hasTab = this.tabsState.some((tab, index) => {  
97 - updateIndex = index;  
98 - return (tab.fullPath || tab.path) === (fullPath || path);  
99 - });  
100 - if (hasTab) {  
101 - const curTab = toRaw(this.tabsState)[updateIndex];  
102 - if (!curTab) return;  
103 - curTab.params = params || curTab.params;  
104 - curTab.query = query || curTab.query;  
105 - curTab.fullPath = fullPath || curTab.fullPath;  
106 - this.tabsState.splice(updateIndex, 1, curTab);  
107 - return;  
108 - }  
109 - this.tabsState = cloneDeep([...this.tabsState, route]);  
110 - }  
111 -  
112 - /**  
113 - * @description: close tab  
114 - */  
115 - @Mutation  
116 - commitCloseTab(route: RouteLocationNormalized): void {  
117 - const { fullPath, meta: { affix } = {} } = route;  
118 - if (affix) return;  
119 - const index = this.tabsState.findIndex((item) => item.fullPath === fullPath);  
120 - index !== -1 && this.tabsState.splice(index, 1);  
121 - }  
122 -  
123 - @Mutation  
124 - commitCloseAllTab(): void {  
125 - this.tabsState = this.tabsState.filter((item) => {  
126 - return item.meta && item.meta.affix;  
127 - });  
128 - }  
129 -  
130 - @Mutation  
131 - commitResetState(): void {  
132 - this.tabsState = [];  
133 - this.cachedTabsState = new Set();  
134 - }  
135 -  
136 - @Mutation  
137 - commitSortTabs({ oldIndex, newIndex }: { oldIndex: number; newIndex: number }): void {  
138 - const currentTab = this.tabsState[oldIndex];  
139 -  
140 - this.tabsState.splice(oldIndex, 1);  
141 - this.tabsState.splice(newIndex, 0, currentTab);  
142 - this.lastDragEndIndexState = this.lastDragEndIndexState + 1;  
143 - }  
144 -  
145 - @Mutation  
146 - closeMultipleTab({ pathList }: { pathList: string[] }): void {  
147 - this.tabsState = toRaw(this.tabsState).filter((item) => !pathList.includes(item.fullPath));  
148 - }  
149 -  
150 - @Action  
151 - addTabAction(route: RouteLocationNormalized) {  
152 - const { path, name } = route;  
153 - // 404 The page does not need to add a tab  
154 - if (  
155 - path === PageEnum.ERROR_PAGE ||  
156 - !name ||  
157 - [REDIRECT_ROUTE.name, PAGE_NOT_FOUND_ROUTE.name].includes(name as string)  
158 - ) {  
159 - return;  
160 - }  
161 - this.commitTabRoutesState(getRawRoute(route));  
162 -  
163 - this.commitCachedMapState();  
164 - }  
165 -  
166 - @Mutation  
167 - async commitRedoPage() {  
168 - const route = router.currentRoute.value;  
169 - const name = route.name;  
170 -  
171 - const findVal = Array.from(this.cachedTabsState).find((item) => item === name);  
172 - if (findVal) {  
173 - this.cachedTabsState.delete(findVal);  
174 - // this.cachedTabsState.splice(index, 1);  
175 - }  
176 - const redo = useRedo();  
177 - await redo();  
178 - }  
179 -  
180 - @Action  
181 - closeAllTabAction() {  
182 - this.commitCloseAllTab();  
183 - this.commitClearCache();  
184 - this.goToPage();  
185 - }  
186 -  
187 - @Action  
188 - closeTabAction(tab: RouteLocationNormalized) {  
189 - function getObj(tabItem: RouteLocationNormalized) {  
190 - const { params, path, query } = tabItem;  
191 - return {  
192 - params: params || {},  
193 - path,  
194 - query: query || {},  
195 - };  
196 - }  
197 - const { currentRoute, replace } = router;  
198 -  
199 - const { path } = unref(currentRoute);  
200 - if (path !== tab.path) {  
201 - // Closed is not the activation tab  
202 - this.commitCloseTab(tab);  
203 - return;  
204 - }  
205 -  
206 - // Closed is activated atb  
207 - let toObj: RouteLocationRaw = {};  
208 -  
209 - const index = this.getTabsState.findIndex((item) => item.path === path);  
210 -  
211 - // If the current is the leftmost tab  
212 - if (index === 0) {  
213 - // There is only one tab, then jump to the homepage, otherwise jump to the right tab  
214 - if (this.getTabsState.length === 1) {  
215 - toObj = PageEnum.BASE_HOME;  
216 - } else {  
217 - // Jump to the right tab  
218 - const page = this.getTabsState[index + 1];  
219 - toObj = getObj(page);  
220 - }  
221 - } else {  
222 - // Close the current tab  
223 - const page = this.getTabsState[index - 1];  
224 - toObj = getObj(page);  
225 - }  
226 - this.commitCloseTab(currentRoute.value);  
227 - replace(toObj);  
228 - }  
229 -  
230 - @Action  
231 - closeTabByKeyAction(key: string) {  
232 - const index = this.tabsState.findIndex((item) => (item.fullPath || item.path) === key);  
233 - index !== -1 && this.closeTabAction(this.tabsState[index]);  
234 - }  
235 -  
236 - @Action  
237 - closeLeftTabAction(route: RouteLocationNormalized): void {  
238 - const index = this.tabsState.findIndex((item) => item.path === route.path);  
239 -  
240 - if (index > 0) {  
241 - const leftTabs = this.tabsState.slice(0, index);  
242 - const pathList: string[] = [];  
243 - for (const item of leftTabs) {  
244 - const affix = item.meta ? item.meta.affix : false;  
245 - if (!affix) {  
246 - pathList.push(item.fullPath);  
247 - }  
248 - }  
249 - this.closeMultipleTab({ pathList });  
250 - }  
251 - this.commitCachedMapState();  
252 - isGotoPage();  
253 - }  
254 -  
255 - @Action  
256 - closeRightTabAction(route: RouteLocationNormalized): void {  
257 - const index = this.tabsState.findIndex((item) => item.fullPath === route.fullPath);  
258 -  
259 - if (index >= 0 && index < this.tabsState.length - 1) {  
260 - const rightTabs = this.tabsState.slice(index + 1, this.tabsState.length);  
261 -  
262 - const pathList: string[] = [];  
263 - for (const item of rightTabs) {  
264 - const affix = item.meta ? item.meta.affix : false;  
265 - if (!affix) {  
266 - pathList.push(item.fullPath);  
267 - }  
268 - }  
269 - this.closeMultipleTab({ pathList });  
270 - }  
271 - this.commitCachedMapState();  
272 - isGotoPage();  
273 - }  
274 -  
275 - @Action  
276 - closeOtherTabAction(route: RouteLocationNormalized): void {  
277 - const closePathList = this.tabsState.map((item) => item.fullPath);  
278 - const pathList: string[] = [];  
279 - closePathList.forEach((path) => {  
280 - if (path !== route.fullPath) {  
281 - const closeItem = this.tabsState.find((item) => item.path === path);  
282 - if (!closeItem) return;  
283 - const affix = closeItem.meta ? closeItem.meta.affix : false;  
284 - if (!affix) {  
285 - pathList.push(closeItem.fullPath);  
286 - }  
287 - }  
288 - });  
289 - this.closeMultipleTab({ pathList });  
290 - this.commitCachedMapState();  
291 - isGotoPage();  
292 - }  
293 -}  
294 -export const tabStore = getModule<Tab>(Tab);  
src/store/modules/user.ts
1 -import type {  
2 - LoginParams,  
3 - GetUserInfoByUserIdModel,  
4 - GetUserInfoByUserIdParams,  
5 -} from '/@/api/sys/model/userModel';  
6 -import type { UserInfo } from '/@/store/types'; 1 +import type { UserInfo } from '/#/store';
  2 +import type { ErrorMessageMode } from '/@/utils/http/axios/types';
7 3
8 -import store from '/@/store/index';  
9 -import { VuexModule, Module, getModule, Mutation, Action } from 'vuex-module-decorators';  
10 -import { hotModuleUnregisterModule } from '/@/utils/helper/vuexHelper'; 4 +import { defineStore } from 'pinia';
  5 +import { store } from '/@/store';
11 6
12 -import { PageEnum } from '/@/enums/pageEnum';  
13 import { RoleEnum } from '/@/enums/roleEnum'; 7 import { RoleEnum } from '/@/enums/roleEnum';
  8 +import { PageEnum } from '/@/enums/pageEnum';
14 import { ROLES_KEY, TOKEN_KEY, USER_INFO_KEY } from '/@/enums/cacheEnum'; 9 import { ROLES_KEY, TOKEN_KEY, USER_INFO_KEY } from '/@/enums/cacheEnum';
15 10
16 -import { useMessage } from '/@/hooks/web/useMessage';  
17 -  
18 -import router from '/@/router'; 11 +import { getAuthCache, setAuthCache } from '/@/utils/auth';
  12 +import {
  13 + GetUserInfoByUserIdModel,
  14 + GetUserInfoByUserIdParams,
  15 + LoginParams,
  16 +} from '/@/api/sys/model/userModel';
19 17
20 -import { loginApi, getUserInfoById } from '/@/api/sys/user'; 18 +import { getUserInfoById, loginApi } from '/@/api/sys/user';
21 19
22 import { useI18n } from '/@/hooks/web/useI18n'; 20 import { useI18n } from '/@/hooks/web/useI18n';
23 -import { ErrorMessageMode } from '/@/utils/http/axios/types';  
24 -import { getAuthCache, setAuthCache } from '/@/utils/auth/index';  
25 -  
26 -const NAME = 'app-user';  
27 -hotModuleUnregisterModule(NAME);  
28 -  
29 -@Module({ namespaced: true, name: NAME, dynamic: true, store })  
30 -class User extends VuexModule {  
31 - // user info  
32 - private userInfoState: UserInfo | null = null;  
33 -  
34 - // token  
35 - private tokenState = '';  
36 -  
37 - // roleList  
38 - private roleListState: RoleEnum[] = [];  
39 -  
40 - get getUserInfoState(): UserInfo {  
41 - return this.userInfoState || getAuthCache<UserInfo>(USER_INFO_KEY) || {};  
42 - }  
43 -  
44 - get getTokenState(): string {  
45 - return this.tokenState || getAuthCache<string>(TOKEN_KEY);  
46 - }  
47 -  
48 - get getRoleListState(): RoleEnum[] {  
49 - return this.roleListState.length > 0 ? this.roleListState : getAuthCache<RoleEnum[]>(ROLES_KEY);  
50 - }  
51 -  
52 - @Mutation  
53 - commitResetState(): void {  
54 - this.userInfoState = null;  
55 - this.tokenState = '';  
56 - this.roleListState = [];  
57 - }  
58 -  
59 - @Mutation  
60 - commitUserInfoState(info: UserInfo): void {  
61 - this.userInfoState = info;  
62 - setAuthCache(USER_INFO_KEY, info);  
63 - }  
64 -  
65 - @Mutation  
66 - commitRoleListState(roleList: RoleEnum[]): void {  
67 - this.roleListState = roleList;  
68 - setAuthCache(ROLES_KEY, roleList);  
69 - }  
70 -  
71 - @Mutation  
72 - commitTokenState(info: string): void {  
73 - this.tokenState = info;  
74 - setAuthCache(TOKEN_KEY, info);  
75 - }  
76 -  
77 - /**  
78 - * @description: login  
79 - */  
80 - @Action  
81 - async login(  
82 - params: LoginParams & {  
83 - goHome?: boolean;  
84 - mode?: ErrorMessageMode;  
85 - }  
86 - ): Promise<GetUserInfoByUserIdModel | null> {  
87 - try {  
88 - const { goHome = true, mode, ...loginParams } = params;  
89 - const data = await loginApi(loginParams, mode);  
90 -  
91 - const { token, userId } = data;  
92 -  
93 - // save token  
94 - this.commitTokenState(token); 21 +import { useMessage } from '/@/hooks/web/useMessage';
  22 +import router from '/@/router';
95 23
96 - // get user info  
97 - const userInfo = await this.getUserInfoAction({ userId }); 24 +interface UserState {
  25 + userInfo: Nullable<UserInfo>;
  26 + token?: string;
  27 + roleList: RoleEnum[];
  28 +}
98 29
99 - goHome && (await router.replace(PageEnum.BASE_HOME)); 30 +export const useUserStore = defineStore({
  31 + id: 'app-user',
  32 + state: (): UserState => ({
  33 + // user info
  34 + userInfo: null,
  35 + // token
  36 + token: undefined,
  37 + // roleList
  38 + roleList: [],
  39 + }),
  40 + getters: {
  41 + getUserInfo(): UserInfo {
  42 + return this.userInfo || getAuthCache<UserInfo>(USER_INFO_KEY) || {};
  43 + },
  44 + getToken(): string {
  45 + return this.token || getAuthCache<string>(TOKEN_KEY);
  46 + },
  47 + getRoleList(): RoleEnum[] {
  48 + return this.roleList.length > 0 ? this.roleList : getAuthCache<RoleEnum[]>(ROLES_KEY);
  49 + },
  50 + },
  51 + actions: {
  52 + setToken(info: string) {
  53 + this.token = info;
  54 + setAuthCache(TOKEN_KEY, info);
  55 + },
  56 + setRoleList(roleList: RoleEnum[]) {
  57 + this.roleList = roleList;
  58 + setAuthCache(ROLES_KEY, roleList);
  59 + },
  60 + setUserInfo(info: UserInfo) {
  61 + this.userInfo = info;
  62 + setAuthCache(USER_INFO_KEY, info);
  63 + },
  64 + resetState() {
  65 + this.userInfo = null;
  66 + this.token = '';
  67 + this.roleList = [];
  68 + },
  69 + /**
  70 + * @description: login
  71 + */
  72 + async login(
  73 + params: LoginParams & {
  74 + goHome?: boolean;
  75 + mode?: ErrorMessageMode;
  76 + }
  77 + ): Promise<GetUserInfoByUserIdModel | null> {
  78 + try {
  79 + const { goHome = true, mode, ...loginParams } = params;
  80 + const data = await loginApi(loginParams, mode);
  81 + const { token, userId } = data;
  82 +
  83 + // save token
  84 + this.setToken(token);
  85 + // get user info
  86 + const userInfo = await this.getUserInfoAction({ userId });
  87 +
  88 + goHome && (await router.replace(PageEnum.BASE_HOME));
  89 + return userInfo;
  90 + } catch (error) {
  91 + return null;
  92 + }
  93 + },
  94 + async getUserInfoAction({ userId }: GetUserInfoByUserIdParams) {
  95 + const userInfo = await getUserInfoById({ userId });
  96 + const { roles } = userInfo;
  97 + const roleList = roles.map((item) => item.value) as RoleEnum[];
  98 + this.setUserInfo(userInfo);
  99 + this.setRoleList(roleList);
100 return userInfo; 100 return userInfo;
101 - } catch (error) {  
102 - return null;  
103 - }  
104 - }  
105 -  
106 - @Action  
107 - async getUserInfoAction({ userId }: GetUserInfoByUserIdParams) {  
108 - const userInfo = await getUserInfoById({ userId });  
109 - const { roles } = userInfo;  
110 - const roleList = roles.map((item) => item.value) as RoleEnum[];  
111 - this.commitUserInfoState(userInfo);  
112 - this.commitRoleListState(roleList);  
113 - return userInfo;  
114 - }  
115 -  
116 - /**  
117 - * @description: logout  
118 - */  
119 - @Action  
120 - async logout(goLogin = false) {  
121 - goLogin && router.push(PageEnum.BASE_LOGIN);  
122 - }  
123 -  
124 - /**  
125 - * @description: Confirm before logging out  
126 - */  
127 - @Action  
128 - async confirmLoginOut() {  
129 - const { createConfirm } = useMessage();  
130 - const { t } = useI18n();  
131 - createConfirm({  
132 - iconType: 'warning',  
133 - title: t('sys.app.logoutTip'),  
134 - content: t('sys.app.logoutMessage'),  
135 - onOk: async () => {  
136 - await this.logout(true);  
137 - },  
138 - });  
139 - } 101 + },
  102 + /**
  103 + * @description: logout
  104 + */
  105 + logout(goLogin = false) {
  106 + goLogin && router.push(PageEnum.BASE_LOGIN);
  107 + },
  108 +
  109 + /**
  110 + * @description: Confirm before logging out
  111 + */
  112 + confirmLoginOut() {
  113 + const { createConfirm } = useMessage();
  114 + const { t } = useI18n();
  115 + createConfirm({
  116 + iconType: 'warning',
  117 + title: t('sys.app.logoutTip'),
  118 + content: t('sys.app.logoutMessage'),
  119 + onOk: async () => {
  120 + await this.logout(true);
  121 + },
  122 + });
  123 + },
  124 + },
  125 +});
  126 +
  127 +// Need to be used outside the setup
  128 +export function useUserStoreWidthOut() {
  129 + return useUserStore(store);
140 } 130 }
141 -export const userStore = getModule<User>(User);  
src/store/types.ts deleted 100644 โ†’ 0
1 -import { MenuModeEnum, MenuTypeEnum } from '../enums/menuEnum';  
2 -  
3 -export interface LockInfo {  
4 - pwd: string | undefined;  
5 - isLock: boolean;  
6 -}  
7 -  
8 -export interface UserInfo {  
9 - // ็”จๆˆทid  
10 - userId: string | number;  
11 - // ็”จๆˆทๅ  
12 - username: string;  
13 - // ็œŸๅฎžๅๅญ—  
14 - realName: string;  
15 - // ไป‹็ป  
16 - desc?: string;  
17 -}  
18 -  
19 -export interface BeforeMiniState {  
20 - menuCollapsed?: boolean;  
21 - menuSplit?: boolean;  
22 - menuMode?: MenuModeEnum;  
23 - menuType?: MenuTypeEnum;  
24 -}  
src/utils/cache/persistent.ts
1 -import type { LockInfo, UserInfo } from '/@/store/types';  
2 -  
3 -import { ProjectConfig } from '/#/config'; 1 +import type { LockInfo, UserInfo } from '/#/store';
  2 +import type { ProjectConfig } from '/#/config';
4 3
5 import { createLocalStorage, createSessionStorage } from '/@/utils/cache'; 4 import { createLocalStorage, createSessionStorage } from '/@/utils/cache';
6 import { Memory } from './memory'; 5 import { Memory } from './memory';
src/utils/env.ts
@@ -35,6 +35,7 @@ export function getAppEnvConfig() { @@ -35,6 +35,7 @@ export function getAppEnvConfig() {
35 `VITE_GLOB_APP_SHORT_NAME Variables can only be characters/underscores, please modify in the environment variables and re-running.` 35 `VITE_GLOB_APP_SHORT_NAME Variables can only be characters/underscores, please modify in the environment variables and re-running.`
36 ); 36 );
37 } 37 }
  38 +
38 return { 39 return {
39 VITE_GLOB_APP_TITLE, 40 VITE_GLOB_APP_TITLE,
40 VITE_GLOB_API_URL, 41 VITE_GLOB_API_URL,
src/utils/http/axios/index.ts
@@ -16,7 +16,8 @@ import { RequestEnum, ResultEnum, ContentTypeEnum } from &#39;/@/enums/httpEnum&#39;; @@ -16,7 +16,8 @@ import { RequestEnum, ResultEnum, ContentTypeEnum } from &#39;/@/enums/httpEnum&#39;;
16 import { isString } from '/@/utils/is'; 16 import { isString } from '/@/utils/is';
17 import { getToken } from '/@/utils/auth'; 17 import { getToken } from '/@/utils/auth';
18 import { setObjToUrlParams, deepMerge } from '/@/utils'; 18 import { setObjToUrlParams, deepMerge } from '/@/utils';
19 -import { errorStore } from '/@/store/modules/error'; 19 +import { useErrorLogStoreWithOut } from '/@/store/modules/errorLog';
  20 +
20 import { errorResult } from './const'; 21 import { errorResult } from './const';
21 import { useI18n } from '/@/hooks/web/useI18n'; 22 import { useI18n } from '/@/hooks/web/useI18n';
22 import { createNow, formatRequestDate } from './helper'; 23 import { createNow, formatRequestDate } from './helper';
@@ -150,7 +151,8 @@ const transform: AxiosTransform = { @@ -150,7 +151,8 @@ const transform: AxiosTransform = {
150 */ 151 */
151 responseInterceptorsCatch: (error: any) => { 152 responseInterceptorsCatch: (error: any) => {
152 const { t } = useI18n(); 153 const { t } = useI18n();
153 - errorStore.setupErrorHandle(error); 154 + const errorLogStore = useErrorLogStoreWithOut();
  155 + errorLogStore.addAjaxErrorInfo(error);
154 const { response, code, message } = error || {}; 156 const { response, code, message } = error || {};
155 const msg: string = response?.data?.error?.message ?? ''; 157 const msg: string = response?.data?.error?.message ?? '';
156 const err: string = error?.toString?.() ?? ''; 158 const err: string = error?.toString?.() ?? '';
src/views/demo/permission/CurrentPermissionMode.vue
@@ -10,7 +10,7 @@ @@ -10,7 +10,7 @@
10 </template> 10 </template>
11 <script lang="ts"> 11 <script lang="ts">
12 import { defineComponent, computed } from 'vue'; 12 import { defineComponent, computed } from 'vue';
13 - import { appStore } from '/@/store/modules/app'; 13 + import { useAppStore } from '/@/store/modules/app';
14 import { PermissionModeEnum } from '/@/enums/appEnum'; 14 import { PermissionModeEnum } from '/@/enums/appEnum';
15 import { Divider } from 'ant-design-vue'; 15 import { Divider } from 'ant-design-vue';
16 import { usePermission } from '/@/hooks/web/usePermission'; 16 import { usePermission } from '/@/hooks/web/usePermission';
@@ -18,9 +18,8 @@ @@ -18,9 +18,8 @@
18 name: 'CurrentPermissionMode', 18 name: 'CurrentPermissionMode',
19 components: { Divider }, 19 components: { Divider },
20 setup() { 20 setup() {
21 - const permissionMode = computed(() => {  
22 - return appStore.getProjectConfig.permissionMode;  
23 - }); 21 + const appStore = useAppStore();
  22 + const permissionMode = computed(() => appStore.getProjectConfig.permissionMode);
24 const { togglePermissionMode } = usePermission(); 23 const { togglePermissionMode } = usePermission();
25 24
26 return { 25 return {
src/views/demo/permission/back/Btn.vue
@@ -5,7 +5,7 @@ @@ -5,7 +5,7 @@
5 <CurrentPermissionMode /> 5 <CurrentPermissionMode />
6 6
7 <p> 7 <p>
8 - ๅฝ“ๅ‰ๆ‹ฅๆœ‰็š„codeๅˆ—่กจ: <a> {{ permissionStore.getPermCodeListState }} </a> 8 + ๅฝ“ๅ‰ๆ‹ฅๆœ‰็š„codeๅˆ—่กจ: <a> {{ permissionStore.getPermCodeList }} </a>
9 </p> 9 </p>
10 <Divider /> 10 <Divider />
11 <Alert class="mt-4" type="info" message="็‚นๅ‡ปๅŽ่ฏทๆŸฅ็œ‹ๆŒ‰้’ฎๅ˜ๅŒ–" show-icon /> 11 <Alert class="mt-4" type="info" message="็‚นๅ‡ปๅŽ่ฏทๆŸฅ็œ‹ๆŒ‰้’ฎๅ˜ๅŒ–" show-icon />
@@ -59,7 +59,7 @@ @@ -59,7 +59,7 @@
59 import CurrentPermissionMode from '../CurrentPermissionMode.vue'; 59 import CurrentPermissionMode from '../CurrentPermissionMode.vue';
60 import { usePermission } from '/@/hooks/web/usePermission'; 60 import { usePermission } from '/@/hooks/web/usePermission';
61 import { Authority } from '/@/components/Authority'; 61 import { Authority } from '/@/components/Authority';
62 - import { permissionStore } from '/@/store/modules/permission'; 62 + import { usePermissionStore } from '/@/store/modules/permission';
63 import { PermissionModeEnum } from '/@/enums/appEnum'; 63 import { PermissionModeEnum } from '/@/enums/appEnum';
64 import { PageWrapper } from '/@/components/Page'; 64 import { PageWrapper } from '/@/components/Page';
65 65
@@ -67,6 +67,7 @@ @@ -67,6 +67,7 @@
67 components: { Alert, PageWrapper, CurrentPermissionMode, Divider, Authority }, 67 components: { Alert, PageWrapper, CurrentPermissionMode, Divider, Authority },
68 setup() { 68 setup() {
69 const { hasPermission } = usePermission(); 69 const { hasPermission } = usePermission();
  70 + const permissionStore = usePermissionStore();
70 71
71 function changePermissionCode(userId: string) { 72 function changePermissionCode(userId: string) {
72 permissionStore.changePermissionCode(userId); 73 permissionStore.changePermissionCode(userId);
src/views/demo/permission/front/Btn.vue
@@ -8,7 +8,7 @@ @@ -8,7 +8,7 @@
8 <CurrentPermissionMode /> 8 <CurrentPermissionMode />
9 9
10 <p> 10 <p>
11 - ๅฝ“ๅ‰่ง’่‰ฒ: <a> {{ userStore.getRoleListState }} </a> 11 + ๅฝ“ๅ‰่ง’่‰ฒ: <a> {{ userStore.getRoleList }} </a>
12 </p> 12 </p>
13 <Alert class="mt-4" type="info" message="็‚นๅ‡ปๅŽ่ฏทๆŸฅ็œ‹ๆŒ‰้’ฎๅ˜ๅŒ–" show-icon /> 13 <Alert class="mt-4" type="info" message="็‚นๅ‡ปๅŽ่ฏทๆŸฅ็œ‹ๆŒ‰้’ฎๅ˜ๅŒ–" show-icon />
14 14
@@ -63,7 +63,7 @@ @@ -63,7 +63,7 @@
63 import { computed, defineComponent } from 'vue'; 63 import { computed, defineComponent } from 'vue';
64 import { Alert, Divider } from 'ant-design-vue'; 64 import { Alert, Divider } from 'ant-design-vue';
65 import CurrentPermissionMode from '../CurrentPermissionMode.vue'; 65 import CurrentPermissionMode from '../CurrentPermissionMode.vue';
66 - import { userStore } from '/@/store/modules/user'; 66 + import { useUserStore } from '/@/store/modules/user';
67 import { RoleEnum } from '/@/enums/roleEnum'; 67 import { RoleEnum } from '/@/enums/roleEnum';
68 import { usePermission } from '/@/hooks/web/usePermission'; 68 import { usePermission } from '/@/hooks/web/usePermission';
69 import { Authority } from '/@/components/Authority'; 69 import { Authority } from '/@/components/Authority';
@@ -73,11 +73,13 @@ @@ -73,11 +73,13 @@
73 components: { Alert, PageWrapper, CurrentPermissionMode, Divider, Authority }, 73 components: { Alert, PageWrapper, CurrentPermissionMode, Divider, Authority },
74 setup() { 74 setup() {
75 const { changeRole, hasPermission } = usePermission(); 75 const { changeRole, hasPermission } = usePermission();
  76 + const userStore = useUserStore();
  77 +
76 return { 78 return {
77 userStore, 79 userStore,
78 RoleEnum, 80 RoleEnum,
79 - isSuper: computed(() => userStore.getRoleListState.includes(RoleEnum.SUPER)),  
80 - isTest: computed(() => userStore.getRoleListState.includes(RoleEnum.TEST)), 81 + isSuper: computed(() => userStore.getRoleList.includes(RoleEnum.SUPER)),
  82 + isTest: computed(() => userStore.getRoleList.includes(RoleEnum.TEST)),
81 changeRole, 83 changeRole,
82 hasPermission, 84 hasPermission,
83 }; 85 };
src/views/demo/permission/front/index.vue
@@ -8,7 +8,7 @@ @@ -8,7 +8,7 @@
8 <CurrentPermissionMode /> 8 <CurrentPermissionMode />
9 9
10 <p> 10 <p>
11 - ๅฝ“ๅ‰่ง’่‰ฒ: <a> {{ userStore.getRoleListState }} </a> 11 + ๅฝ“ๅ‰่ง’่‰ฒ: <a> {{ userStore.getRoleList }} </a>
12 </p> 12 </p>
13 <Alert class="mt-4" type="info" message="็‚นๅ‡ปๅŽ่ฏทๆŸฅ็œ‹ๅทฆไพง่œๅ•ๅ˜ๅŒ–" show-icon /> 13 <Alert class="mt-4" type="info" message="็‚นๅ‡ปๅŽ่ฏทๆŸฅ็œ‹ๅทฆไพง่œๅ•ๅ˜ๅŒ–" show-icon />
14 14
@@ -29,7 +29,7 @@ @@ -29,7 +29,7 @@
29 import { computed, defineComponent } from 'vue'; 29 import { computed, defineComponent } from 'vue';
30 import { Alert } from 'ant-design-vue'; 30 import { Alert } from 'ant-design-vue';
31 import CurrentPermissionMode from '../CurrentPermissionMode.vue'; 31 import CurrentPermissionMode from '../CurrentPermissionMode.vue';
32 - import { userStore } from '/@/store/modules/user'; 32 + import { useUserStore } from '/@/store/modules/user';
33 import { RoleEnum } from '/@/enums/roleEnum'; 33 import { RoleEnum } from '/@/enums/roleEnum';
34 import { usePermission } from '/@/hooks/web/usePermission'; 34 import { usePermission } from '/@/hooks/web/usePermission';
35 import { PageWrapper } from '/@/components/Page'; 35 import { PageWrapper } from '/@/components/Page';
@@ -38,11 +38,13 @@ @@ -38,11 +38,13 @@
38 components: { Alert, CurrentPermissionMode, PageWrapper }, 38 components: { Alert, CurrentPermissionMode, PageWrapper },
39 setup() { 39 setup() {
40 const { changeRole } = usePermission(); 40 const { changeRole } = usePermission();
  41 + const userStore = useUserStore();
  42 +
41 return { 43 return {
42 userStore, 44 userStore,
43 RoleEnum, 45 RoleEnum,
44 - isSuper: computed(() => userStore.getRoleListState.includes(RoleEnum.SUPER)),  
45 - isTest: computed(() => userStore.getRoleListState.includes(RoleEnum.TEST)), 46 + isSuper: computed(() => userStore.getRoleList.includes(RoleEnum.SUPER)),
  47 + isTest: computed(() => userStore.getRoleList.includes(RoleEnum.TEST)),
46 changeRole, 48 changeRole,
47 }; 49 };
48 }, 50 },
src/views/sys/error-log/DetailModal.vue
@@ -5,6 +5,7 @@ @@ -5,6 +5,7 @@
5 </template> 5 </template>
6 <script lang="ts"> 6 <script lang="ts">
7 import type { PropType } from 'vue'; 7 import type { PropType } from 'vue';
  8 + import type { ErrorLogInfo } from '/#/store';
8 9
9 import { defineComponent } from 'vue'; 10 import { defineComponent } from 'vue';
10 import { BasicModal } from '/@/components/Modal/index'; 11 import { BasicModal } from '/@/components/Modal/index';
@@ -12,8 +13,6 @@ @@ -12,8 +13,6 @@
12 13
13 import { useI18n } from '/@/hooks/web/useI18n'; 14 import { useI18n } from '/@/hooks/web/useI18n';
14 15
15 - import { ErrorInfo } from '/@/store/modules/error';  
16 -  
17 import { getDescSchema } from './data'; 16 import { getDescSchema } from './data';
18 17
19 export default defineComponent({ 18 export default defineComponent({
@@ -21,7 +20,7 @@ @@ -21,7 +20,7 @@
21 components: { BasicModal, Description }, 20 components: { BasicModal, Description },
22 props: { 21 props: {
23 info: { 22 info: {
24 - type: Object as PropType<ErrorInfo>, 23 + type: Object as PropType<ErrorLogInfo>,
25 default: null, 24 default: null,
26 }, 25 },
27 }, 26 },
@@ -30,7 +29,7 @@ @@ -30,7 +29,7 @@
30 29
31 const [register] = useDescription({ 30 const [register] = useDescription({
32 column: 2, 31 column: 2,
33 - schema: getDescSchema(), 32 + schema: getDescSchema()!,
34 }); 33 });
35 34
36 return { 35 return {
src/views/sys/error-log/data.tsx
@@ -57,7 +57,7 @@ export function getColumns(): BasicColumn[] { @@ -57,7 +57,7 @@ export function getColumns(): BasicColumn[] {
57 ]; 57 ];
58 } 58 }
59 59
60 -export function getDescSchema() { 60 +export function getDescSchema(): any {
61 return getColumns().map((column) => { 61 return getColumns().map((column) => {
62 return { 62 return {
63 field: column.dataIndex!, 63 field: column.dataIndex!,
src/views/sys/error-log/index.vue
@@ -28,6 +28,8 @@ @@ -28,6 +28,8 @@
28 </template> 28 </template>
29 29
30 <script lang="ts"> 30 <script lang="ts">
  31 + import type { ErrorLogInfo } from '/#/store';
  32 +
31 import { defineComponent, watch, ref, nextTick } from 'vue'; 33 import { defineComponent, watch, ref, nextTick } from 'vue';
32 34
33 import DetailModal from './DetailModal.vue'; 35 import DetailModal from './DetailModal.vue';
@@ -37,7 +39,7 @@ @@ -37,7 +39,7 @@
37 import { useMessage } from '/@/hooks/web/useMessage'; 39 import { useMessage } from '/@/hooks/web/useMessage';
38 import { useI18n } from '/@/hooks/web/useI18n'; 40 import { useI18n } from '/@/hooks/web/useI18n';
39 41
40 - import { errorStore, ErrorInfo } from '/@/store/modules/error'; 42 + import { useErrorLogStore } from '/@/store/modules/errorLog';
41 43
42 import { fireErrorApi } from '/@/api/demo/error'; 44 import { fireErrorApi } from '/@/api/demo/error';
43 45
@@ -49,11 +51,11 @@ @@ -49,11 +51,11 @@
49 name: 'ErrorHandler', 51 name: 'ErrorHandler',
50 components: { DetailModal, BasicTable, TableAction }, 52 components: { DetailModal, BasicTable, TableAction },
51 setup() { 53 setup() {
52 - const rowInfo = ref<ErrorInfo>(); 54 + const rowInfo = ref<ErrorLogInfo>();
53 const imgList = ref<string[]>([]); 55 const imgList = ref<string[]>([]);
54 56
55 const { t } = useI18n(); 57 const { t } = useI18n();
56 - 58 + const errorLogStore = useErrorLogStore();
57 const [register, { setTableData }] = useTable({ 59 const [register, { setTableData }] = useTable({
58 title: t('sys.errorLog.tableTitle'), 60 title: t('sys.errorLog.tableTitle'),
59 columns: getColumns(), 61 columns: getColumns(),
@@ -67,7 +69,7 @@ @@ -67,7 +69,7 @@
67 const [registerModal, { openModal }] = useModal(); 69 const [registerModal, { openModal }] = useModal();
68 70
69 watch( 71 watch(
70 - () => errorStore.getErrorInfoState, 72 + () => errorLogStore.getErrorLogInfoList,
71 (list) => { 73 (list) => {
72 nextTick(() => { 74 nextTick(() => {
73 setTableData(cloneDeep(list)); 75 setTableData(cloneDeep(list));
@@ -82,7 +84,7 @@ @@ -82,7 +84,7 @@
82 createMessage.info(t('sys.errorLog.enableMessage')); 84 createMessage.info(t('sys.errorLog.enableMessage'));
83 } 85 }
84 // ๆŸฅ็œ‹่ฏฆๆƒ… 86 // ๆŸฅ็œ‹่ฏฆๆƒ…
85 - function handleDetail(row: ErrorInfo) { 87 + function handleDetail(row: ErrorLogInfo) {
86 rowInfo.value = row; 88 rowInfo.value = row;
87 openModal(true); 89 openModal(true);
88 } 90 }
src/views/sys/lock/LockPage.vue
@@ -38,7 +38,7 @@ @@ -38,7 +38,7 @@
38 class="enter-x" 38 class="enter-x"
39 v-model:value="password" 39 v-model:value="password"
40 /> 40 />
41 - <span :class="`${prefixCls}-entry__err-msg enter-x`" v-if="errMsgRef"> 41 + <span :class="`${prefixCls}-entry__err-msg enter-x`" v-if="errMsg">
42 {{ t('sys.lock.alert') }} 42 {{ t('sys.lock.alert') }}
43 </span> 43 </span>
44 <div :class="`${prefixCls}-entry__footer enter-x`"> 44 <div :class="`${prefixCls}-entry__footer enter-x`">
@@ -46,7 +46,7 @@ @@ -46,7 +46,7 @@
46 type="link" 46 type="link"
47 size="small" 47 size="small"
48 class="mt-2 mr-2 enter-x" 48 class="mt-2 mr-2 enter-x"
49 - :disabled="loadingRef" 49 + :disabled="loading"
50 @click="handleShowForm(true)" 50 @click="handleShowForm(true)"
51 > 51 >
52 {{ t('common.back') }} 52 {{ t('common.back') }}
@@ -55,12 +55,12 @@ @@ -55,12 +55,12 @@
55 type="link" 55 type="link"
56 size="small" 56 size="small"
57 class="mt-2 mr-2 enter-x" 57 class="mt-2 mr-2 enter-x"
58 - :disabled="loadingRef" 58 + :disabled="loading"
59 @click="goLogin" 59 @click="goLogin"
60 > 60 >
61 {{ t('sys.lock.backToLogin') }} 61 {{ t('sys.lock.backToLogin') }}
62 </a-button> 62 </a-button>
63 - <a-button class="mt-2" type="link" size="small" @click="unLock()" :loading="loadingRef"> 63 + <a-button class="mt-2" type="link" size="small" @click="unLock()" :loading="loading">
64 {{ t('sys.lock.entry') }} 64 {{ t('sys.lock.entry') }}
65 </a-button> 65 </a-button>
66 </div> 66 </div>
@@ -80,8 +80,8 @@ @@ -80,8 +80,8 @@
80 import { defineComponent, ref, computed } from 'vue'; 80 import { defineComponent, ref, computed } from 'vue';
81 import { Input } from 'ant-design-vue'; 81 import { Input } from 'ant-design-vue';
82 82
83 - import { userStore } from '/@/store/modules/user';  
84 - import { lockStore } from '/@/store/modules/lock'; 83 + import { useUserStore } from '/@/store/modules/user';
  84 + import { useLockStore } from '/@/store/modules/lock';
85 import { useI18n } from '/@/hooks/web/useI18n'; 85 import { useI18n } from '/@/hooks/web/useI18n';
86 86
87 import { useNow } from './useNow'; 87 import { useNow } from './useNow';
@@ -95,19 +95,21 @@ @@ -95,19 +95,21 @@
95 components: { LockOutlined, InputPassword: Input.Password }, 95 components: { LockOutlined, InputPassword: Input.Password },
96 96
97 setup() { 97 setup() {
98 - const passwordRef = ref('');  
99 - const loadingRef = ref(false);  
100 - const errMsgRef = ref(false); 98 + const password = ref('');
  99 + const loading = ref(false);
  100 + const errMsg = ref(false);
101 const showDate = ref(true); 101 const showDate = ref(true);
102 102
103 const { prefixCls } = useDesign('lock-page'); 103 const { prefixCls } = useDesign('lock-page');
  104 + const lockStore = useLockStore();
  105 + const userStore = useUserStore();
104 106
105 const { ...state } = useNow(true); 107 const { ...state } = useNow(true);
106 108
107 const { t } = useI18n(); 109 const { t } = useI18n();
108 110
109 const realName = computed(() => { 111 const realName = computed(() => {
110 - const { realName } = userStore.getUserInfoState || {}; 112 + const { realName } = userStore.getUserInfo || {};
111 return realName; 113 return realName;
112 }); 114 });
113 115
@@ -115,16 +117,16 @@ @@ -115,16 +117,16 @@
115 * @description: unLock 117 * @description: unLock
116 */ 118 */
117 async function unLock() { 119 async function unLock() {
118 - if (!passwordRef.value) { 120 + if (!password.value) {
119 return; 121 return;
120 } 122 }
121 - let password = passwordRef.value; 123 + let pwd = password.value;
122 try { 124 try {
123 - loadingRef.value = true;  
124 - const res = await lockStore.unLockAction({ password });  
125 - errMsgRef.value = !res; 125 + loading.value = true;
  126 + const res = await lockStore.unLock(pwd);
  127 + errMsg.value = !res;
126 } finally { 128 } finally {
127 - loadingRef.value = false; 129 + loading.value = false;
128 } 130 }
129 } 131 }
130 132
@@ -141,12 +143,12 @@ @@ -141,12 +143,12 @@
141 goLogin, 143 goLogin,
142 realName, 144 realName,
143 unLock, 145 unLock,
144 - errMsgRef,  
145 - loadingRef, 146 + errMsg,
  147 + loading,
146 t, 148 t,
147 prefixCls, 149 prefixCls,
148 showDate, 150 showDate,
149 - password: passwordRef, 151 + password,
150 handleShowForm, 152 handleShowForm,
151 headerImg, 153 headerImg,
152 ...state, 154 ...state,
src/views/sys/lock/index.vue
@@ -7,17 +7,13 @@ @@ -7,17 +7,13 @@
7 import { defineComponent, computed } from 'vue'; 7 import { defineComponent, computed } from 'vue';
8 import LockPage from './LockPage.vue'; 8 import LockPage from './LockPage.vue';
9 9
10 - import { lockStore } from '/@/store/modules/lock'; 10 + import { useLockStore } from '/@/store/modules/lock';
11 export default defineComponent({ 11 export default defineComponent({
12 name: 'Lock', 12 name: 'Lock',
13 components: { LockPage }, 13 components: { LockPage },
14 setup() { 14 setup() {
15 - const getIsLock = computed(() => {  
16 - const { getLockInfo } = lockStore;  
17 - const { isLock } = getLockInfo;  
18 - return isLock;  
19 - });  
20 - 15 + const lockStore = useLockStore();
  16 + const getIsLock = computed(() => lockStore?.getLockInfo?.isLock ?? false);
21 return { getIsLock }; 17 return { getIsLock };
22 }, 18 },
23 }); 19 });
src/views/sys/lock/useNow.ts
1 import { dateUtil } from '/@/utils/dateUtil'; 1 import { dateUtil } from '/@/utils/dateUtil';
2 import { reactive, toRefs } from 'vue'; 2 import { reactive, toRefs } from 'vue';
3 -import { localeStore } from '/@/store/modules/locale'; 3 +import { useLocaleStore } from '/@/store/modules/locale';
4 import { tryOnMounted, tryOnUnmounted } from '@vueuse/core'; 4 import { tryOnMounted, tryOnUnmounted } from '@vueuse/core';
5 5
6 export function useNow(immediate = true) { 6 export function useNow(immediate = true) {
  7 + const localeStore = useLocaleStore();
7 const localData = dateUtil.localeData(localeStore.getLocale); 8 const localData = dateUtil.localeData(localeStore.getLocale);
8 let timer: IntervalHandle; 9 let timer: IntervalHandle;
9 10
src/views/sys/login/Login.vue
@@ -58,7 +58,7 @@ @@ -58,7 +58,7 @@
58 import { useGlobSetting } from '/@/hooks/setting'; 58 import { useGlobSetting } from '/@/hooks/setting';
59 import { useI18n } from '/@/hooks/web/useI18n'; 59 import { useI18n } from '/@/hooks/web/useI18n';
60 import { useDesign } from '/@/hooks/web/useDesign'; 60 import { useDesign } from '/@/hooks/web/useDesign';
61 - import { localeStore } from '/@/store/modules/locale'; 61 + import { useLocaleStore } from '/@/store/modules/locale';
62 62
63 export default defineComponent({ 63 export default defineComponent({
64 name: 'Login', 64 name: 'Login',
@@ -76,6 +76,7 @@ @@ -76,6 +76,7 @@
76 const globSetting = useGlobSetting(); 76 const globSetting = useGlobSetting();
77 const { prefixCls } = useDesign('login'); 77 const { prefixCls } = useDesign('login');
78 const { t } = useI18n(); 78 const { t } = useI18n();
  79 + const localeStore = useLocaleStore();
79 80
80 return { 81 return {
81 t, 82 t,
src/views/sys/login/LoginForm.vue
@@ -85,7 +85,7 @@ @@ -85,7 +85,7 @@
85 import { useI18n } from '/@/hooks/web/useI18n'; 85 import { useI18n } from '/@/hooks/web/useI18n';
86 import { useMessage } from '/@/hooks/web/useMessage'; 86 import { useMessage } from '/@/hooks/web/useMessage';
87 87
88 - import { userStore } from '/@/store/modules/user'; 88 + import { useUserStore } from '/@/store/modules/user';
89 import { LoginStateEnum, useLoginState, useFormRules, useFormValid } from './useLogin'; 89 import { LoginStateEnum, useLoginState, useFormRules, useFormValid } from './useLogin';
90 import { useDesign } from '/@/hooks/web/useDesign'; 90 import { useDesign } from '/@/hooks/web/useDesign';
91 import { useKeyPress } from '/@/hooks/event/useKeyPress'; 91 import { useKeyPress } from '/@/hooks/event/useKeyPress';
@@ -114,6 +114,7 @@ @@ -114,6 +114,7 @@
114 const { t } = useI18n(); 114 const { t } = useI18n();
115 const { notification } = useMessage(); 115 const { notification } = useMessage();
116 const { prefixCls } = useDesign('login'); 116 const { prefixCls } = useDesign('login');
  117 + const userStore = useUserStore();
117 118
118 const { setLoginState, getLoginState } = useLoginState(); 119 const { setLoginState, getLoginState } = useLoginState();
119 const { getFormRules } = useFormRules(); 120 const { getFormRules } = useFormRules();
types/store.ts 0 โ†’ 100644
  1 +import { ErrorTypeEnum } from '/@/enums/exceptionEnum';
  2 +import { MenuModeEnum, MenuTypeEnum } from '/@/enums/menuEnum';
  3 +
  4 +// Lock screen information
  5 +export interface LockInfo {
  6 + // Password required
  7 + pwd?: string | undefined;
  8 + // Is it locked?
  9 + isLock?: boolean;
  10 +}
  11 +
  12 +// Error-log information
  13 +export interface ErrorLogInfo {
  14 + // Type of error
  15 + type: ErrorTypeEnum;
  16 + // Error file
  17 + file: string;
  18 + // Error name
  19 + name?: string;
  20 + // Error message
  21 + message: string;
  22 + // Error stack
  23 + stack?: string;
  24 + // Error detail
  25 + detail: string;
  26 + // Error url
  27 + url: string;
  28 + // Error time
  29 + time?: string;
  30 +}
  31 +
  32 +export interface UserInfo {
  33 + userId: string | number;
  34 + username: string;
  35 + realName: string;
  36 + desc?: string;
  37 +}
  38 +
  39 +export interface BeforeMiniState {
  40 + menuCollapsed?: boolean;
  41 + menuSplit?: boolean;
  42 + menuMode?: MenuModeEnum;
  43 + menuType?: MenuTypeEnum;
  44 +}
yarn.lock
@@ -1762,25 +1762,25 @@ @@ -1762,25 +1762,25 @@
1762 resolved "https://registry.npmjs.org/@vue/shared/-/shared-3.0.11.tgz#20d22dd0da7d358bb21c17f9bde8628152642c77" 1762 resolved "https://registry.npmjs.org/@vue/shared/-/shared-3.0.11.tgz#20d22dd0da7d358bb21c17f9bde8628152642c77"
1763 integrity sha512-b+zB8A2so8eCE0JsxjL24J7vdGl8rzPQ09hZNhystm+KqSbKcAej1A+Hbva1rCMmTTqA+hFnUSDc5kouEo0JzA== 1763 integrity sha512-b+zB8A2so8eCE0JsxjL24J7vdGl8rzPQ09hZNhystm+KqSbKcAej1A+Hbva1rCMmTTqA+hFnUSDc5kouEo0JzA==
1764 1764
1765 -"@vueuse/core@^4.8.0":  
1766 - version "4.8.0"  
1767 - resolved "https://registry.npmjs.org/@vueuse/core/-/core-4.8.0.tgz#d86e36956521c0f9b6571cb58b27f0e2535259b3"  
1768 - integrity sha512-nUH4Hn1DN4kkuF1r5ZcfGnjoAKDD0Kw9oFnt/TUo1aueNijq4KujagtoQN8OC4Pei10TeTDdqhmZAWnaCE1NbA== 1765 +"@vueuse/core@^4.8.1":
  1766 + version "4.8.1"
  1767 + resolved "https://registry.npmjs.org/@vueuse/core/-/core-4.8.1.tgz#d7a7fb2e72610d1962ecb9244bd93dacb96d921c"
  1768 + integrity sha512-oXFEDaKNU69Rj20/Hd7ZlmTpEtA2M19cRkZaL4A0Nl0w5Wb5In/8aK+0vtdi1VyMUXXbq6h1OGKCJcIhg5cziA==
1769 dependencies: 1769 dependencies:
1770 - "@vueuse/shared" "4.8.0" 1770 + "@vueuse/shared" "4.8.1"
1771 vue-demi latest 1771 vue-demi latest
1772 1772
1773 -"@vueuse/shared@4.8.0":  
1774 - version "4.8.0"  
1775 - resolved "https://registry.npmjs.org/@vueuse/shared/-/shared-4.8.0.tgz#abf3da96ca81b4be82e885928193fef2c676cdbc"  
1776 - integrity sha512-g1lSbHD4ptiS74qBUvffJ98QjRsoCH7ILjxVzJF488EPAmp5z3taLnoggt6NXfonnYve7fEPuqsJqd2BLOxT1A== 1773 +"@vueuse/shared@4.8.1":
  1774 + version "4.8.1"
  1775 + resolved "https://registry.npmjs.org/@vueuse/shared/-/shared-4.8.1.tgz#45fd5f64bf4e8944db42a5b72fa2705cfc74608a"
  1776 + integrity sha512-ONKJoIvZPrGCA8loK7dX+ZcjgZLikI+vPiz1lWlXs6+jZiQiZSLkmvg1NjV6Cfb6OqbDCfEScTWLbZHB7EwrRw==
1777 dependencies: 1777 dependencies:
1778 vue-demi latest 1778 vue-demi latest
1779 1779
1780 -"@windicss/plugin-utils@0.12.5":  
1781 - version "0.12.5"  
1782 - resolved "https://registry.npmjs.org/@windicss/plugin-utils/-/plugin-utils-0.12.5.tgz#d03517d1ae7a48b5b459e3d670e873d38b63e4a1"  
1783 - integrity sha512-4ux2o4s6D/gRTD68os41oxs/0NFk/eSJxHhZL9nN2wy4RGt+pPMQJyOHV56l7zDh9B0ywU5+ZRxDjdw2cl5Yvg== 1780 +"@windicss/plugin-utils@0.13.1":
  1781 + version "0.13.1"
  1782 + resolved "https://registry.npmjs.org/@windicss/plugin-utils/-/plugin-utils-0.13.1.tgz#e0e172855ebcf0b8a5f0f358befdcaf44bae5cf1"
  1783 + integrity sha512-Vr7f7yWxmB5AWwe+iDPV3JbhTlZHbDvM89IfJ0hyP6PqYmZNTtUfMXMbHXZJHVAbQ54dWBMG23WmeC9X327ETA==
1784 dependencies: 1784 dependencies:
1785 debug "^4.3.2" 1785 debug "^4.3.2"
1786 fast-glob "^3.2.5" 1786 fast-glob "^3.2.5"
@@ -1788,7 +1788,7 @@ @@ -1788,7 +1788,7 @@
1788 micromatch "^4.0.2" 1788 micromatch "^4.0.2"
1789 pirates "^4.0.1" 1789 pirates "^4.0.1"
1790 sucrase "^3.17.1" 1790 sucrase "^3.17.1"
1791 - windicss "^2.5.11" 1791 + windicss "^2.5.12"
1792 1792
1793 "@zxcvbn-ts/core@^0.3.0": 1793 "@zxcvbn-ts/core@^0.3.0":
1794 version "0.3.0" 1794 version "0.3.0"
@@ -3670,21 +3670,11 @@ esbuild-register@^2.2.0: @@ -3670,21 +3670,11 @@ esbuild-register@^2.2.0:
3670 esbuild "^0.9.2" 3670 esbuild "^0.9.2"
3671 jsonc-parser "^3.0.0" 3671 jsonc-parser "^3.0.0"
3672 3672
3673 -esbuild@^0.11.4:  
3674 - version "0.11.5"  
3675 - resolved "https://registry.npmjs.org/esbuild/-/esbuild-0.11.5.tgz#25b18a2ff2fb9580683edce26a48f64c08c2f2df"  
3676 - integrity sha512-aRs6jAE+bVRp1tyfzUugAw1T/Y0Fwzp4Z2ROikF3h+UifoD5QlEbEYQGc6orNnnSIRhWR5VWBH7LozlAumaLHg==  
3677 -  
3678 -esbuild@^0.11.6: 3673 +esbuild@^0.11.4, esbuild@^0.11.6, esbuild@^0.9.2, esbuild@^0.9.3:
3679 version "0.11.6" 3674 version "0.11.6"
3680 resolved "https://registry.npmjs.org/esbuild/-/esbuild-0.11.6.tgz#20961309c4cfed00b71027e18806150358d0cbb0" 3675 resolved "https://registry.npmjs.org/esbuild/-/esbuild-0.11.6.tgz#20961309c4cfed00b71027e18806150358d0cbb0"
3681 integrity sha512-L+nKW9ftVS/N2CVJMR9YmXHbkm+vHzlNYuo09rzipQhF7dYNvRLfWoEPSDRTl10and4owFBV9rJ2CTFNtLIOiw== 3676 integrity sha512-L+nKW9ftVS/N2CVJMR9YmXHbkm+vHzlNYuo09rzipQhF7dYNvRLfWoEPSDRTl10and4owFBV9rJ2CTFNtLIOiw==
3682 3677
3683 -esbuild@^0.9.2, esbuild@^0.9.3:  
3684 - version "0.9.7"  
3685 - resolved "https://registry.npmjs.org/esbuild/-/esbuild-0.9.7.tgz#ea0d639cbe4b88ec25fbed4d6ff00c8d788ef70b"  
3686 - integrity sha512-VtUf6aQ89VTmMLKrWHYG50uByMF4JQlVysb8dmg6cOgW8JnFCipmz7p+HNBl+RR3LLCuBxFGVauAe2wfnF9bLg==  
3687 -  
3688 escalade@^3.1.1: 3678 escalade@^3.1.1:
3689 version "3.1.1" 3679 version "3.1.1"
3690 resolved "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40" 3680 resolved "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz#d8cfdc7000965c5a0174b4a82eaa5c0552742e40"
@@ -3752,10 +3742,10 @@ eslint-visitor-keys@^2.0.0: @@ -3752,10 +3742,10 @@ eslint-visitor-keys@^2.0.0:
3752 resolved "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.0.0.tgz#21fdc8fbcd9c795cc0321f0563702095751511a8" 3742 resolved "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-2.0.0.tgz#21fdc8fbcd9c795cc0321f0563702095751511a8"
3753 integrity sha512-QudtT6av5WXels9WjIM7qz1XD1cWGvX4gGXvp/zBn9nXG02D0utdU3Em2m/QjTnrsk6bBjmCygl3rmj118msQQ== 3743 integrity sha512-QudtT6av5WXels9WjIM7qz1XD1cWGvX4gGXvp/zBn9nXG02D0utdU3Em2m/QjTnrsk6bBjmCygl3rmj118msQQ==
3754 3744
3755 -eslint@^7.23.0:  
3756 - version "7.23.0"  
3757 - resolved "https://registry.npmjs.org/eslint/-/eslint-7.23.0.tgz#8d029d252f6e8cf45894b4bee08f5493f8e94325"  
3758 - integrity sha512-kqvNVbdkjzpFy0XOszNwjkKzZ+6TcwCQ/h+ozlcIWwaimBBuhlQ4nN6kbiM2L+OjDcznkTJxzYfRFH92sx4a0Q== 3745 +eslint@^7.24.0:
  3746 + version "7.24.0"
  3747 + resolved "https://registry.npmjs.org/eslint/-/eslint-7.24.0.tgz#2e44fa62d93892bfdb100521f17345ba54b8513a"
  3748 + integrity sha512-k9gaHeHiFmGCDQ2rEfvULlSLruz6tgfA8DEn+rY9/oYPFFTlz55mM/Q/Rij1b2Y42jwZiK3lXvNTw6w6TXzcKQ==
3759 dependencies: 3749 dependencies:
3760 "@babel/code-frame" "7.12.11" 3750 "@babel/code-frame" "7.12.11"
3761 "@eslint/eslintrc" "^0.4.0" 3751 "@eslint/eslintrc" "^0.4.0"
@@ -6942,6 +6932,11 @@ pify@^4.0.1: @@ -6942,6 +6932,11 @@ pify@^4.0.1:
6942 resolved "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz#4b2cd25c50d598735c50292224fd8c6df41e3231" 6932 resolved "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz#4b2cd25c50d598735c50292224fd8c6df41e3231"
6943 integrity sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g== 6933 integrity sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==
6944 6934
  6935 +pinia@^2.0.0-alpha.12:
  6936 + version "2.0.0-alpha.12"
  6937 + resolved "https://registry.npmjs.org/pinia/-/pinia-2.0.0-alpha.12.tgz#690e9a7b4c176bb9d95fe0dc8ec4ab8847b09493"
  6938 + integrity sha512-qmcDpuoAwxQKAVp7/cOkXFYDaja+vyXMWR6kvdyzeJcGGMvZf1HQ2xFhUSW5lf1eW5IiQP0cBRdF3ZDyVa+JIQ==
  6939 +
6945 pinkie-promise@^2.0.0: 6940 pinkie-promise@^2.0.0:
6946 version "2.0.1" 6941 version "2.0.1"
6947 resolved "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz#2135d6dfa7a358c069ac9b178776288228450ffa" 6942 resolved "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz#2135d6dfa7a358c069ac9b178776288228450ffa"
@@ -7691,10 +7686,10 @@ rollup-plugin-visualizer@5.3.0: @@ -7691,10 +7686,10 @@ rollup-plugin-visualizer@5.3.0:
7691 source-map "^0.7.3" 7686 source-map "^0.7.3"
7692 yargs "^16.2.0" 7687 yargs "^16.2.0"
7693 7688
7694 -rollup@^2.25.0, rollup@^2.38.5, rollup@^2.44.0:  
7695 - version "2.44.0"  
7696 - resolved "https://registry.npmjs.org/rollup/-/rollup-2.44.0.tgz#8da324d1c4fd12beef9ae6e12f4068265b6d95eb"  
7697 - integrity sha512-rGSF4pLwvuaH/x4nAS+zP6UNn5YUDWf/TeEU5IoXSZKBbKRNTCI3qMnYXKZgrC0D2KzS2baiOZt1OlqhMu5rnQ== 7689 +rollup@^2.25.0, rollup@^2.38.5, rollup@^2.44.0, rollup@^2.45.1:
  7690 + version "2.45.1"
  7691 + resolved "https://registry.npmjs.org/rollup/-/rollup-2.45.1.tgz#eae2b94dc2088b4e0a3b7197a5a1ee0bdd589d5c"
  7692 + integrity sha512-vPD+JoDj3CY8k6m1bLcAFttXMe78P4CMxoau0iLVS60+S9kLsv2379xaGy4NgYWu+h2WTlucpoLPAoUoixFBag==
7698 optionalDependencies: 7693 optionalDependencies:
7699 fsevents "~2.3.1" 7694 fsevents "~2.3.1"
7700 7695
@@ -9187,15 +9182,15 @@ vite-plugin-theme@^0.6.3: @@ -9187,15 +9182,15 @@ vite-plugin-theme@^0.6.3:
9187 esbuild-plugin-alias "^0.1.2" 9182 esbuild-plugin-alias "^0.1.2"
9188 tinycolor2 "^1.4.2" 9183 tinycolor2 "^1.4.2"
9189 9184
9190 -vite-plugin-windicss@0.12.5:  
9191 - version "0.12.5"  
9192 - resolved "https://registry.npmjs.org/vite-plugin-windicss/-/vite-plugin-windicss-0.12.5.tgz#74a5043db3615fe432855f6ecff13be36f7a6843"  
9193 - integrity sha512-M/eEA+x94kxZNpEEkJLdY7M6Lp3WFhN0Kb/a2zhdPxBviMwaHSA5A7fUqN1xTYMxlQe4xM7D7naxL7EpnSNlmg== 9185 +vite-plugin-windicss@0.13.1:
  9186 + version "0.13.1"
  9187 + resolved "https://registry.npmjs.org/vite-plugin-windicss/-/vite-plugin-windicss-0.13.1.tgz#82a488f3395be710ae2166b83b0612a5eaec7738"
  9188 + integrity sha512-WmFfTLTMSY5gRC3MWX9o72Yni2HRdrtJ2im+cCyZ2W/p4WE6T702zFCScO8Tnz/E08GDx4OH6oFCZWeZYwgxzg==
9194 dependencies: 9189 dependencies:
9195 - "@windicss/plugin-utils" "0.12.5" 9190 + "@windicss/plugin-utils" "0.13.1"
9196 chalk "^4.1.0" 9191 chalk "^4.1.0"
9197 debug "^4.3.2" 9192 debug "^4.3.2"
9198 - windicss "^2.5.11" 9193 + windicss "^2.5.12"
9199 9194
9200 vite@2.1.5: 9195 vite@2.1.5:
9201 version "2.1.5" 9196 version "2.1.5"
@@ -9265,16 +9260,6 @@ vue@^3.0.0: @@ -9265,16 +9260,6 @@ vue@^3.0.0:
9265 "@vue/runtime-dom" "3.0.10" 9260 "@vue/runtime-dom" "3.0.10"
9266 "@vue/shared" "3.0.10" 9261 "@vue/shared" "3.0.10"
9267 9262
9268 -vuex-module-decorators@^1.0.1:  
9269 - version "1.0.1"  
9270 - resolved "https://registry.npmjs.org/vuex-module-decorators/-/vuex-module-decorators-1.0.1.tgz#d34dafb5428a3636f1c26d3d014c15fc9659ccd0"  
9271 - integrity sha512-FLWZsXV5XAtl/bcKUyQFpnSBtpc3wK/7zSdy9oKbyp71mZd4ut5y2zSd219wWW9OG7WUOlVwac4rXFFDVnq7ug==  
9272 -  
9273 -vuex@^4.0.0:  
9274 - version "4.0.0"  
9275 - resolved "https://registry.npmjs.org/vuex/-/vuex-4.0.0.tgz#ac877aa76a9c45368c979471e461b520d38e6cf5"  
9276 - integrity sha512-56VPujlHscP5q/e7Jlpqc40sja4vOhC4uJD1llBCWolVI8ND4+VzisDVkUMl+z5y0MpIImW6HjhNc+ZvuizgOw==  
9277 -  
9278 warning@^4.0.0: 9263 warning@^4.0.0:
9279 version "4.0.3" 9264 version "4.0.3"
9280 resolved "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz#16e9e077eb8a86d6af7d64aa1e05fd85b4678ca3" 9265 resolved "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz#16e9e077eb8a86d6af7d64aa1e05fd85b4678ca3"
@@ -9326,10 +9311,10 @@ which@^2.0.1: @@ -9326,10 +9311,10 @@ which@^2.0.1:
9326 dependencies: 9311 dependencies:
9327 isexe "^2.0.0" 9312 isexe "^2.0.0"
9328 9313
9329 -windicss@^2.5.11:  
9330 - version "2.5.11"  
9331 - resolved "https://registry.npmjs.org/windicss/-/windicss-2.5.11.tgz#dd4027c724c7b12a37746d1474b96a52239157d1"  
9332 - integrity sha512-u7b4rOPb8MwO1glkf0gdDygZ+lIzXb/PYLNjqni5Fe2684DCEt6dWTKdk3iMxXgbKoqRNncKu7xt3pFwXHdSAw== 9314 +windicss@^2.5.12:
  9315 + version "2.5.12"
  9316 + resolved "https://registry.npmjs.org/windicss/-/windicss-2.5.12.tgz#7bc469b05d7a8fa3905d49d6521a1ff9107d0ea4"
  9317 + integrity sha512-BZ0Ps1C0RlCHBVOPcw/DAReeR9o/mKaoFgkBsVphQ23M5nsvVfVXgGlNJZssjAQsXnlDpj97pnIhtDn1ENBjXw==
9333 9318
9334 wmf@~1.0.1: 9319 wmf@~1.0.1:
9335 version "1.0.2" 9320 version "1.0.2"