@ives_xxz/framework 1.5.7 → 1.5.8
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/manager/FWPromiseManager.ts +69 -38
- package/package.json +1 -1
|
@@ -1,8 +1,11 @@
|
|
|
1
|
-
import { FWSystemDefine } from
|
|
2
|
-
import FWLog from
|
|
3
|
-
import { FWManager } from
|
|
4
|
-
|
|
5
|
-
export default class FWPromiseManager
|
|
1
|
+
import { FWSystemDefine } from "../define/FWSystemDefine";
|
|
2
|
+
import FWLog from "../log/FWLog";
|
|
3
|
+
import { FWManager } from "./FWManager";
|
|
4
|
+
|
|
5
|
+
export default class FWPromiseManager
|
|
6
|
+
extends FWManager
|
|
7
|
+
implements FW.PromiseManager
|
|
8
|
+
{
|
|
6
9
|
private promiseRegistry: Map<number, FW.PromiseProxy>;
|
|
7
10
|
private uniqueId: number = 0;
|
|
8
11
|
|
|
@@ -18,7 +21,7 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
18
21
|
/** 创建Promise执行器 */
|
|
19
22
|
public execute<T = any>(
|
|
20
23
|
executor: FW.PromiseExcutor<T>,
|
|
21
|
-
options: FW.PromiseExecuteOptions = {}
|
|
24
|
+
options: FW.PromiseExecuteOptions = {}
|
|
22
25
|
): FW.PromiseProxy<T> {
|
|
23
26
|
const id = this.uniqueId++;
|
|
24
27
|
const abortController = new AbortController();
|
|
@@ -30,13 +33,18 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
30
33
|
return new Promise<T>((resolve, reject) => {
|
|
31
34
|
if (options.timeout && options.timeout > 0) {
|
|
32
35
|
timerSchedule = FW.Entry.timeMgr.scheduleOnce(() => {
|
|
33
|
-
const timeoutError = new Error(
|
|
36
|
+
const timeoutError = new Error(
|
|
37
|
+
`Promise ${id} timeout after ${options.timeout} s`
|
|
38
|
+
);
|
|
34
39
|
if (
|
|
35
40
|
retryCount < maxRetryTimes &&
|
|
36
|
-
(!options.retryCondition ||
|
|
41
|
+
(!options.retryCondition ||
|
|
42
|
+
options.retryCondition(timeoutError, retryCount))
|
|
37
43
|
) {
|
|
38
44
|
retryCount++;
|
|
39
|
-
FWLog.debug(
|
|
45
|
+
FWLog.debug(
|
|
46
|
+
`Promise ${id} timeout, retrying (${retryCount}/${maxRetryTimes})`
|
|
47
|
+
);
|
|
40
48
|
if (retryInterval > 0) {
|
|
41
49
|
FW.Entry.timeMgr.scheduleOnce(() => {
|
|
42
50
|
createPromise().then(resolve, reject);
|
|
@@ -64,11 +72,11 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
64
72
|
return;
|
|
65
73
|
}
|
|
66
74
|
|
|
67
|
-
abortController.signal.addEventListener(
|
|
75
|
+
abortController.signal.addEventListener("abort", onAbort);
|
|
68
76
|
|
|
69
77
|
const wrappedResolve = (value: T | PromiseLike<T>) => {
|
|
70
78
|
promiseProxy.status = FWSystemDefine.FWPromiseStatus.FULFILLED;
|
|
71
|
-
abortController.signal.removeEventListener(
|
|
79
|
+
abortController.signal.removeEventListener("abort", onAbort);
|
|
72
80
|
this.removePromise(id);
|
|
73
81
|
timerSchedule?.unSchedule();
|
|
74
82
|
resolve(value);
|
|
@@ -78,10 +86,14 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
78
86
|
timerSchedule?.unSchedule();
|
|
79
87
|
if (
|
|
80
88
|
retryCount < maxRetryTimes &&
|
|
81
|
-
(!options.retryCondition ||
|
|
89
|
+
(!options.retryCondition ||
|
|
90
|
+
options.retryCondition(reason, retryCount))
|
|
82
91
|
) {
|
|
83
92
|
retryCount++;
|
|
84
|
-
FWLog.debug(
|
|
93
|
+
FWLog.debug(
|
|
94
|
+
`Promise ${id} failed, retrying (${retryCount}/${maxRetryTimes}):`,
|
|
95
|
+
reason
|
|
96
|
+
);
|
|
85
97
|
if (retryInterval > 0) {
|
|
86
98
|
FW.Entry.timeMgr.scheduleOnce(() => {
|
|
87
99
|
createPromise().then(resolve, reject);
|
|
@@ -90,16 +102,23 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
90
102
|
createPromise().then(resolve, reject);
|
|
91
103
|
}
|
|
92
104
|
} else {
|
|
93
|
-
if (
|
|
105
|
+
if (
|
|
106
|
+
promiseProxy.status === FWSystemDefine.FWPromiseStatus.PENDING
|
|
107
|
+
) {
|
|
94
108
|
promiseProxy.status = FWSystemDefine.FWPromiseStatus.REJECTED;
|
|
95
|
-
abortController.signal.removeEventListener(
|
|
109
|
+
abortController.signal.removeEventListener("abort", onAbort);
|
|
96
110
|
this.removePromise(id);
|
|
97
111
|
reject(reason);
|
|
98
112
|
}
|
|
99
113
|
}
|
|
100
114
|
};
|
|
101
115
|
try {
|
|
102
|
-
executor(
|
|
116
|
+
executor(
|
|
117
|
+
wrappedResolve,
|
|
118
|
+
wrappedReject,
|
|
119
|
+
abortController.signal,
|
|
120
|
+
options.reason
|
|
121
|
+
);
|
|
103
122
|
} catch (error) {
|
|
104
123
|
wrappedReject(error);
|
|
105
124
|
}
|
|
@@ -114,16 +133,16 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
114
133
|
abortController,
|
|
115
134
|
abort: (reason?: any) => {
|
|
116
135
|
if (promiseProxy.status === FWSystemDefine.FWPromiseStatus.PENDING) {
|
|
117
|
-
FWLog.debug(reason ||
|
|
136
|
+
FWLog.debug(reason || "promise cancelled");
|
|
118
137
|
abortController.abort(reason);
|
|
119
138
|
}
|
|
120
139
|
},
|
|
121
140
|
|
|
122
141
|
addAbortEventListener: (
|
|
123
142
|
listener: (this: AbortSignal, ev: Event) => any,
|
|
124
|
-
options?: boolean | AddEventListenerOptions
|
|
143
|
+
options?: boolean | AddEventListenerOptions
|
|
125
144
|
) => {
|
|
126
|
-
abortController.signal.addEventListener(
|
|
145
|
+
abortController.signal.addEventListener("abort", listener, options);
|
|
127
146
|
},
|
|
128
147
|
};
|
|
129
148
|
|
|
@@ -134,7 +153,7 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
134
153
|
/** 批量执行Promise并等待所有完成 */
|
|
135
154
|
public all<T = any>(
|
|
136
155
|
promises: FW.PromiseProxy<T>[],
|
|
137
|
-
options: FW.PromiseExecuteOptions = {}
|
|
156
|
+
options: FW.PromiseExecuteOptions = {}
|
|
138
157
|
): FW.PromiseProxy<FW.PromiseResult<T>> {
|
|
139
158
|
const id = this.uniqueId++;
|
|
140
159
|
const abortController = new AbortController();
|
|
@@ -148,13 +167,18 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
148
167
|
if (options.timeout && options.timeout > 0) {
|
|
149
168
|
timerSchedule?.unSchedule();
|
|
150
169
|
timerSchedule = FW.Entry.timeMgr.scheduleOnce(() => {
|
|
151
|
-
const timeoutError = new Error(
|
|
170
|
+
const timeoutError = new Error(
|
|
171
|
+
`All Promise ${id} timeout after ${options.timeout} s`
|
|
172
|
+
);
|
|
152
173
|
if (
|
|
153
174
|
retryCount < maxRetryTimes &&
|
|
154
|
-
(!options.retryCondition ||
|
|
175
|
+
(!options.retryCondition ||
|
|
176
|
+
options.retryCondition(timeoutError, retryCount))
|
|
155
177
|
) {
|
|
156
178
|
retryCount++;
|
|
157
|
-
FWLog.debug(
|
|
179
|
+
FWLog.debug(
|
|
180
|
+
`All Promise ${id} timeout, retrying (${retryCount}/${maxRetryTimes})`
|
|
181
|
+
);
|
|
158
182
|
if (retryInterval > 0) {
|
|
159
183
|
FW.Entry.timeMgr.scheduleOnce(() => {
|
|
160
184
|
createPromise().then(resolve, reject);
|
|
@@ -182,7 +206,7 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
182
206
|
return;
|
|
183
207
|
}
|
|
184
208
|
|
|
185
|
-
abortController.signal.addEventListener(
|
|
209
|
+
abortController.signal.addEventListener("abort", onAbort);
|
|
186
210
|
|
|
187
211
|
const processAll = async () => {
|
|
188
212
|
const result: FW.PromiseResult<T> = {
|
|
@@ -199,8 +223,8 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
199
223
|
.filter(
|
|
200
224
|
(id) =>
|
|
201
225
|
!result.success.some((s) => s.id === id) &&
|
|
202
|
-
!result.failed.some((f) => f.id === id)
|
|
203
|
-
)
|
|
226
|
+
!result.failed.some((f) => f.id === id)
|
|
227
|
+
)
|
|
204
228
|
);
|
|
205
229
|
break;
|
|
206
230
|
}
|
|
@@ -209,7 +233,9 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
209
233
|
const value = await promiseProxy.promise;
|
|
210
234
|
result.success.push(value);
|
|
211
235
|
} catch (error) {
|
|
212
|
-
if (
|
|
236
|
+
if (
|
|
237
|
+
promiseProxy.status === FWSystemDefine.FWPromiseStatus.CANCELLED
|
|
238
|
+
) {
|
|
213
239
|
result.cancelled.push(promiseProxy.id);
|
|
214
240
|
} else {
|
|
215
241
|
result.failed.push({
|
|
@@ -226,7 +252,7 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
226
252
|
processAll()
|
|
227
253
|
.then((result) => {
|
|
228
254
|
promiseProxy.status = FWSystemDefine.FWPromiseStatus.FULFILLED;
|
|
229
|
-
abortController.signal.removeEventListener(
|
|
255
|
+
abortController.signal.removeEventListener("abort", onAbort);
|
|
230
256
|
this.removePromise(id);
|
|
231
257
|
timerSchedule?.unSchedule();
|
|
232
258
|
resolve(result);
|
|
@@ -235,12 +261,13 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
235
261
|
timerSchedule?.unSchedule();
|
|
236
262
|
if (
|
|
237
263
|
retryCount < maxRetryTimes &&
|
|
238
|
-
(!options.retryCondition ||
|
|
264
|
+
(!options.retryCondition ||
|
|
265
|
+
options.retryCondition(error, retryCount))
|
|
239
266
|
) {
|
|
240
267
|
retryCount++;
|
|
241
268
|
FWLog.debug(
|
|
242
269
|
`All Promise ${id} failed, retrying (${retryCount}/${maxRetryTimes}):`,
|
|
243
|
-
error
|
|
270
|
+
error
|
|
244
271
|
);
|
|
245
272
|
if (retryInterval > 0) {
|
|
246
273
|
FW.Entry.timeMgr.scheduleOnce(() => {
|
|
@@ -250,9 +277,11 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
250
277
|
createPromise().then(resolve, reject);
|
|
251
278
|
}
|
|
252
279
|
} else {
|
|
253
|
-
if (
|
|
280
|
+
if (
|
|
281
|
+
promiseProxy.status === FWSystemDefine.FWPromiseStatus.PENDING
|
|
282
|
+
) {
|
|
254
283
|
promiseProxy.status = FWSystemDefine.FWPromiseStatus.REJECTED;
|
|
255
|
-
abortController.signal.removeEventListener(
|
|
284
|
+
abortController.signal.removeEventListener("abort", onAbort);
|
|
256
285
|
this.removePromise(id);
|
|
257
286
|
reject(error);
|
|
258
287
|
}
|
|
@@ -269,15 +298,15 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
269
298
|
abortController,
|
|
270
299
|
abort: (reason?: any) => {
|
|
271
300
|
if (promiseProxy.status === FWSystemDefine.FWPromiseStatus.PENDING) {
|
|
272
|
-
FWLog.debug(reason ||
|
|
301
|
+
FWLog.debug(reason || "all promise cancelled");
|
|
273
302
|
abortController.abort(reason);
|
|
274
303
|
}
|
|
275
304
|
},
|
|
276
305
|
addAbortEventListener: (
|
|
277
306
|
listener: (this: AbortSignal, ev: Event) => any,
|
|
278
|
-
options?: boolean | AddEventListenerOptions
|
|
307
|
+
options?: boolean | AddEventListenerOptions
|
|
279
308
|
) => {
|
|
280
|
-
abortController.signal.addEventListener(
|
|
309
|
+
abortController.signal.addEventListener("abort", listener, options);
|
|
281
310
|
},
|
|
282
311
|
};
|
|
283
312
|
|
|
@@ -288,7 +317,10 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
288
317
|
/** 取消指定Promise */
|
|
289
318
|
public cancel(id: number, reason?: any): boolean {
|
|
290
319
|
const promiseProxy = this.promiseRegistry.get(id);
|
|
291
|
-
if (
|
|
320
|
+
if (
|
|
321
|
+
promiseProxy &&
|
|
322
|
+
promiseProxy.status === FWSystemDefine.FWPromiseStatus.PENDING
|
|
323
|
+
) {
|
|
292
324
|
promiseProxy.abort(reason);
|
|
293
325
|
return true;
|
|
294
326
|
}
|
|
@@ -313,7 +345,6 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
313
345
|
promiseProxy.abort(reason);
|
|
314
346
|
cancelled.push(id);
|
|
315
347
|
});
|
|
316
|
-
FWLog.error(cancelled);
|
|
317
348
|
return cancelled;
|
|
318
349
|
}
|
|
319
350
|
|
|
@@ -340,7 +371,7 @@ export default class FWPromiseManager extends FWManager implements FW.PromiseMan
|
|
|
340
371
|
/** 获取正在执行的Promise数量 */
|
|
341
372
|
public getActiveCount(): number {
|
|
342
373
|
return Array.from(this.promiseRegistry.values()).filter(
|
|
343
|
-
(p) => p.status === FWSystemDefine.FWPromiseStatus.PENDING
|
|
374
|
+
(p) => p.status === FWSystemDefine.FWPromiseStatus.PENDING
|
|
344
375
|
).length;
|
|
345
376
|
}
|
|
346
377
|
|