@zat-design/sisyphus-react 4.2.0-beta.3 → 4.2.0-beta.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +16 -5
- package/dist/index.esm.css +1 -1
- package/dist/less.esm.css +1 -1
- package/es/ProAction/index.less +0 -1
- package/es/ProDownload/style/index.less +0 -1
- package/es/ProDrawerForm/style/index.less +2 -1
- package/es/ProEditLabel/style/index.less +0 -1
- package/es/ProEditTable/components/Summary/index.d.ts +1 -1
- package/es/ProEditTable/style/index.less +150 -114
- package/es/ProEditTable/utils/config.d.ts +2 -2
- package/es/ProEditTable/utils/tools.d.ts +1 -1
- package/es/ProEditTable/utils/useEditTableError.d.ts +1 -1
- package/es/ProEnum/hooks/useEnum.js +22 -71
- package/es/ProEnum/hooks/useEnumRequest.js +9 -10
- package/es/ProEnum/hooks/useFrequentEnumRequest.js +2 -1
- package/es/ProEnum/index.d.ts +2 -0
- package/es/ProEnum/index.js +4 -2
- package/es/ProEnum/style/index.less +0 -1
- package/es/ProEnum/utils/frequentEnum.d.ts +1 -2
- package/es/ProEnum/utils/frequentEnum.js +2 -2
- package/es/ProEnum/utils/getEnum.d.ts +47 -0
- package/es/ProEnum/utils/getEnum.js +151 -0
- package/es/ProEnum/utils/index.d.ts +13 -3
- package/es/ProEnum/utils/index.js +44 -10
- package/es/ProForm/components/base/SwitchCheckbox/style/index.less +4 -5
- package/es/ProForm/components/base/TimePicker/style/index.less +0 -1
- package/es/ProForm/components/combination/Container/style/index.less +18 -19
- package/es/ProForm/components/combination/FormList/style/index.less +4 -4
- package/es/ProForm/components/combination/Group/style/index.less +43 -50
- package/es/ProForm/components/combination/Group/utils/index.d.ts +27 -27
- package/es/ProForm/components/combination/ProModalSelect/style/index.less +20 -16
- package/es/ProForm/components/combination/ProNumberRange/style/index.less +3 -3
- package/es/ProForm/components/combination/ProTimeLimit/style/index.less +1 -1
- package/es/ProForm/style/index.less +39 -44
- package/es/ProLayout/components/Layout/Header/style/index.less +224 -222
- package/es/ProLayout/components/Layout/Icon/style/index.less +1 -1
- package/es/ProLayout/components/Layout/Menu/FoldMenu/style/index.less +4 -1
- package/es/ProLayout/components/Layout/Menu/OpenMenu/style/index.less +9 -7
- package/es/ProLayout/components/Layout/Menu/SideMenu/style/index.less +3 -5
- package/es/ProLayout/components/Layout/Menu/style/index.less +9 -5
- package/es/ProLayout/components/Layout/index.less +4 -4
- package/es/ProLayout/components/ProCollapse/PropTypes.d.ts +45 -45
- package/es/ProLayout/components/ProCollapse/style/index.less +30 -32
- package/es/ProLayout/components/ProFooter/style/index.less +0 -1
- package/es/ProLayout/components/ProHeader/PropTypes.d.ts +31 -31
- package/es/ProLayout/components/ProHeader/components/ProBackBtn/style/index.less +7 -7
- package/es/ProLayout/components/ProHeader/style/index.less +8 -9
- package/es/ProLayout/components/TabsManager/style/index.less +9 -11
- package/es/ProLayout/style/index.less +197 -201
- package/es/ProLayout/utils/index.d.ts +1 -1
- package/es/ProSelect/style/index.less +0 -1
- package/es/ProSelect/utils/index.d.ts +1 -1
- package/es/ProStep/components/Item/index.js +1 -1
- package/es/ProStep/components/LazyLoad/index.d.ts +19 -0
- package/es/ProStep/components/LazyLoad/index.js +55 -0
- package/es/ProStep/components/Listener/index.js +1 -1
- package/es/ProStep/propsType.d.ts +1 -1
- package/es/ProStep/style/index.less +7 -9
- package/es/ProTable/components/RcTable/components/DraggableTable/components/DndWrapper/index.d.ts +1 -1
- package/es/ProTable/propsType.d.ts +1 -1
- package/es/ProTable/style/index.less +24 -22
- package/es/ProTooltip/style/index.less +0 -1
- package/es/ProTree/components/ProTreeSelect/style/index.less +102 -99
- package/es/ProTree/style/index.less +108 -109
- package/es/ProTreeModal/style/index.less +10 -9
- package/es/ProUpload/style/index.less +20 -22
- package/es/global.less +1 -1
- package/es/index.d.ts +2 -2
- package/es/style/core/normalize.less +11 -2
- package/es/style/index.less +2 -2
- package/es/style/less.less +2 -2
- package/es/style/theme/antd.less +19 -23
- package/es/style/theme/base.less +81 -81
- package/es/style/theme/tokens.less +13 -14
- package/es/style/variables.less +1 -1
- package/package.json +23 -20
|
@@ -1,11 +1,7 @@
|
|
|
1
1
|
/* eslint-disable no-redeclare */
|
|
2
|
-
import { useState, useEffect } from 'react';
|
|
2
|
+
import { useState, useEffect, useRef } from 'react';
|
|
3
3
|
import { useProConfig } from "../../ProConfigProvider";
|
|
4
|
-
import { getEnumData } from "../utils";
|
|
5
|
-
let baseEnumStorage = (window.localStorage.getItem('zat-design-pro-component-cacheKey') && JSON.parse(window.localStorage.getItem('zat-design-pro-component-cacheKey'))) ?? null;
|
|
6
|
-
|
|
7
|
-
// 模块级缓存,用于存储正在进行的 IndexedDB 读取 Promise,避免重复读取
|
|
8
|
-
const indexedDBLoadingCache = new Map();
|
|
4
|
+
import { getEnumData, baseCacheKey, baseStorage } from "../utils";
|
|
9
5
|
|
|
10
6
|
/**
|
|
11
7
|
* input code output [DataOption[],getEnumLabel]
|
|
@@ -44,17 +40,15 @@ const indexedDBLoadingCache = new Map();
|
|
|
44
40
|
|
|
45
41
|
function useEnum(codes, value, compose) {
|
|
46
42
|
const {
|
|
47
|
-
storage =
|
|
48
|
-
cacheKey =
|
|
43
|
+
storage = baseStorage,
|
|
44
|
+
cacheKey = baseCacheKey,
|
|
49
45
|
fieldNames = {},
|
|
50
46
|
clear = true,
|
|
51
47
|
dics = {}
|
|
52
48
|
} = useProConfig('ProEnum') || {};
|
|
53
49
|
|
|
54
|
-
//
|
|
55
|
-
|
|
56
|
-
baseEnumStorage = null;
|
|
57
|
-
}
|
|
50
|
+
// 用 ref 记录哪些 cacheKey 已触发过加载,防止 enumData 变化导致重复 I/O
|
|
51
|
+
const hasLoadedRef = useRef(new Set());
|
|
58
52
|
|
|
59
53
|
// 使用 state 来存储异步加载的数据
|
|
60
54
|
const [enumData, setEnumData] = useState(() => {
|
|
@@ -70,7 +64,7 @@ function useEnum(codes, value, compose) {
|
|
|
70
64
|
data: {}
|
|
71
65
|
};
|
|
72
66
|
}
|
|
73
|
-
return getEnumData(storage, cacheKey
|
|
67
|
+
return getEnumData(storage, cacheKey) || {
|
|
74
68
|
data: {}
|
|
75
69
|
};
|
|
76
70
|
});
|
|
@@ -79,7 +73,6 @@ function useEnum(codes, value, compose) {
|
|
|
79
73
|
useEffect(() => {
|
|
80
74
|
if (storage === 'indexedDB' && dics && Object.keys(dics).length > 0) {
|
|
81
75
|
setEnumData(prevData => {
|
|
82
|
-
// 只有当 dics 有数据且与当前数据不同时才更新
|
|
83
76
|
if (JSON.stringify(dics) !== JSON.stringify(prevData?.data)) {
|
|
84
77
|
return {
|
|
85
78
|
data: dics
|
|
@@ -90,67 +83,25 @@ function useEnum(codes, value, compose) {
|
|
|
90
83
|
}
|
|
91
84
|
}, [storage, cacheKey, dics]);
|
|
92
85
|
|
|
93
|
-
// 异步加载 IndexedDB
|
|
86
|
+
// 异步加载 IndexedDB 数据(每个 cacheKey 只触发一次,由 hasLoadedRef 防重)
|
|
94
87
|
useEffect(() => {
|
|
95
|
-
if (storage === 'indexedDB') {
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
indexedDBLoadingCache.delete(cacheKey);
|
|
106
|
-
// 错误已在 getEnumData 中处理,这里返回空数据
|
|
107
|
-
return {
|
|
108
|
-
data: {}
|
|
109
|
-
};
|
|
88
|
+
if (storage === 'indexedDB' && !hasLoadedRef.current.has(cacheKey)) {
|
|
89
|
+
hasLoadedRef.current.add(cacheKey);
|
|
90
|
+
Promise.resolve(getEnumData(storage, cacheKey)).then(data => {
|
|
91
|
+
setEnumData(prevData => {
|
|
92
|
+
if (data && JSON.stringify(data) !== JSON.stringify(prevData)) {
|
|
93
|
+
return data || {
|
|
94
|
+
data: {}
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
return prevData;
|
|
110
98
|
});
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
loadPromise.then(data => {
|
|
114
|
-
// 如果数据为空或无效,且当前 enumData 也是空的,尝试重新读取
|
|
115
|
-
if ((!data || !data.data || Object.keys(data.data).length === 0) && (!enumData || !enumData.data || Object.keys(enumData.data).length === 0)) {
|
|
116
|
-
// 延迟重试,给 IndexedDB 一些时间
|
|
117
|
-
setTimeout(() => {
|
|
118
|
-
// 清除缓存,允许重新读取
|
|
119
|
-
indexedDBLoadingCache.delete(cacheKey);
|
|
120
|
-
Promise.resolve(getEnumData(storage, cacheKey, baseEnumStorage)).then(retryData => {
|
|
121
|
-
if (retryData && retryData.data && Object.keys(retryData.data).length > 0) {
|
|
122
|
-
setEnumData(prevData => {
|
|
123
|
-
if (retryData && JSON.stringify(retryData) !== JSON.stringify(prevData)) {
|
|
124
|
-
baseEnumStorage = retryData;
|
|
125
|
-
return retryData;
|
|
126
|
-
}
|
|
127
|
-
return prevData;
|
|
128
|
-
});
|
|
129
|
-
}
|
|
130
|
-
}).catch(() => {
|
|
131
|
-
// 重试失败,保持空数据
|
|
132
|
-
});
|
|
133
|
-
}, 100);
|
|
134
|
-
} else {
|
|
135
|
-
setEnumData(prevData => {
|
|
136
|
-
if (data && JSON.stringify(data) !== JSON.stringify(prevData)) {
|
|
137
|
-
baseEnumStorage = data;
|
|
138
|
-
return data || {
|
|
139
|
-
data: {}
|
|
140
|
-
};
|
|
141
|
-
}
|
|
142
|
-
return prevData;
|
|
143
|
-
});
|
|
144
|
-
}
|
|
99
|
+
}).catch(() => {
|
|
100
|
+
// 错误已在 getEnumData 中处理
|
|
145
101
|
});
|
|
146
102
|
}
|
|
147
|
-
}, [storage, cacheKey
|
|
148
|
-
const catchData = storage === 'indexedDB' ? enumData : getEnumData(storage, cacheKey
|
|
149
|
-
|
|
150
|
-
// 默认枚举缓存数据(仅同步存储)
|
|
151
|
-
if (storage !== 'indexedDB') {
|
|
152
|
-
baseEnumStorage = catchData;
|
|
153
|
-
}
|
|
103
|
+
}, [storage, cacheKey]);
|
|
104
|
+
const catchData = storage === 'indexedDB' ? enumData : getEnumData(storage, cacheKey);
|
|
154
105
|
if (!codes) {
|
|
155
106
|
return catchData;
|
|
156
107
|
}
|
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
import { useEffect } from 'react';
|
|
2
2
|
import { useDeepCompareEffect, useRequest as useRequestFunc } from 'ahooks';
|
|
3
|
-
import { diffCode, getEnumData, setEnumData, removeEnumData, cacheFieldNames, baseCacheKey } from "../utils";
|
|
3
|
+
import { diffCode, getEnumData, setEnumData, removeEnumData, cacheFieldNames, baseCacheKey, baseStorage } from "../utils";
|
|
4
4
|
import locale from "../../locale";
|
|
5
5
|
import "../utils/eventCenter";
|
|
6
|
-
const baseEnumStorage = (window.localStorage.getItem(baseCacheKey) && JSON.parse(window.localStorage.getItem(baseCacheKey))) ?? null;
|
|
7
6
|
const useEnumRequest = (props, dispatch) => {
|
|
8
7
|
const {
|
|
9
8
|
main = false,
|
|
@@ -16,7 +15,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
16
15
|
},
|
|
17
16
|
cacheKey = baseCacheKey,
|
|
18
17
|
requestRefresh = false,
|
|
19
|
-
storage =
|
|
18
|
+
storage = baseStorage,
|
|
20
19
|
dataSource = {},
|
|
21
20
|
useRequest,
|
|
22
21
|
transformResponse,
|
|
@@ -74,7 +73,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
74
73
|
}
|
|
75
74
|
|
|
76
75
|
// 获取缓存数据(支持异步)
|
|
77
|
-
const cacheData = await Promise.resolve(getEnumData(storage, cacheKey
|
|
76
|
+
const cacheData = await Promise.resolve(getEnumData(storage, cacheKey) || {
|
|
78
77
|
data: {}
|
|
79
78
|
});
|
|
80
79
|
|
|
@@ -106,7 +105,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
106
105
|
},
|
|
107
106
|
getCache: () => {
|
|
108
107
|
// 支持异步读取
|
|
109
|
-
const cachePromise = Promise.resolve(getEnumData(storage, cacheKey
|
|
108
|
+
const cachePromise = Promise.resolve(getEnumData(storage, cacheKey) || {
|
|
110
109
|
data: {}
|
|
111
110
|
});
|
|
112
111
|
|
|
@@ -132,7 +131,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
132
131
|
}
|
|
133
132
|
|
|
134
133
|
// 同步存储的处理
|
|
135
|
-
const res = getEnumData(storage, cacheKey
|
|
134
|
+
const res = getEnumData(storage, cacheKey) || {
|
|
136
135
|
data: {}
|
|
137
136
|
};
|
|
138
137
|
dispatch({
|
|
@@ -162,7 +161,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
162
161
|
}
|
|
163
162
|
});
|
|
164
163
|
const mergeData = async () => {
|
|
165
|
-
const cacheData = await Promise.resolve(getEnumData(storage, cacheKey
|
|
164
|
+
const cacheData = await Promise.resolve(getEnumData(storage, cacheKey) || {
|
|
166
165
|
data: {}
|
|
167
166
|
});
|
|
168
167
|
if (typeof cacheData === 'object') {
|
|
@@ -244,7 +243,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
244
243
|
// TODO 这段代码目前看起来是没啥用的、没起到作用
|
|
245
244
|
mergeData();
|
|
246
245
|
} else if (Object.keys(dataSource)) {
|
|
247
|
-
const res = await Promise.resolve(getEnumData(storage, cacheKey
|
|
246
|
+
const res = await Promise.resolve(getEnumData(storage, cacheKey) || {
|
|
248
247
|
data: {}
|
|
249
248
|
});
|
|
250
249
|
dispatch({
|
|
@@ -255,7 +254,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
255
254
|
}
|
|
256
255
|
});
|
|
257
256
|
} else {
|
|
258
|
-
const res = await Promise.resolve(getEnumData(storage, cacheKey
|
|
257
|
+
const res = await Promise.resolve(getEnumData(storage, cacheKey) || {
|
|
259
258
|
data: {}
|
|
260
259
|
});
|
|
261
260
|
dispatch({
|
|
@@ -270,7 +269,7 @@ const useEnumRequest = (props, dispatch) => {
|
|
|
270
269
|
}, [useRequest?.options]);
|
|
271
270
|
const shareProEnumDic = async cacheData => {
|
|
272
271
|
logDebug(cacheData);
|
|
273
|
-
const storageData = await Promise.resolve(getEnumData(storage, cacheKey
|
|
272
|
+
const storageData = await Promise.resolve(getEnumData(storage, cacheKey) || {
|
|
274
273
|
data: {}
|
|
275
274
|
});
|
|
276
275
|
dispatch({
|
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
import { useDeepCompareEffect, useRequest as useRequestFunc } from 'ahooks';
|
|
2
2
|
import { replaceFrequentEnumCache } from "../utils/frequentEnum";
|
|
3
|
+
import { baseCacheKey } from "../utils";
|
|
3
4
|
const useFrequentEnumRequest = (props, dispatch) => {
|
|
4
5
|
const {
|
|
5
6
|
frequentEnums,
|
|
6
7
|
fieldNames,
|
|
7
8
|
clear = true,
|
|
8
9
|
storage = 'localStorage',
|
|
9
|
-
cacheKey =
|
|
10
|
+
cacheKey = baseCacheKey,
|
|
10
11
|
dics,
|
|
11
12
|
dataSource
|
|
12
13
|
} = props;
|
package/es/ProEnum/index.d.ts
CHANGED
|
@@ -1,8 +1,10 @@
|
|
|
1
1
|
import useEnum from './hooks/useEnum';
|
|
2
|
+
import getEnum from './utils/getEnum';
|
|
2
3
|
import type { ProEnumType } from './propsType';
|
|
3
4
|
declare const ProEnum: {
|
|
4
5
|
(props: ProEnumType): import("react/jsx-runtime").JSX.Element;
|
|
5
6
|
getEnumLabel: (code: string | string[], value: any, compose?: boolean, fieldNameLabel?: string, fieldNameValue?: string) => import("react/jsx-runtime").JSX.Element;
|
|
6
7
|
useEnum: typeof useEnum;
|
|
8
|
+
getEnum: typeof getEnum;
|
|
7
9
|
};
|
|
8
10
|
export default ProEnum;
|
package/es/ProEnum/index.js
CHANGED
|
@@ -12,9 +12,10 @@ import { useProConfig } from "../ProConfigProvider";
|
|
|
12
12
|
import ProEnumTag from "./components/Tag";
|
|
13
13
|
import ProEnumGroup from "./components/Group";
|
|
14
14
|
import Container from "../ProForm/components/Container";
|
|
15
|
-
import { isObject } from "./utils";
|
|
15
|
+
import { isObject, baseCacheKey } from "./utils";
|
|
16
16
|
import getEnumLabel from "./utils/getEnumLabel";
|
|
17
17
|
import useEnum from "./hooks/useEnum";
|
|
18
|
+
import getEnum from "./utils/getEnum";
|
|
18
19
|
import locale from "../locale";
|
|
19
20
|
import { useFieldProps } from "../ProForm/utils/useFieldProps";
|
|
20
21
|
import { jsx as _jsx, Fragment as _Fragment } from "react/jsx-runtime";
|
|
@@ -42,7 +43,7 @@ const ProEnum = props => {
|
|
|
42
43
|
const {
|
|
43
44
|
fieldNames,
|
|
44
45
|
clear = true,
|
|
45
|
-
cacheKey =
|
|
46
|
+
cacheKey = baseCacheKey,
|
|
46
47
|
showCodeName,
|
|
47
48
|
...resProps
|
|
48
49
|
} = useProConfig('ProEnum') || {};
|
|
@@ -282,4 +283,5 @@ const ProEnum = props => {
|
|
|
282
283
|
};
|
|
283
284
|
ProEnum.getEnumLabel = getEnumLabel;
|
|
284
285
|
ProEnum.useEnum = useEnum;
|
|
286
|
+
ProEnum.getEnum = getEnum;
|
|
285
287
|
export default ProEnum;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
+
import type { StorageType } from './index';
|
|
1
2
|
import type { FrequentEnumConfig } from '../propsType';
|
|
2
|
-
type StorageType = 'localStorage' | 'sessionStorage' | 'indexedDB';
|
|
3
3
|
/**
|
|
4
4
|
* 替换频繁枚举缓存数据的参数接口
|
|
5
5
|
*/
|
|
@@ -37,4 +37,3 @@ export declare function validateFrequentEnumConfig(config: FrequentEnumConfig):
|
|
|
37
37
|
* @returns 合并后的数据
|
|
38
38
|
*/
|
|
39
39
|
export declare function mergeFrequentEnumData(cacheData: any, dics: any, dataSource: any): any;
|
|
40
|
-
export {};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { getEnumData, setEnumData, cacheFieldNames } from "./index";
|
|
1
|
+
import { getEnumData, setEnumData, cacheFieldNames, baseCacheKey } from "./index";
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* 替换频繁枚举缓存数据的参数接口
|
|
@@ -52,7 +52,7 @@ async function replaceFrequentEnumCacheAsync(params) {
|
|
|
52
52
|
export function replaceFrequentEnumCache(params) {
|
|
53
53
|
const {
|
|
54
54
|
storage = 'localStorage',
|
|
55
|
-
cacheKey =
|
|
55
|
+
cacheKey = baseCacheKey,
|
|
56
56
|
enums = [],
|
|
57
57
|
newData = {},
|
|
58
58
|
fieldNames = {
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import type { StorageType } from './index';
|
|
2
|
+
export interface GetEnumParams {
|
|
3
|
+
/** 单个枚举 code */
|
|
4
|
+
code?: string;
|
|
5
|
+
/** 多个枚举 code,与 code 互斥 */
|
|
6
|
+
codes?: string[];
|
|
7
|
+
/** 单值查询,返回 [label, option],与 values 互斥 */
|
|
8
|
+
value?: string | number;
|
|
9
|
+
/** 多值查询,返回 [labels[], options[]],与 value 互斥 */
|
|
10
|
+
values?: (string | number)[];
|
|
11
|
+
/** 为 true 时返回 value-label 组合形式 */
|
|
12
|
+
compose?: boolean;
|
|
13
|
+
/** 存储类型,默认 indexedDB */
|
|
14
|
+
storage?: StorageType;
|
|
15
|
+
/** 缓存 key,默认 zat-design-pro-component-cacheKey */
|
|
16
|
+
cacheKey?: string;
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* 在函数/回调中获取枚举数据,无需在 React 组件内使用。
|
|
20
|
+
*
|
|
21
|
+
* 枚举数据由 ProConfigProvider 初始化时写入 storage。
|
|
22
|
+
*
|
|
23
|
+
* **同步优先策略**:
|
|
24
|
+
* - 内存缓存命中时直接返回值,无需 `await`
|
|
25
|
+
* - localStorage/sessionStorage 首次调用同步读取并预热内存缓存
|
|
26
|
+
* - indexedDB 首次调用(内存未命中)返回 Promise,需 `await` 兜底
|
|
27
|
+
*
|
|
28
|
+
* 典型用法:在 ProConfigProvider 初始化完成后,事件回调/工具函数中直接调用无需 await:
|
|
29
|
+
*
|
|
30
|
+
* @example
|
|
31
|
+
* // 获取全部枚举(内存命中时同步返回)
|
|
32
|
+
* const allEnums = getEnum(config);
|
|
33
|
+
*
|
|
34
|
+
* // 获取单个枚举 options
|
|
35
|
+
* const [cityOptions, getLabel] = getEnum({ code: 'city', ...config });
|
|
36
|
+
*
|
|
37
|
+
* // 获取多个枚举
|
|
38
|
+
* const { city, status } = getEnum({ codes: ['city', 'status'], ...config });
|
|
39
|
+
*
|
|
40
|
+
* // 根据值查询 label
|
|
41
|
+
* const [label, option] = getEnum({ code: 'city', value: 'sh', ...config });
|
|
42
|
+
*
|
|
43
|
+
* // indexedDB 首次加载时兜底(数据未预热时需 await)
|
|
44
|
+
* const allEnums = await getEnum(config);
|
|
45
|
+
*/
|
|
46
|
+
declare function getEnum(params?: GetEnumParams): any;
|
|
47
|
+
export default getEnum;
|
|
@@ -0,0 +1,151 @@
|
|
|
1
|
+
import { getEnumData, getEnumDataSync, baseCacheKey, baseStorage } from "./index";
|
|
2
|
+
const FIELD_VALUE = 'value';
|
|
3
|
+
const FIELD_LABEL = 'label';
|
|
4
|
+
const FIELD_CHILDREN = 'children';
|
|
5
|
+
|
|
6
|
+
/** 递归在嵌套结构中查找选项 */
|
|
7
|
+
function findOption(opts, target) {
|
|
8
|
+
const found = opts.find(opt => String(opt[FIELD_VALUE]) === String(target));
|
|
9
|
+
if (found) return found;
|
|
10
|
+
return opts.reduce((acc, opt) => {
|
|
11
|
+
if (acc) return acc;
|
|
12
|
+
const children = opt[FIELD_CHILDREN];
|
|
13
|
+
return Array.isArray(children) ? findOption(children, target) : undefined;
|
|
14
|
+
}, undefined);
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
/** 移除 children 字段 */
|
|
18
|
+
function omitChildren(option) {
|
|
19
|
+
const {
|
|
20
|
+
[FIELD_CHILDREN]: _,
|
|
21
|
+
...rest
|
|
22
|
+
} = option;
|
|
23
|
+
return rest;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/** 格式化单个 label */
|
|
27
|
+
function formatLabel(opt, v, compose) {
|
|
28
|
+
return compose ? `${v}-${opt[FIELD_LABEL]}` : opt[FIELD_LABEL];
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/** 将 allData 按查询参数转换为最终结果 */
|
|
32
|
+
function resolveEnumResult(allData, params) {
|
|
33
|
+
const {
|
|
34
|
+
code,
|
|
35
|
+
codes,
|
|
36
|
+
value,
|
|
37
|
+
values,
|
|
38
|
+
compose
|
|
39
|
+
} = params;
|
|
40
|
+
if (!code && !codes) {
|
|
41
|
+
return allData;
|
|
42
|
+
}
|
|
43
|
+
if (codes) {
|
|
44
|
+
return codes.reduce((acc, c) => {
|
|
45
|
+
const opts = allData[c];
|
|
46
|
+
if (Array.isArray(opts) && opts.length) acc[c] = opts;
|
|
47
|
+
return acc;
|
|
48
|
+
}, {});
|
|
49
|
+
}
|
|
50
|
+
const options = allData[code] ?? [];
|
|
51
|
+
const getLabelFn = (v, composeFn) => {
|
|
52
|
+
const found = findOption(options, v);
|
|
53
|
+
return found ? formatLabel(found, v, composeFn) : undefined;
|
|
54
|
+
};
|
|
55
|
+
if (values !== undefined) {
|
|
56
|
+
const labels = [];
|
|
57
|
+
const foundOptions = [];
|
|
58
|
+
values.forEach(v => {
|
|
59
|
+
const found = findOption(options, v);
|
|
60
|
+
if (found) {
|
|
61
|
+
foundOptions.push(omitChildren(found));
|
|
62
|
+
labels.push(formatLabel(found, v, compose));
|
|
63
|
+
} else {
|
|
64
|
+
foundOptions.push({
|
|
65
|
+
label: '',
|
|
66
|
+
value: ''
|
|
67
|
+
});
|
|
68
|
+
labels.push('');
|
|
69
|
+
}
|
|
70
|
+
});
|
|
71
|
+
return [labels, foundOptions];
|
|
72
|
+
}
|
|
73
|
+
if (value !== undefined) {
|
|
74
|
+
const found = findOption(options, value);
|
|
75
|
+
if (found) {
|
|
76
|
+
return [formatLabel(found, value, compose), omitChildren(found)];
|
|
77
|
+
}
|
|
78
|
+
return [undefined, undefined];
|
|
79
|
+
}
|
|
80
|
+
return [options, getLabelFn];
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
/**
|
|
84
|
+
* 在函数/回调中获取枚举数据,无需在 React 组件内使用。
|
|
85
|
+
*
|
|
86
|
+
* 枚举数据由 ProConfigProvider 初始化时写入 storage。
|
|
87
|
+
*
|
|
88
|
+
* **同步优先策略**:
|
|
89
|
+
* - 内存缓存命中时直接返回值,无需 `await`
|
|
90
|
+
* - localStorage/sessionStorage 首次调用同步读取并预热内存缓存
|
|
91
|
+
* - indexedDB 首次调用(内存未命中)返回 Promise,需 `await` 兜底
|
|
92
|
+
*
|
|
93
|
+
* 典型用法:在 ProConfigProvider 初始化完成后,事件回调/工具函数中直接调用无需 await:
|
|
94
|
+
*
|
|
95
|
+
* @example
|
|
96
|
+
* // 获取全部枚举(内存命中时同步返回)
|
|
97
|
+
* const allEnums = getEnum(config);
|
|
98
|
+
*
|
|
99
|
+
* // 获取单个枚举 options
|
|
100
|
+
* const [cityOptions, getLabel] = getEnum({ code: 'city', ...config });
|
|
101
|
+
*
|
|
102
|
+
* // 获取多个枚举
|
|
103
|
+
* const { city, status } = getEnum({ codes: ['city', 'status'], ...config });
|
|
104
|
+
*
|
|
105
|
+
* // 根据值查询 label
|
|
106
|
+
* const [label, option] = getEnum({ code: 'city', value: 'sh', ...config });
|
|
107
|
+
*
|
|
108
|
+
* // indexedDB 首次加载时兜底(数据未预热时需 await)
|
|
109
|
+
* const allEnums = await getEnum(config);
|
|
110
|
+
*/
|
|
111
|
+
function getEnum(params) {
|
|
112
|
+
const {
|
|
113
|
+
code,
|
|
114
|
+
codes,
|
|
115
|
+
value,
|
|
116
|
+
values,
|
|
117
|
+
compose,
|
|
118
|
+
storage = baseStorage,
|
|
119
|
+
cacheKey = baseCacheKey
|
|
120
|
+
} = params ?? {};
|
|
121
|
+
if (code && codes) {
|
|
122
|
+
console.error('[getEnum] code 和 codes 不能同时传入');
|
|
123
|
+
return undefined;
|
|
124
|
+
}
|
|
125
|
+
if (value !== undefined && values !== undefined) {
|
|
126
|
+
console.error('[getEnum] value 和 values 不能同时传入');
|
|
127
|
+
return undefined;
|
|
128
|
+
}
|
|
129
|
+
const syncResult = getEnumDataSync(storage, cacheKey);
|
|
130
|
+
if (syncResult !== undefined) {
|
|
131
|
+
return resolveEnumResult(syncResult.data ?? {}, {
|
|
132
|
+
code,
|
|
133
|
+
codes,
|
|
134
|
+
value,
|
|
135
|
+
values,
|
|
136
|
+
compose
|
|
137
|
+
});
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
// indexedDB 首次加载兜底,返回 Promise
|
|
141
|
+
return getEnumData(storage, cacheKey).then(res => {
|
|
142
|
+
return resolveEnumResult(res?.data ?? {}, {
|
|
143
|
+
code,
|
|
144
|
+
codes,
|
|
145
|
+
value,
|
|
146
|
+
values,
|
|
147
|
+
compose
|
|
148
|
+
});
|
|
149
|
+
});
|
|
150
|
+
}
|
|
151
|
+
export default getEnum;
|
|
@@ -1,6 +1,10 @@
|
|
|
1
1
|
import { DataOptionType } from '../propsType';
|
|
2
|
-
type StorageType = 'localStorage' | 'sessionStorage' | 'indexedDB';
|
|
2
|
+
export type StorageType = 'localStorage' | 'sessionStorage' | 'indexedDB';
|
|
3
3
|
export declare const baseCacheKey = "zat-design-pro-component-cacheKey";
|
|
4
|
+
/** v4 默认存储类型 */
|
|
5
|
+
export declare const baseStorage: StorageType;
|
|
6
|
+
/** 模块级内存缓存,key 为 cacheKey,替代原单例 baseEnumStorage 变量 */
|
|
7
|
+
export declare const enumMemoryCache: Map<string, any>;
|
|
4
8
|
interface EnumRes {
|
|
5
9
|
data: Record<string, DataOptionType[]>;
|
|
6
10
|
[key: string]: any;
|
|
@@ -9,10 +13,9 @@ interface EnumRes {
|
|
|
9
13
|
* 获取枚举数据
|
|
10
14
|
* @param storage
|
|
11
15
|
* @param cacheKey
|
|
12
|
-
* @param baseEnumStorage
|
|
13
16
|
* @returns
|
|
14
17
|
*/
|
|
15
|
-
export declare function getEnumData(storage: StorageType, cacheKey: string
|
|
18
|
+
export declare function getEnumData(storage: StorageType, cacheKey: string): EnumRes | Promise<EnumRes>;
|
|
16
19
|
/**
|
|
17
20
|
* 设置枚举数据
|
|
18
21
|
* @param storage
|
|
@@ -26,6 +29,13 @@ export declare function setEnumData(storage: StorageType, cacheKey: string, data
|
|
|
26
29
|
* @param cacheKey
|
|
27
30
|
*/
|
|
28
31
|
export declare function removeEnumData(storage: StorageType, cacheKey: string): Promise<void>;
|
|
32
|
+
/**
|
|
33
|
+
* 从内存缓存或同步存储中同步读取枚举数据,不触发任何异步 I/O。
|
|
34
|
+
* - 内存缓存命中时直接返回
|
|
35
|
+
* - localStorage/sessionStorage 同步读取并预热内存缓存
|
|
36
|
+
* - indexedDB 未命中时返回 undefined(需异步兜底)
|
|
37
|
+
*/
|
|
38
|
+
export declare function getEnumDataSync(storage: StorageType, cacheKey: string): EnumRes | undefined;
|
|
29
39
|
/**
|
|
30
40
|
* 判断枚举列表是否存在
|
|
31
41
|
* @param storage
|
|
@@ -1,6 +1,12 @@
|
|
|
1
1
|
import { get, set, del } from 'idb-keyval';
|
|
2
2
|
export const baseCacheKey = 'zat-design-pro-component-cacheKey';
|
|
3
3
|
|
|
4
|
+
/** v4 默认存储类型 */
|
|
5
|
+
export const baseStorage = 'indexedDB';
|
|
6
|
+
|
|
7
|
+
/** 模块级内存缓存,key 为 cacheKey,替代原单例 baseEnumStorage 变量 */
|
|
8
|
+
export const enumMemoryCache = new Map();
|
|
9
|
+
|
|
4
10
|
// IndexedDB 可用性检测缓存
|
|
5
11
|
let indexedDBAvailable = null;
|
|
6
12
|
|
|
@@ -73,22 +79,23 @@ async function setToIndexedDB(key, value) {
|
|
|
73
79
|
* 获取枚举数据
|
|
74
80
|
* @param storage
|
|
75
81
|
* @param cacheKey
|
|
76
|
-
* @param baseEnumStorage
|
|
77
82
|
* @returns
|
|
78
83
|
*/
|
|
79
|
-
export function getEnumData(storage, cacheKey
|
|
80
|
-
// IndexedDB
|
|
84
|
+
export function getEnumData(storage, cacheKey) {
|
|
85
|
+
// IndexedDB:先查内存缓存,命中则同步返回,避免实际 I/O
|
|
81
86
|
if (storage === 'indexedDB') {
|
|
82
|
-
|
|
87
|
+
if (enumMemoryCache.has(cacheKey)) {
|
|
88
|
+
return Promise.resolve(enumMemoryCache.get(cacheKey));
|
|
89
|
+
}
|
|
90
|
+
return getFromIndexedDB(cacheKey).then(data => {
|
|
91
|
+
enumMemoryCache.set(cacheKey, data);
|
|
92
|
+
return data;
|
|
93
|
+
});
|
|
83
94
|
}
|
|
84
95
|
|
|
85
96
|
// localStorage/sessionStorage 保持同步
|
|
86
|
-
if (baseEnumStorage && window.localStorage.getItem(cacheKey) && cacheKey === baseCacheKey) {
|
|
87
|
-
return baseEnumStorage;
|
|
88
|
-
}
|
|
89
97
|
if (storage === 'localStorage') {
|
|
90
98
|
const data = JSON.parse(window.localStorage.getItem(cacheKey) || '{}');
|
|
91
|
-
// 确保返回的数据格式正确,包含 data 字段
|
|
92
99
|
if (data && typeof data === 'object' && 'data' in data) {
|
|
93
100
|
return data;
|
|
94
101
|
}
|
|
@@ -98,7 +105,6 @@ export function getEnumData(storage, cacheKey, baseEnumStorage) {
|
|
|
98
105
|
}
|
|
99
106
|
if (storage === 'sessionStorage') {
|
|
100
107
|
const data = JSON.parse(window.sessionStorage.getItem(cacheKey) || '{}');
|
|
101
|
-
// 确保返回的数据格式正确,包含 data 字段
|
|
102
108
|
if (data && typeof data === 'object' && 'data' in data) {
|
|
103
109
|
return data;
|
|
104
110
|
}
|
|
@@ -122,8 +128,9 @@ export function setEnumData(storage, cacheKey, data) {
|
|
|
122
128
|
return;
|
|
123
129
|
}
|
|
124
130
|
|
|
125
|
-
// IndexedDB
|
|
131
|
+
// IndexedDB:同步写内存缓存,异步持久化到 IndexedDB
|
|
126
132
|
if (storage === 'indexedDB') {
|
|
133
|
+
enumMemoryCache.set(cacheKey, data);
|
|
127
134
|
return setToIndexedDB(cacheKey, data);
|
|
128
135
|
}
|
|
129
136
|
|
|
@@ -158,6 +165,33 @@ export async function removeEnumData(storage, cacheKey) {
|
|
|
158
165
|
}
|
|
159
166
|
}
|
|
160
167
|
|
|
168
|
+
/**
|
|
169
|
+
* 从内存缓存或同步存储中同步读取枚举数据,不触发任何异步 I/O。
|
|
170
|
+
* - 内存缓存命中时直接返回
|
|
171
|
+
* - localStorage/sessionStorage 同步读取并预热内存缓存
|
|
172
|
+
* - indexedDB 未命中时返回 undefined(需异步兜底)
|
|
173
|
+
*/
|
|
174
|
+
export function getEnumDataSync(storage, cacheKey) {
|
|
175
|
+
if (enumMemoryCache.has(cacheKey)) return enumMemoryCache.get(cacheKey);
|
|
176
|
+
if (storage === 'localStorage') {
|
|
177
|
+
const d = JSON.parse(window.localStorage.getItem(cacheKey) || '{}');
|
|
178
|
+
const res = d?.data ? d : {
|
|
179
|
+
data: {}
|
|
180
|
+
};
|
|
181
|
+
enumMemoryCache.set(cacheKey, res);
|
|
182
|
+
return res;
|
|
183
|
+
}
|
|
184
|
+
if (storage === 'sessionStorage') {
|
|
185
|
+
const d = JSON.parse(window.sessionStorage.getItem(cacheKey) || '{}');
|
|
186
|
+
const res = d?.data ? d : {
|
|
187
|
+
data: {}
|
|
188
|
+
};
|
|
189
|
+
enumMemoryCache.set(cacheKey, res);
|
|
190
|
+
return res;
|
|
191
|
+
}
|
|
192
|
+
return undefined;
|
|
193
|
+
}
|
|
194
|
+
|
|
161
195
|
/**
|
|
162
196
|
* 判断枚举列表是否存在
|
|
163
197
|
* @param storage
|
|
@@ -1,13 +1,12 @@
|
|
|
1
|
-
|
|
2
1
|
.switch-checkbox-view {
|
|
3
|
-
display
|
|
2
|
+
display: flex;
|
|
4
3
|
align-items: center;
|
|
5
4
|
|
|
6
5
|
.switch-checkbox-view-label {
|
|
7
|
-
flex
|
|
8
|
-
overflow
|
|
6
|
+
flex: 0 0 @zaui-form-label-width;
|
|
7
|
+
overflow: initial;
|
|
9
8
|
line-height: 1;
|
|
10
9
|
white-space: pre-wrap;
|
|
11
|
-
color
|
|
10
|
+
color: var(--zaui-aide-text, #939599);
|
|
12
11
|
}
|
|
13
12
|
}
|