@cassiewang/cassie-store 1.0.0

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.
Files changed (55) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +43 -0
  3. package/dist/AsyncDemo/index.d.ts +3 -0
  4. package/dist/AsyncDemo/index.js +209 -0
  5. package/dist/AsyncDemo/userStore.d.ts +22 -0
  6. package/dist/AsyncDemo/userStore.js +365 -0
  7. package/dist/ComputedDemo/index.d.ts +3 -0
  8. package/dist/ComputedDemo/index.js +118 -0
  9. package/dist/ComputedDemo/shoppingCartStore.d.ts +19 -0
  10. package/dist/ComputedDemo/shoppingCartStore.js +106 -0
  11. package/dist/Foo/index.d.ts +5 -0
  12. package/dist/Foo/index.js +5 -0
  13. package/dist/Manager/AsyncManager.d.ts +22 -0
  14. package/dist/Manager/AsyncManager.js +111 -0
  15. package/dist/Model.d.ts +43 -0
  16. package/dist/Model.js +210 -0
  17. package/dist/UseGetState/TestComponent.d.ts +7 -0
  18. package/dist/UseGetState/TestComponent.js +97 -0
  19. package/dist/UseGetState/counterStore.d.ts +11 -0
  20. package/dist/UseGetState/counterStore.js +31 -0
  21. package/dist/UseGetState/index.d.ts +3 -0
  22. package/dist/UseGetState/index.js +21 -0
  23. package/dist/UseGetStateDemo/counterStore.d.ts +9 -0
  24. package/dist/UseGetStateDemo/counterStore.js +29 -0
  25. package/dist/UseGetStateDemo/index.d.ts +3 -0
  26. package/dist/UseGetStateDemo/index.js +65 -0
  27. package/dist/WatchDemo/index.d.ts +3 -0
  28. package/dist/WatchDemo/index.js +88 -0
  29. package/dist/WatchDemo/themeStore.d.ts +14 -0
  30. package/dist/WatchDemo/themeStore.js +159 -0
  31. package/dist/WatchDemo1/index.d.ts +3 -0
  32. package/dist/WatchDemo1/index.js +91 -0
  33. package/dist/WatchDemo1/themeStore.d.ts +14 -0
  34. package/dist/WatchDemo1/themeStore.js +151 -0
  35. package/dist/hooks/index.d.ts +3 -0
  36. package/dist/hooks/index.js +3 -0
  37. package/dist/hooks/useCreation.d.ts +1 -0
  38. package/dist/hooks/useCreation.js +8 -0
  39. package/dist/hooks/useLatest.d.ts +2 -0
  40. package/dist/hooks/useLatest.js +6 -0
  41. package/dist/hooks/useMemoizedFn.d.ts +1 -0
  42. package/dist/hooks/useMemoizedFn.js +8 -0
  43. package/dist/index.d.ts +1 -0
  44. package/dist/index.js +1 -0
  45. package/dist/type.d.ts +15 -0
  46. package/dist/type.js +1 -0
  47. package/dist/utils/event.d.ts +15 -0
  48. package/dist/utils/event.js +83 -0
  49. package/dist/utils/index.d.ts +2 -0
  50. package/dist/utils/index.js +4 -0
  51. package/dist/utils/object.d.ts +1 -0
  52. package/dist/utils/object.js +23 -0
  53. package/dist/utils/utils.d.ts +17 -0
  54. package/dist/utils/utils.js +105 -0
  55. package/package.json +118 -0
