v-dict 2.0.0 → 2.0.2

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.
@@ -12,10 +12,9 @@ function mapToObj(map, {
12
12
  obj = {},
13
13
  itemTransformer
14
14
  } = {}) {
15
- var _a;
16
15
  clearObj(obj);
17
16
  for (const [key, value] of map) {
18
- obj[key] = (_a = itemTransformer == null ? void 0 : itemTransformer(value)) != null ? _a : value;
17
+ obj[key] = isFunction(itemTransformer) ? itemTransformer(value) : value;
19
18
  }
20
19
  return obj;
21
20
  }
package/dist/index.cjs CHANGED
@@ -38,10 +38,9 @@ function mapToObj(map, {
38
38
  obj = {},
39
39
  itemTransformer
40
40
  } = {}) {
41
- var _a;
42
41
  clearObj(obj);
43
42
  for (const [key, value] of map) {
44
- obj[key] = (_a = itemTransformer == null ? void 0 : itemTransformer(value)) != null ? _a : value;
43
+ obj[key] = isFunction(itemTransformer) ? itemTransformer(value) : value;
45
44
  }
46
45
  return obj;
47
46
  }
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
- import { warn, isFunction, cloneDeep, createPromise, mapToObj, mapToList, toMap, merge } from './chunk-SXX4ZFIR.js';
2
- export { defineDictData } from './chunk-SXX4ZFIR.js';
1
+ import { warn, isFunction, cloneDeep, createPromise, mapToObj, mapToList, toMap, merge } from './chunk-E7KZBQBQ.js';
2
+ export { defineDictData } from './chunk-E7KZBQBQ.js';
3
3
  import { reactive, readonly, shallowRef, toRef, ref, watch, computed } from 'vue';
4
4
 