@@ -0,0 +1,111 @@
1
+ function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (o) { return typeof o; } : function (o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); }
2
+ function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
3
+ function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, _toPropertyKey(descriptor.key), descriptor); } }
4
+ function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); Object.defineProperty(Constructor, "prototype", { writable: false }); return Constructor; }
5
+ function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function"); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, writable: true, configurable: true } }); Object.defineProperty(subClass, "prototype", { writable: false }); if (superClass) _setPrototypeOf(subClass, superClass); }
6
+ function _setPrototypeOf(o, p) { _setPrototypeOf = Object.setPrototypeOf ? Object.setPrototypeOf.bind() : function _setPrototypeOf(o, p) { o.__proto__ = p; return o; }; return _setPrototypeOf(o, p); }
7
+ function _createSuper(Derived) { var hasNativeReflectConstruct = _isNativeReflectConstruct(); return function _createSuperInternal() { var Super = _getPrototypeOf(Derived), result; if (hasNativeReflectConstruct) { var NewTarget = _getPrototypeOf(this).constructor; result = Reflect.construct(Super, arguments, NewTarget); } else { result = Super.apply(this, arguments); } return _possibleConstructorReturn(this, result); }; }
8
+ function _possibleConstructorReturn(self, call) { if (call && (_typeof(call) === "object" || typeof call === "function")) { return call; } else if (call !== void 0) { throw new TypeError("Derived constructors may only return object or undefined"); } return _assertThisInitialized(self); }
9
+ function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; }
10
+ function _isNativeReflectConstruct() { if (typeof Reflect === "undefined" || !Reflect.construct) return false; if (Reflect.construct.sham) return false; if (typeof Proxy === "function") return true; try { Boolean.prototype.valueOf.call(Reflect.construct(Boolean, [], function () {})); return true; } catch (e) { return false; } }
11
+ function _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf.bind() : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); }
12
+ function _defineProperty(obj, key, value) { key = _toPropertyKey(key); if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
13
+ function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : String(i); }
14
+ function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
15
+ // src/Manager/AsyncManager.ts - AsyncManager类实现
16
+ import { EventEmitter2 } from "../utils/event";
17
+ var DEFAULT_TIMEOUT = 300;
18
+ export var AsyncManager = /*#__PURE__*/function (_EventEmitter) {
19
+ _inherits(AsyncManager, _EventEmitter);
20
+ var _super = _createSuper(AsyncManager);
21
+ // 存储每个请求的控制器
22
+
23
+ function AsyncManager(options) {
24
+ var _this;
25
+ _classCallCheck(this, AsyncManager);
26
+ _this = _super.call(this);
27
+ _defineProperty(_assertThisInitialized(_this), "execId", 0);
28
+ // 执行ID,用于解决竞态条件
29
+ _defineProperty(_assertThisInitialized(_this), "options", {});
30
+ _defineProperty(_assertThisInitialized(_this), "abortSignalMap", {});
31
+ if (options) {
32
+ _this.options = options;
33
+ }
34
+ return _this;
35
+ }
36
+
37
+ // 获取当前执行ID
38
+ _createClass(AsyncManager, [{
39
+ key: "getCurrentExecId",
40
+ value: function getCurrentExecId() {
41
+ return this.execId;
42
+ }
43
+
44
+ // 获取指定执行ID的控制器
45
+ }, {
46
+ key: "getAbortController",
47
+ value: function getAbortController(execId) {
48
+ return this.abortSignalMap[execId];
49
+ }
50
+
51
+ // 🎯 核心方法:执行异步操作
52
+ }, {
53
+ key: "exec",
54
+ value: function exec(fn) {
55
+ var _this2 = this;
56
+ var tryCount = 0;
57
+ var execId = ++this.execId; // 生成新的执行ID
58
+ console.log("\u5148\u6267\u884C\u7684 execId: ".concat(execId, ", \u5F53\u524D\u6700\u65B0\u7684 this.execId: ").concat(this.execId));
59
+ // 触发loading事件
60
+ this.emit('loading');
61
+ return new Promise(function (resolve, reject) {
62
+ var _exec = function _exec() {
63
+ // 获取上一个请求的控制器
64
+ var lastAbortController = _this2.abortSignalMap[execId - 1] || null;
65
+
66
+ // 创建当前请求的控制器
67
+ var abortController = _this2.abortSignalMap[execId] = new AbortController();
68
+
69
+ // 执行用户提供的异步函数
70
+ fn({
71
+ lastAbortController: lastAbortController,
72
+ abortController: abortController
73
+ }, tryCount).then(function (res) {
74
+ // 🎯 关键:只有最新的请求才处理成功结果
75
+ console.log('then execId, this.execId:', execId, _this2.execId);
76
+ if (execId === _this2.execId) {
77
+ _this2.emit('success', res);
78
+ }
79
+ resolve(res);
80
+ delete _this2.abortSignalMap[execId];
81
+ _this2.emit('finish', null, res);
82
+ return res;
83
+ }).catch(function (e) {
84
+ // 🎯 关键:只有最新的请求才处理错误
85
+ if (execId === _this2.execId) {
86
+ // 检查是否需要重试
87
+ if (tryCount < (_this2.options.retryCount || 0)) {
88
+ setTimeout(function () {
89
+ _exec(); // 重试
90
+ }, _this2.options.retryInterval || DEFAULT_TIMEOUT);
91
+ } else {
92
+ _this2.emit('error', e);
93
+ reject(e);
94
+ delete _this2.abortSignalMap[execId];
95
+ _this2.emit('finish', e, null);
96
+ }
97
+ } else {
98
+ // 非最新请求,直接清理并拒绝
99
+ delete _this2.abortSignalMap[execId];
100
+ _this2.emit('finish', e, null);
101
+ reject(e);
102
+ }
103
+ tryCount++;
104
+ });
105
+ };
106
+ _exec(); // 开始执行
107
+ });
108
+ }
109
+ }]);
110
+ return AsyncManager;
111
+ }(EventEmitter2);
@@ -0,0 +1,43 @@
1
+ import type { IDispatchOptions, TEqualityFn, TComputed, TWatch } from './type';
2
+ import { AsyncManager } from './Manager/AsyncManager';
3
+ import type { AsyncManagerOptions } from './Manager/AsyncManager';
4
+ type IEffects<M extends Model<any, any>> = Record<string, ((this: M, ...args: any[]) => any) | any>;
5
+ export interface IModelConfig<TState extends Record<string, any> = Record<string, any>, TEffects extends IEffects<Model<TState, TEffects>> = IEffects<Model>> {
6
+ state: TState;
7
+ effects?: Partial<TEffects>;
8
+ watch?: TWatch<TState>;
9
+ computed?: TComputed<TState>;
10
+ }
11
+ type TSubscribeFunc<TState extends Record<string, any> = Record<string, any>, TEffects extends Record<string, any> = Record<string, any>> = (state: Model<TState, TEffects>, silent: boolean) => any;
12
+ export declare class Model<TState extends Record<string, any> = Record<string, any>, TEffects extends Record<string, any> = Record<string, any>> {
13
+ config: IModelConfig<TState, TEffects>;
14
+ isUnMount: boolean;
15
+ state: TState;
16
+ _preState: TState;
17
+ _subscribes: TSubscribeFunc<TState, TEffects>[];
18
+ _isInited: boolean;
19
+ asyncManagerMap: Record<string, AsyncManager<Partial<TState>, (aborts: {
20
+ lastAbortController: AbortController | null;
21
+ abortController: AbortController;
22
+ }, tryCount: number) => Promise<Partial<TState>>>>;
23
+ constructor(config: IModelConfig<TState, TEffects>);
24
+ asyncManager(name: string, options?: {
25
+ loadingKey?: string;
26
+ errorKey?: string;
27
+ config?: AsyncManagerOptions;
28
+ showLoading?: boolean;
29
+ }): AsyncManager<Partial<TState>, (aborts: {
30
+ lastAbortController: AbortController | null;
31
+ abortController: AbortController;
32
+ }, tryCount: number) => Promise<Partial<TState>>>;
33
+ init(): void;
34
+ getState: () => TState;
35
+ setState(state: Partial<TState> | ((state: TState) => Partial<TState>), options?: IDispatchOptions): void;
36
+ getActualState(prevState: TState, payload: Partial<TState>): TState;
37
+ dispatch(options?: IDispatchOptions): void;
38
+ subscribe(func: TSubscribeFunc<TState, TEffects>): () => void;
39
+ unsubscribe(func: TSubscribeFunc<TState, TEffects>): void;
40
+ useSelector: (equalityFn?: TEqualityFn<TState>) => TState;
41
+ useGetState: <Key extends keyof TState & string>(keys?: Key[], equalityFn?: TEqualityFn<TState>) => TState;
42
+ }
43
+ export {};
package/dist/Model.js ADDED
@@ -0,0 +1,210 @@
1
+ function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
2
+ function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
3
+ function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (o) { return typeof o; } : function (o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); }
4
+ function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
5
+ function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, _toPropertyKey(descriptor.key), descriptor); } }
6
+ function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); Object.defineProperty(Constructor, "prototype", { writable: false }); return Constructor; }
7
+ function _defineProperty(obj, key, value) { key = _toPropertyKey(key); if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
8
+ function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : String(i); }
9
+ function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
10
+ import { useCallback } from 'react';
11
+ import useSyncExternalStoreExports from 'use-sync-external-store/shim/with-selector';
12
+ import { shallowEqualKeys, execWatchHandler } from "./utils";
13
+ import { useMemoizedFn } from "./hooks";
14
+ import { calcComputedState } from "./utils"; // 🆕 新增导入
15
+
16
+ import { AsyncManager } from "./Manager/AsyncManager";
17
+ var useSyncExternalStoreWithSelector = useSyncExternalStoreExports.useSyncExternalStoreWithSelector;
18
+
19
+ // src/type.ts - 扩展现有的IModelConfig接口
20
+
21
+ export var Model = /*#__PURE__*/function () {
22
+ function Model(config) {
23
+ var _this = this;
24
+ _classCallCheck(this, Model);
25
+ _defineProperty(this, "isUnMount", false);
26
+ _defineProperty(this, "state", {});
27
+ _defineProperty(this, "_preState", {});
28
+ _defineProperty(this, "_subscribes", []);
29
+ _defineProperty(this, "_isInited", false);
30
+ _defineProperty(this, "asyncManagerMap", {});
31
+ _defineProperty(this, "getState", function () {
32
+ if (!_this._isInited) {
33
+ _this.init();
34
+ }
35
+ return _this.state;
36
+ });
37
+ _defineProperty(this, "useSelector", function (equalityFn) {
38
+ var subscribe = useCallback(function (listener) {
39
+ return _this.subscribe(function (_, silent) {
40
+ if (!silent) {
41
+ listener();
42
+ }
43
+ });
44
+ }, [_this]);
45
+ var selector = useMemoizedFn(function (state) {
46
+ return state;
47
+ });
48
+ var isEqual = useMemoizedFn(function (prevState, nextState) {
49
+ if (equalityFn) {
50
+ return equalityFn(prevState, nextState);
51
+ }
52
+ return Object.is(prevState, nextState);
53
+ });
54
+ var state = useSyncExternalStoreWithSelector(subscribe, _this.getState, _this.getState, selector, isEqual);
55
+ return state;
56
+ });
57
+ _defineProperty(this, "useGetState", function (keys, equalityFn) {
58
+ return _this.useSelector(function (prevState, nextState) {
59
+ if (equalityFn) {
60
+ return equalityFn(prevState, nextState);
61
+ }
62
+ if (keys && shallowEqualKeys(prevState, nextState, keys)) {
63
+ return true;
64
+ }
65
+ return false;
66
+ });
67
+ });
68
+ this.config = config;
69
+ }
70
+
71
+ // 🆕 新增:asyncManager方法(源码中的实现)
72
+ _createClass(Model, [{
73
+ key: "asyncManager",
74
+ value: function asyncManager(name, options) {
75
+ var _this2 = this;
76
+ var _ref = options || {},
77
+ _ref$loadingKey = _ref.loadingKey,
78
+ loadingKey = _ref$loadingKey === void 0 ? 'loading' : _ref$loadingKey,
79
+ _ref$errorKey = _ref.errorKey,
80
+ errorKey = _ref$errorKey === void 0 ? 'error' : _ref$errorKey,
81
+ _ref$showLoading = _ref.showLoading,
82
+ showLoading = _ref$showLoading === void 0 ? true : _ref$showLoading,
83
+ config = _ref.config;
84
+
85
+ // 如果不存在,创建新的AsyncManager
86
+ if (!this.asyncManagerMap[name]) {
87
+ this.asyncManagerMap[name] = new AsyncManager(config);
88
+ }
89
+ var asyncManager = this.asyncManagerMap[name];
90
+
91
+ // 🎯 关键:清除之前的监听器,重新绑定
92
+ asyncManager.offAllListeners();
93
+
94
+ // 🎯 绑定loading事件
95
+ asyncManager.on('loading', function () {
96
+ if (showLoading) {
97
+ _this2.setState(_defineProperty({}, loadingKey, true));
98
+ }
99
+ });
100
+
101
+ // 🎯 绑定success事件
102
+ asyncManager.on('success', function (result) {
103
+ if (_typeof(result) === 'object' && result !== null) {
104
+ _this2.setState(_objectSpread(_defineProperty({}, loadingKey, false), result));
105
+ }
106
+ });
107
+
108
+ // 🎯 绑定error事件
109
+ asyncManager.on('error', function (error) {
110
+ _this2.setState(_defineProperty(_defineProperty({}, loadingKey, false), errorKey, error));
111
+ });
112
+ return this.asyncManagerMap[name];
113
+ }
114
+
115
+ // 🔧 修改:init方法,使用getActualState
116
+ }, {
117
+ key: "init",
118
+ value: function init() {
119
+ if (!this._isInited) {
120
+ this._isInited = true;
121
+ var _config = this.config;
122
+
123
+ // 🆕 使用getActualState处理初始状态(包含计算属性)
124
+ this.state = this.getActualState({}, _config.state || {});
125
+ this._preState = _objectSpread({}, this.state);
126
+ }
127
+ }
128
+ }, {
129
+ key: "setState",
130
+ value:
131
+ // 🔧 修改:setState方法,使用getActualState
132
+ function setState(state, options) {
133
+ if (!this._isInited) {
134
+ this.init();
135
+ }
136
+ if (state) {
137
+ // 1. 处理函数形式的state
138
+ var payload;
139
+ if (typeof state === 'function') {
140
+ payload = state(this.state);
141
+ } else {
142
+ payload = state;
143
+ }
144
+
145
+ // 🆕 2. 使用getActualState处理状态(包含计算属性)
146
+ this.state = this.getActualState(this._preState, payload);
147
+
148
+ // 3. 分发更新
149
+ this.dispatch(options);
150
+ this._preState = _objectSpread({}, this.state);
151
+ }
152
+ }
153
+
154
+ // 🆕 新增:getActualState方法(源码中的核心方法)
155
+ }, {
156
+ key: "getActualState",
157
+ value: function getActualState(prevState, payload) {
158
+ // 1. 合并状态
159
+ var nextState = _objectSpread(_objectSpread({}, prevState), payload);
160
+
161
+ // 2. 获取配置
162
+ var _ref2 = this.config || {},
163
+ computed = _ref2.computed,
164
+ watch = _ref2.watch;
165
+
166
+ // 🆕 3. 处理计算属性
167
+ nextState = calcComputedState({
168
+ prevState: prevState,
169
+ nextState: nextState,
170
+ computed: computed
171
+ });
172
+
173
+ // 4. 执行 watch
174
+ execWatchHandler({
175
+ prevState: prevState,
176
+ nextState: nextState,
177
+ watch: watch
178
+ });
179
+ return nextState;
180
+ }
181
+ }, {
182
+ key: "dispatch",
183
+ value: function dispatch(options) {
184
+ var _this3 = this;
185
+ if (this.isUnMount) return;
186
+ this._subscribes.forEach(function (func) {
187
+ return func(_this3, (options === null || options === void 0 ? void 0 : options.silent) || false);
188
+ });
189
+ }
190
+ }, {
191
+ key: "subscribe",
192
+ value: function subscribe(func) {
193
+ var _this4 = this;
194
+ this._subscribes.push(func);
195
+ return function () {
196
+ _this4.unsubscribe(func);
197
+ };
198
+ }
199
+ }, {
200
+ key: "unsubscribe",
201
+ value: function unsubscribe(func) {
202
+ if (this._subscribes.length) {
203
+ this._subscribes = this._subscribes.filter(function (fn) {
204
+ return fn !== func;
205
+ });
206
+ }
207
+ }
208
+ }]);
209
+ return Model;
210
+ }();
@@ -0,0 +1,7 @@
1
+ import React from 'react';
2
+ declare function FullStateComponent(): React.JSX.Element;
3
+ declare function CountOnlyComponent(): React.JSX.Element;
4
+ declare function NameOnlyComponent(): React.JSX.Element;
5
+ declare function CustomEqualityComponent(): React.JSX.Element;
6
+ declare function ControlPanel(): React.JSX.Element;
7
+ export { FullStateComponent, CountOnlyComponent, NameOnlyComponent, CustomEqualityComponent, ControlPanel };
@@ -0,0 +1,97 @@
1
+ import React from 'react';
2
+ import { counterStore, increment, decrement, updateName } from "./counterStore";
3
+
4
+ // 完整状态组件
5
+ function FullStateComponent() {
6
+ debugger;
7
+ var state = counterStore.useGetState();
8
+ console.log('FullStateComponent 重新渲染');
9
+ return /*#__PURE__*/React.createElement("div", {
10
+ style: {
11
+ padding: "10px",
12
+ border: "1px solid #ccc",
13
+ margin: '5px'
14
+ }
15
+ }, /*#__PURE__*/React.createElement("h3", null, "\u5B8C\u6574\u72B6\u6001\u7EC4\u4EF6"), /*#__PURE__*/React.createElement("div", null, "\u8BA1\u6570\uFF1A", state.count), /*#__PURE__*/React.createElement("div", null, "\u540D\u79F0\uFF1A", state.name), /*#__PURE__*/React.createElement("div", null, "\u66F4\u65B0\u65F6\u95F4\uFF1A", new Date(state.lastUpdated).toLocaleTimeString()));
16
+ }
17
+
18
+ // 只关心 count 的组件
19
+ function CountOnlyComponent() {
20
+ debugger;
21
+ var state = counterStore.useGetState(['count']);
22
+ console.log(state, 'state121==');
23
+ console.log('CountOnlyComponent 重新渲染');
24
+ return /*#__PURE__*/React.createElement("div", {
25
+ style: {
26
+ padding: '10px',
27
+ border: "1px solid #00f",
28
+ margin: "5px"
29
+ }
30
+ }, /*#__PURE__*/React.createElement("h3", null, "\u53EA\u5173\u5FC3Count\u7684\u7EC4\u4EF6"), /*#__PURE__*/React.createElement("div", null, "\u8BA1\u6570\uFF1A", state.count));
31
+ }
32
+ // 只关心name的组件
33
+ function NameOnlyComponent() {
34
+ var state = counterStore.useGetState(['name']);
35
+ console.log('NameOnlyComponent 重新渲染');
36
+ console.log(state, 'state456==');
37
+ return /*#__PURE__*/React.createElement("div", {
38
+ style: {
39
+ padding: "10px",
40
+ border: '1px solid #0f0',
41
+ margin: '5px'
42
+ }
43
+ }, /*#__PURE__*/React.createElement("h3", null, "\u53EA\u5173\u5FC3Name\u7684\u7EC4\u4EF6"), /*#__PURE__*/React.createElement("div", null, "\u540D\u79F0", state.name));
44
+ }
45
+
46
+ // 自定义相等性检查的组件
47
+ function CustomEqualityComponent() {
48
+ debugger;
49
+ // 只有当 count 变化超过5s 才重新渲染
50
+ var state = counterStore.useGetState(undefined, function (prev, next) {
51
+ return Math.abs(prev.count - next.count) < 5;
52
+ });
53
+ console.log('CustomEqualityComponent 重新渲染');
54
+ return /*#__PURE__*/React.createElement("div", {
55
+ style: {
56
+ padding: "10px",
57
+ border: '1px solid #f00',
58
+ margin: "5px"
59
+ }
60
+ }, /*#__PURE__*/React.createElement("h3", null, "\u81EA\u5B9A\u4E49\u76F8\u7B49\u6027\u68C0\u67E5\u7EC4\u4EF6"), /*#__PURE__*/React.createElement("div", null, "\u8BA1\u6570\uFF1A", state.count, " \uFF08\u53EA\u6709\u53D8\u5316\u8D85\u8FC75 \u624D\u91CD\u65B0\u6E32\u67D3\uFF09"));
61
+ }
62
+
63
+ // 控制面板
64
+ function ControlPanel() {
65
+ return /*#__PURE__*/React.createElement("div", {
66
+ style: {
67
+ padding: '20px',
68
+ background: "#f5f5f5",
69
+ margin: "10px"
70
+ }
71
+ }, /*#__PURE__*/React.createElement("h3", null, "\u63A7\u5236\u9762\u677F"), /*#__PURE__*/React.createElement("button", {
72
+ onClick: increment,
73
+ style: {
74
+ margin: '5px'
75
+ }
76
+ }, "\u589E\u52A0\u8BA1\u6570"), /*#__PURE__*/React.createElement("button", {
77
+ onClick: decrement,
78
+ style: {
79
+ margin: '5px'
80
+ }
81
+ }, "\u51CF\u5C11\u8BA1\u6570"), /*#__PURE__*/React.createElement("button", {
82
+ onClick: function onClick() {
83
+ return updateName('Updated Name');
84
+ },
85
+ style: {
86
+ margin: '5px'
87
+ }
88
+ }, "\u66F4\u65B0\u540D\u79F0"), /*#__PURE__*/React.createElement("button", {
89
+ onClick: function onClick() {
90
+ return updateName('My Counter');
91
+ },
92
+ style: {
93
+ margin: '5px'
94
+ }
95
+ }, "\u91CD\u7F6E\u540D\u79F0"));
96
+ }
97
+ export { FullStateComponent, CountOnlyComponent, NameOnlyComponent, CustomEqualityComponent, ControlPanel };
@@ -0,0 +1,11 @@
1
+ import { Model } from '../Model';
2
+ interface CounterState {
3
+ count: number;
4
+ name: string;
5
+ lastUpdated: number;
6
+ }
7
+ declare const counterStore: Model<CounterState, Record<string, any>>;
8
+ declare const increment: () => void;
9
+ declare const decrement: () => void;
10
+ declare const updateName: (name: string) => void;
11
+ export { counterStore, increment, decrement, updateName };
@@ -0,0 +1,31 @@
1
+ import { Model } from "../Model";
2
+ var counterStore = new Model({
3
+ state: {
4
+ count: 0,
5
+ name: 'My Counter',
6
+ lastUpdated: Date.now()
7
+ }
8
+ });
9
+ // 辅助函数
10
+ var increment = function increment() {
11
+ debugger;
12
+ var currentState = counterStore.getState();
13
+ counterStore.setState({
14
+ count: currentState.count + 1,
15
+ lastUpdated: Date.now()
16
+ });
17
+ };
18
+ var decrement = function decrement() {
19
+ var currentState = counterStore.getState();
20
+ counterStore.setState({
21
+ count: currentState.count - 1,
22
+ lastUpdated: Date.now()
23
+ });
24
+ };
25
+ var updateName = function updateName(name) {
26
+ counterStore.setState({
27
+ name: name,
28
+ lastUpdated: Date.now()
29
+ });
30
+ };
31
+ export { counterStore, increment, decrement, updateName };
@@ -0,0 +1,3 @@
1
+ import React from 'react';
2
+ declare function App(): React.JSX.Element;
3
+ export default App;
@@ -0,0 +1,21 @@
1
+ import React from 'react';
2
+ import { FullStateComponent, CountOnlyComponent, NameOnlyComponent, CustomEqualityComponent, ControlPanel } from "./TestComponent";
3
+ function App() {
4
+ return /*#__PURE__*/React.createElement("div", {
5
+ style: {
6
+ padding: "20px"
7
+ }
8
+ }, /*#__PURE__*/React.createElement("h1", null, "useGetState Hook \u6D4B\u8BD5"), /*#__PURE__*/React.createElement(ControlPanel, null), /*#__PURE__*/React.createElement("div", {
9
+ style: {
10
+ display: 'flex',
11
+ flexWrap: 'wrap'
12
+ }
13
+ }, /*#__PURE__*/React.createElement(FullStateComponent, null), /*#__PURE__*/React.createElement(CountOnlyComponent, null), /*#__PURE__*/React.createElement(NameOnlyComponent, null), /*#__PURE__*/React.createElement(CustomEqualityComponent, null)), /*#__PURE__*/React.createElement("div", {
14
+ style: {
15
+ marginTop: '20px',
16
+ padding: '15px',
17
+ background: '#fff3cd'
18
+ }
19
+ }, /*#__PURE__*/React.createElement("h3", null, "\u6D4B\u8BD5\u8BF4\u660E\uFF1A"), /*#__PURE__*/React.createElement("ul", null, /*#__PURE__*/React.createElement("li", null, /*#__PURE__*/React.createElement("strong", null, "\u70B9\u51FB\"\u589E\u52A0\u8BA1\u6570\""), "\uFF1AFullStateComponent \u548C CountOnlyComponent \u4F1A\u91CD\u65B0\u6E32\u67D3"), /*#__PURE__*/React.createElement("li", null, /*#__PURE__*/React.createElement("strong", null, "\u70B9\u51FB\"\u66F4\u65B0\u540D\u79F0\""), "\uFF1AFullStateComponent \u548C NameOnlyComponent \u4F1A\u91CD\u65B0\u6E32\u67D3"), /*#__PURE__*/React.createElement("li", null, /*#__PURE__*/React.createElement("strong", null, "CustomEqualityComponent"), "\uFF1A\u53EA\u6709\u8BA1\u6570\u53D8\u5316\u8D85\u8FC75\u65F6\u624D\u91CD\u65B0\u6E32\u67D3"), /*#__PURE__*/React.createElement("li", null, /*#__PURE__*/React.createElement("strong", null, "\u6253\u5F00\u63A7\u5236\u53F0"), "\uFF1A\u89C2\u5BDF\u5404\u7EC4\u4EF6\u7684\u91CD\u65B0\u6E32\u67D3\u65E5\u5FD7"))));
20
+ }
21
+ export default App;
@@ -0,0 +1,9 @@
1
+ import { Model } from '../Model';
2
+ interface CounterState {
3
+ count: number;
4
+ name: string;
5
+ }
6
+ declare const counterStore: Model<CounterState, Record<string, any>>;
7
+ declare const increment: () => void;
8
+ declare const decrement: () => void;
9
+ export { counterStore, increment, decrement };
@@ -0,0 +1,29 @@
1
+ import { Model } from "../Model";
2
+
3
+ // 🔧 修正:Store创建方式
4
+
5
+ // 修正前(错误):
6
+ // const counterStore = new Model({ count: 0, name: 'My Counter' });
7
+
8
+ // 修正后(正确):
9
+ var counterStore = new Model({
10
+ state: {
11
+ count: 0,
12
+ name: 'My Counter'
13
+ }
14
+ });
15
+
16
+ // 创建辅助函数
17
+ var increment = function increment() {
18
+ var currentState = counterStore.getState();
19
+ counterStore.setState({
20
+ count: currentState.count + 1
21
+ });
22
+ };
23
+ var decrement = function decrement() {
24
+ var currentState = counterStore.getState();
25
+ counterStore.setState({
26
+ count: currentState.count - 1
27
+ });
28
+ };
29
+ export { counterStore, increment, decrement };
@@ -0,0 +1,3 @@
1
+ import React from 'react';
2
+ declare function App(): React.JSX.Element;
3
+ export default App;
@@ -0,0 +1,65 @@
1
+ import React from 'react';
2
+ // 导入store和辅助函数
3
+ import { counterStore, increment, decrement } from "./counterStore"; // 根据你的文件路径调整
4
+
5
+ // 主计数器组件 - 使用完整状态
6
+ function Counter() {
7
+ // 🎯 使用完整状态(不传keys参数)
8
+ var state = counterStore.useGetState();
9
+ console.log('Counter组件重新渲染'); // 观察渲染次数
10
+
11
+ return /*#__PURE__*/React.createElement("div", {
12
+ style: {
13
+ padding: '20px',
14
+ border: '1px solid #ccc',
15
+ margin: '10px'
16
+ }
17
+ }, /*#__PURE__*/React.createElement("h2", null, state.name), /*#__PURE__*/React.createElement("div", {
18
+ style: {
19
+ fontSize: '24px',
20
+ margin: '10px 0'
21
+ }
22
+ }, "\u8BA1\u6570: ", state.count), /*#__PURE__*/React.createElement("button", {
23
+ onClick: increment
24
+ }, "+1"), /*#__PURE__*/React.createElement("button", {
25
+ onClick: decrement
26
+ }, "-1"));
27
+ }
28
+
29
+ // 显示组件 - 只关心count字段
30
+ function CountDisplay() {
31
+ // 🎯 使用选择性订阅,只关心count字段
32
+ var state = counterStore.useGetState(['count']);
33
+ console.log('CountDisplay组件重新渲染');
34
+ return /*#__PURE__*/React.createElement("div", {
35
+ style: {
36
+ padding: '10px',
37
+ background: '#f0f0f0',
38
+ margin: '10px'
39
+ }
40
+ }, "\u5F53\u524D\u8BA1\u6570: ", state.count);
41
+ }
42
+
43
+ // 只显示名字的组件 - 只关心name字段
44
+ function NameDisplay() {
45
+ // 🎯 使用选择性订阅,只关心name字段
46
+ var state = counterStore.useGetState(['name']);
47
+ console.log('NameDisplay组件重新渲染');
48
+ return /*#__PURE__*/React.createElement("div", {
49
+ style: {
50
+ padding: '10px',
51
+ background: '#e0e0e0',
52
+ margin: '10px'
53
+ }
54
+ }, "\u540D\u79F0: ", state.name);
55
+ }
56
+ function App() {
57
+ return /*#__PURE__*/React.createElement("div", null, /*#__PURE__*/React.createElement("h1", null, "useGetState Hook \u6D4B\u8BD5"), /*#__PURE__*/React.createElement(Counter, null), /*#__PURE__*/React.createElement(CountDisplay, null), /*#__PURE__*/React.createElement(NameDisplay, null), /*#__PURE__*/React.createElement("div", {
58
+ style: {
59
+ margin: '20px',
60
+ padding: '10px',
61
+ background: '#fff3cd'
62
+ }
63
+ }, /*#__PURE__*/React.createElement("h3", null, "\u6D4B\u8BD5\u8BF4\u660E\uFF1A"), /*#__PURE__*/React.createElement("p", null, "1. \u70B9\u51FB+1/-1\u6309\u94AE\uFF0C\u89C2\u5BDF\u6240\u6709\u7EC4\u4EF6\u90FD\u4F1A\u91CD\u65B0\u6E32\u67D3"), /*#__PURE__*/React.createElement("p", null, "2. \u6253\u5F00\u63A7\u5236\u53F0\uFF0C\u89C2\u5BDF\u6E32\u67D3\u65E5\u5FD7"), /*#__PURE__*/React.createElement("p", null, "3. \u8FD9\u8BF4\u660E\u6240\u6709\u7EC4\u4EF6\u90FD\u6210\u529F\u8BA2\u9605\u4E86\u72B6\u6001\u53D8\u5316")));
64
+ }
65
+ export default App;
@@ -0,0 +1,3 @@
1
+ import React from 'react';
2
+ declare function ThemeDemo(): React.JSX.Element;
3
+ export default ThemeDemo;