5
5
  function createDictManager(createDictManagerOptions = {}) {
@@ -38,10 +38,9 @@ function mapToObj(map, {
38
38
  obj = {},
39
39
  itemTransformer
40
40
  } = {}) {
41
- var _a;
42
41
  clearObj(obj);
43
42
  for (const [key, value] of map) {
44
- obj[key] = (_a = itemTransformer == null ? void 0 : itemTransformer(value)) != null ? _a : value;
43
+ obj[key] = isFunction(itemTransformer) ? itemTransformer(value) : value;
45
44
  }
46
45
  return obj;
47
46
  }
@@ -141,14 +140,22 @@ function createDictManager(createDictManagerOptions = {}) {
141
140
  } = createDictManagerOptions;
142
141
  const defineDictOptionsMap = /* @__PURE__ */ new Map();
143
142
  const maps = /* @__PURE__ */ Object.create(null);
144
- const versionMap = /* @__PURE__ */ Object.create(null);
143
+ const listenersMap = /* @__PURE__ */ Object.create(null);
144
+ function emitChange(code) {
145
+ var _a;
146
+ const listeners = code ? (_a = listenersMap[code]) != null ? _a : [] : Object.values(listenersMap).flat();
147
+ for (let listener of listeners) {
148
+ listener();
149
+ }
150
+ }
145
151
  function clear(code) {
146
152
  var _a;
147
153
  if (code) {
148
154
  (_a = maps[code]) == null ? void 0 : _a.clear();
149
- return;
155
+ } else {
156
+ Object.values(maps).forEach((map) => map == null ? void 0 : map.clear());
150
157
  }
151
- Object.values(maps).forEach((map) => map.clear());
158
+ emitChange(code);
152
159
  }
153
160
  function _defineDict(defineDictInternalOptions, code, defineDictOptions) {
154
161
  const { pickValues, omitValues, extendCode } = defineDictInternalOptions;
@@ -156,7 +163,6 @@ function createDictManager(createDictManagerOptions = {}) {
156
163
  warn(`code "${code}" already exists`);
157
164
  } else {
158
165
  maps[code] = /* @__PURE__ */ new Map();
159
- versionMap[code] = 0;
160
166
  }
161
167
  const _defineDictOptions = Object.assign(
162
168
  {
@@ -172,23 +178,56 @@ function createDictManager(createDictManagerOptions = {}) {
172
178
  const { data, remote, fetch, extra, transformer, itemTransformer } = _defineDictOptions;
173
179
  let globalLoadPromise = null;
174
180
  let init = false;
175
- async function loadDict(options, mapRef) {
181
+ async function loadDict(options, map = /* @__PURE__ */ new Map()) {
176
182
  var _a;
177
183
  if (remote) {
178
184
  const res = (_a = await (fetch == null ? void 0 : fetch(extendCode != null ? extendCode : code, options))) != null ? _a : [];
179
- toMap(res, { pickValues, omitValues, transformer, map: mapRef.current });
185
+ toMap(res, { pickValues, omitValues, transformer, map });
180
186
  toMap(cloneDeep(data), { pickValues, omitValues, transformer }).forEach(
181
187
  (value, key) => {
182
- if (mapRef.current.has(key)) {
183
- merge(mapRef.current.get(key), value);
188
+ if (map.has(key)) {
189
+ merge(map.get(key), value);
184
190
  }
185
191
  }
186
192
  );
187
193
  } else {
188
- toMap(cloneDeep(data), { pickValues, omitValues, transformer, map: mapRef.current });
194
+ toMap(cloneDeep(data), { pickValues, omitValues, transformer, map });
189
195
  }
190
- versionMap[code] += 1;
196
+ return map;
191
197
  }
198
+ function subscribeMap(listener) {
199
+ var _a;
200
+ listenersMap[code] = [...(_a = listenersMap[code]) != null ? _a : [], listener];
201
+ return () => {
202
+ listenersMap[code] = listenersMap[code].filter((l) => l !== listener);
203
+ };
204
+ }
205
+ function getMapSnapshot() {
206
+ return maps[code];
207
+ }
208
+ const createStateFromMap = (map = /* @__PURE__ */ new Map()) => {
209
+ const newObj = /* @__PURE__ */ Object.create(null);
210
+ const newList = [];
211
+ mapToObj(map, {
212
+ obj: newObj,
213
+ itemTransformer
214
+ });
215
+ mapToList(map, {
216
+ list: newList,
217
+ itemTransformer
218
+ });
219
+ const newE = Object.fromEntries(
220
+ Array.from(map.keys()).map((key) => {
221
+ var _a;
222
+ return [key, (_a = transformer == null ? void 0 : transformer(key)) != null ? _a : key];
223
+ })
224
+ );
225
+ return {
226
+ map: newObj,
227
+ list: newList,
228
+ E: newE
229
+ };
230
+ };
192
231
  function useDict(useDictOptions = {}) {
193
232
  const mergedOptions = {
194
233
  clone: false,
@@ -200,52 +239,37 @@ function createDictManager(createDictManagerOptions = {}) {
200
239
  const loadPromiseRef = react.useRef(
201
240
  !clone ? globalLoadPromise : createPromise()
202
241
  );
203
- const mapRef = react.useRef(!clone ? maps[code] : /* @__PURE__ */ new Map());
204
- const versionRef = react.useRef(0);
205
- const getStateFromMapRef = () => {
206
- const newObj = /* @__PURE__ */ Object.create(null);
207
- const newList = [];
208
- mapToObj(mapRef.current, {
209
- obj: newObj,
210
- itemTransformer
211
- });
212
- mapToList(mapRef.current, {
213
- list: newList,
214
- itemTransformer
215
- });
216
- const newE = Object.fromEntries(
217
- Array.from(mapRef.current.keys()).map((key) => {
218
- var _a;
219
- return [key, (_a = transformer == null ? void 0 : transformer(key)) != null ? _a : key];
220
- })
221
- );
222
- return {
223
- map: newObj,
224
- list: newList,
225
- E: newE
226
- };
227
- };
228
- const [state, setState] = react.useState(getStateFromMapRef());
229
- if (versionRef.current !== versionMap[code]) {
230
- versionRef.current = versionMap[code];
231
- setState(getStateFromMapRef());
232
- }
242
+ const map = react.useSyncExternalStore(subscribeMap, getMapSnapshot);
243
+ const [clonedMap, setClonedMap] = react.useState(/* @__PURE__ */ new Map());
244
+ const state = react.useMemo(
245
+ () => createStateFromMap(!clone ? map : clonedMap),
246
+ [clone, map, clonedMap]
247
+ );
233
248
  const load = react.useCallback((options) => {
234
249
  const oldLoadPromise = loadPromiseRef.current;
235
250
  loadPromiseRef.current = createPromise();
236
- loadDict({ ...mergedOptions, ...options }, mapRef).then(() => {
237
- setState(getStateFromMapRef());
251
+ loadDict({ ...mergedOptions, ...options }).then((map2) => {
252
+ if (!clone) {
253
+ maps[code] = map2;
254
+ emitChange(code);
255
+ } else {
256
+ setClonedMap(map2);
257
+ }
238
258
  oldLoadPromise == null ? void 0 : oldLoadPromise.resolve(void 0);
239
259
  loadPromiseRef.current.resolve(void 0);
240
260
  });
241
261
  return loadPromiseRef.current;
242
262
  }, []);
243
263
  const clear2 = react.useCallback(() => {
244
- mapRef.current.clear();
245
- setState(getStateFromMapRef());
264
+ if (!clone) {
265
+ maps[code] = /* @__PURE__ */ new Map();
266
+ emitChange(code);
267
+ return;
268
+ }
269
+ setClonedMap(map);
246
270
  }, []);
247
271
  const getItem = react.useCallback((value) => {
248
- return value !== null && value !== void 0 ? mapRef.current.get(value) : null;
272
+ return value !== null && value !== void 0 ? state.map[value] : null;
249
273
  }, []);
250
274
  react.useEffect(() => {
251
275
  if (!remote || immediate) {
@@ -290,7 +314,7 @@ function createDictManager(createDictManagerOptions = {}) {
290
314
  // @ts-ignore
291
315
  ...extra == null ? void 0 : extra(_ctx)
292
316
  };
293
- }, [state]);
317
+ }, [state, loadPromiseRef.current]);
294
318
  return ctx;
295
319
  }
296
320
  useDict.extend = (extendCode2, extendOptions) => {
@@ -1,6 +1,6 @@
1
- import { warn, isFunction, cloneDeep, createPromise, toMap, merge, mapToObj, mapToList } from '../chunk-SXX4ZFIR.js';
2
- export { defineDictData } from '../chunk-SXX4ZFIR.js';
3
- import { useRef, useState, useCallback, useEffect, useMemo } from 'react';
1
+ import { warn, isFunction, cloneDeep, createPromise, toMap, merge, mapToObj, mapToList } from '../chunk-E7KZBQBQ.js';
2
+ export { defineDictData } from '../chunk-E7KZBQBQ.js';
3
+ import { useRef, useSyncExternalStore, useState, useMemo, useCallback, useEffect } from 'react';
4
4
 
5
5
  function createDictManager(createDictManagerOptions = {}) {
6
6
  const {
@@ -11,14 +11,22 @@ function createDictManager(createDictManagerOptions = {}) {
11
11
  } = createDictManagerOptions;
12
12
  const defineDictOptionsMap = /* @__PURE__ */ new Map();
13
13
  const maps = /* @__PURE__ */ Object.create(null);
14
- const versionMap = /* @__PURE__ */ Object.create(null);
14
+ const listenersMap = /* @__PURE__ */ Object.create(null);
15
+ function emitChange(code) {
16
+ var _a;
17
+ const listeners = code ? (_a = listenersMap[code]) != null ? _a : [] : Object.values(listenersMap).flat();
18
+ for (let listener of listeners) {
19
+ listener();
20
+ }
21
+ }
15
22
  function clear(code) {
16
23
  var _a;
17
24
  if (code) {
18
25
  (_a = maps[code]) == null ? void 0 : _a.clear();
19
- return;
26
+ } else {
27
+ Object.values(maps).forEach((map) => map == null ? void 0 : map.clear());
20
28
  }
21
- Object.values(maps).forEach((map) => map.clear());
29
+ emitChange(code);
22
30
  }
23
31
  function _defineDict(defineDictInternalOptions, code, defineDictOptions) {
24
32
  const { pickValues, omitValues, extendCode } = defineDictInternalOptions;
@@ -26,7 +34,6 @@ function createDictManager(createDictManagerOptions = {}) {
26
34
  warn(`code "${code}" already exists`);
27
35
  } else {
28
36
  maps[code] = /* @__PURE__ */ new Map();
29
- versionMap[code] = 0;
30
37
  }
31
38
  const _defineDictOptions = Object.assign(
32
39
  {
@@ -42,23 +49,56 @@ function createDictManager(createDictManagerOptions = {}) {
42
49
  const { data, remote, fetch, extra, transformer, itemTransformer } = _defineDictOptions;
43
50
  let globalLoadPromise = null;
44
51
  let init = false;
45
- async function loadDict(options, mapRef) {
52
+ async function loadDict(options, map = /* @__PURE__ */ new Map()) {
46
53
  var _a;
47
54
  if (remote) {
48
55
  const res = (_a = await (fetch == null ? void 0 : fetch(extendCode != null ? extendCode : code, options))) != null ? _a : [];
49
- toMap(res, { pickValues, omitValues, transformer, map: mapRef.current });
56
+ toMap(res, { pickValues, omitValues, transformer, map });
50
57
  toMap(cloneDeep(data), { pickValues, omitValues, transformer }).forEach(
51
58
  (value, key) => {
52
- if (mapRef.current.has(key)) {
53
- merge(mapRef.current.get(key), value);
59
+ if (map.has(key)) {
60
+ merge(map.get(key), value);
54
61
  }
55
62
  }
56
63
  );
57
64
  } else {
58
- toMap(cloneDeep(data), { pickValues, omitValues, transformer, map: mapRef.current });
65
+ toMap(cloneDeep(data), { pickValues, omitValues, transformer, map });
59
66
  }
60
- versionMap[code] += 1;
67
+ return map;
61
68
  }
69
+ function subscribeMap(listener) {
70
+ var _a;
71
+ listenersMap[code] = [...(_a = listenersMap[code]) != null ? _a : [], listener];
72
+ return () => {
73
+ listenersMap[code] = listenersMap[code].filter((l) => l !== listener);
74
+ };
75
+ }
76
+ function getMapSnapshot() {
77
+ return maps[code];
78
+ }
79
+ const createStateFromMap = (map = /* @__PURE__ */ new Map()) => {
80
+ const newObj = /* @__PURE__ */ Object.create(null);
81
+ const newList = [];
82
+ mapToObj(map, {
83
+ obj: newObj,
84
+ itemTransformer
85
+ });
86
+ mapToList(map, {
87
+ list: newList,
88
+ itemTransformer
89
+ });
90
+ const newE = Object.fromEntries(
91
+ Array.from(map.keys()).map((key) => {
92
+ var _a;
93
+ return [key, (_a = transformer == null ? void 0 : transformer(key)) != null ? _a : key];
94
+ })
95
+ );
96
+ return {
97
+ map: newObj,
98
+ list: newList,
99
+ E: newE
100
+ };
101
+ };
62
102
  function useDict(useDictOptions = {}) {
63
103
  const mergedOptions = {
64
104
  clone: false,
@@ -70,52 +110,37 @@ function createDictManager(createDictManagerOptions = {}) {
70
110
  const loadPromiseRef = useRef(
71
111
  !clone ? globalLoadPromise : createPromise()
72
112
  );
73
- const mapRef = useRef(!clone ? maps[code] : /* @__PURE__ */ new Map());
74
- const versionRef = useRef(0);
75
- const getStateFromMapRef = () => {
76
- const newObj = /* @__PURE__ */ Object.create(null);
77
- const newList = [];
78
- mapToObj(mapRef.current, {
79
- obj: newObj,
80
- itemTransformer
81
- });
82
- mapToList(mapRef.current, {
83
- list: newList,
84
- itemTransformer
85
- });
86
- const newE = Object.fromEntries(
87
- Array.from(mapRef.current.keys()).map((key) => {
88
- var _a;
89
- return [key, (_a = transformer == null ? void 0 : transformer(key)) != null ? _a : key];
90
- })
91
- );
92
- return {
93
- map: newObj,
94
- list: newList,
95
- E: newE
96
- };
97
- };
98
- const [state, setState] = useState(getStateFromMapRef());
99
- if (versionRef.current !== versionMap[code]) {
100
- versionRef.current = versionMap[code];
101
- setState(getStateFromMapRef());
102
- }
113
+ const map = useSyncExternalStore(subscribeMap, getMapSnapshot);
114
+ const [clonedMap, setClonedMap] = useState(/* @__PURE__ */ new Map());
115
+ const state = useMemo(
116
+ () => createStateFromMap(!clone ? map : clonedMap),
117
+ [clone, map, clonedMap]
118
+ );
103
119
  const load = useCallback((options) => {
104
120
  const oldLoadPromise = loadPromiseRef.current;
105
121
  loadPromiseRef.current = createPromise();
106
- loadDict({ ...mergedOptions, ...options }, mapRef).then(() => {
107
- setState(getStateFromMapRef());
122
+ loadDict({ ...mergedOptions, ...options }).then((map2) => {
123
+ if (!clone) {
124
+ maps[code] = map2;
125
+ emitChange(code);
126
+ } else {
127
+ setClonedMap(map2);
128
+ }
108
129
  oldLoadPromise == null ? void 0 : oldLoadPromise.resolve(void 0);
109
130
  loadPromiseRef.current.resolve(void 0);
110
131
  });
111
132
  return loadPromiseRef.current;
112
133
  }, []);
113
134
  const clear2 = useCallback(() => {
114
- mapRef.current.clear();
115
- setState(getStateFromMapRef());
135
+ if (!clone) {
136
+ maps[code] = /* @__PURE__ */ new Map();
137
+ emitChange(code);
138
+ return;
139
+ }
140
+ setClonedMap(map);
116
141
  }, []);
117
142
  const getItem = useCallback((value) => {
118
- return value !== null && value !== void 0 ? mapRef.current.get(value) : null;
143
+ return value !== null && value !== void 0 ? state.map[value] : null;
119
144
  }, []);
120
145
  useEffect(() => {
121
146
  if (!remote || immediate) {
@@ -160,7 +185,7 @@ function createDictManager(createDictManagerOptions = {}) {
160
185
  // @ts-ignore
161
186
  ...extra == null ? void 0 : extra(_ctx)
162
187
  };
163
- }, [state]);
188
+ }, [state, loadPromiseRef.current]);
164
189
  return ctx;
165
190
  }
166
191
  useDict.extend = (extendCode2, extendOptions) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "v-dict",
3
- "version": "2.0.0",
3
+ "version": "2.0.2",
4
4
  "type": "module",
5
5
  "description": "Vue3 & React Dict Manager",
6
6
  "repository": {
@@ -48,8 +48,8 @@
48
48
  "dependencies": {},
49
49
  "peerDependencies": {
50
50
  "vue": "^3.0.0",
51
- "react": "^16.8.0 || ^17.0.0 || ^18.0.0",
52
- "react-dom": "^16.8.0 || ^17.0.0 || ^18.0.0"
51
+ "react": ">=16.8.0",
52
+ "react-dom": ">=16.8.0"
53
53
  },
54
54
  "devDependencies": {
55
55
  "@changesets/cli": "^2.27.1",