Skip to content

Commit 6ad56f1

Browse files
committed
better sync promise?
1 parent 09a413f commit 6ad56f1

File tree

1 file changed

+64
-64
lines changed

1 file changed

+64
-64
lines changed

packages/core/src/utils-hoist/syncpromise.ts

Lines changed: 64 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ export function rejectedSyncPromise<T = never>(reason?: any): PromiseLike<T> {
3939
});
4040
}
4141

42+
type Executor<T> = (resolve: (value?: T | PromiseLike<T> | null) => void, reject: (reason?: any) => void) => void;
43+
4244
/**
4345
* Thenable class that behaves like a Promise and follows it's interface
4446
* but is not async internally
@@ -47,73 +49,12 @@ export class SyncPromise<T> implements PromiseLike<T> {
4749
private _state: States;
4850
private _handlers: Array<[boolean, (value: T) => void, (reason: any) => any]>;
4951
private _value: any;
50-
private _resolve: (value?: T | PromiseLike<T> | null) => void;
51-
private _reject: (reason?: any) => void;
52-
private _executeHandlers: () => void;
53-
private _setResult: (state: States, value?: T | PromiseLike<T> | any) => void;
54-
55-
public constructor(
56-
executor: (resolve: (value?: T | PromiseLike<T> | null) => void, reject: (reason?: any) => void) => void,
57-
) {
52+
53+
public constructor(executor: Executor<T>) {
5854
this._state = States.PENDING;
5955
this._handlers = [];
6056

61-
// We set this functions here as class properties, to make binding them easier
62-
// This way, the `this` context is easier to maintain
63-
this._resolve = (value?: T | PromiseLike<T> | null) => {
64-
this._setResult(States.RESOLVED, value);
65-
};
66-
67-
this._reject = (reason?: any) => {
68-
this._setResult(States.REJECTED, reason);
69-
};
70-
71-
this._executeHandlers = () => {
72-
if (this._state === States.PENDING) {
73-
return;
74-
}
75-
76-
const cachedHandlers = this._handlers.slice();
77-
this._handlers = [];
78-
79-
cachedHandlers.forEach(handler => {
80-
if (handler[0]) {
81-
return;
82-
}
83-
84-
if (this._state === States.RESOLVED) {
85-
handler[1](this._value as unknown as any);
86-
}
87-
88-
if (this._state === States.REJECTED) {
89-
handler[2](this._value);
90-
}
91-
92-
handler[0] = true;
93-
});
94-
};
95-
96-
this._setResult = (state: States, value?: T | PromiseLike<T> | any) => {
97-
if (this._state !== States.PENDING) {
98-
return;
99-
}
100-
101-
if (isThenable(value)) {
102-
void (value as PromiseLike<T>).then(this._resolve, this._reject);
103-
return;
104-
}
105-
106-
this._state = state;
107-
this._value = value;
108-
109-
this._executeHandlers();
110-
};
111-
112-
try {
113-
executor(this._resolve, this._reject);
114-
} catch (e) {
115-
this._reject(e);
116-
}
57+
this._runExecutor(executor);
11758
}
11859

11960
/** @inheritdoc */
@@ -191,4 +132,63 @@ export class SyncPromise<T> implements PromiseLike<T> {
191132
});
192133
});
193134
}
135+
136+
/** Excute the resolve/reject handlers. */
137+
private _executeHandlers(): void {
138+
if (this._state === States.PENDING) {
139+
return;
140+
}
141+
142+
const cachedHandlers = this._handlers.slice();
143+
this._handlers = [];
144+
145+
cachedHandlers.forEach(handler => {
146+
if (handler[0]) {
147+
return;
148+
}
149+
150+
if (this._state === States.RESOLVED) {
151+
handler[1](this._value as unknown as any);
152+
}
153+
154+
if (this._state === States.REJECTED) {
155+
handler[2](this._value);
156+
}
157+
158+
handler[0] = true;
159+
});
160+
}
161+
162+
/** Run the executor for the SyncPromise. */
163+
private _runExecutor(executor: Executor<T>): void {
164+
const setResult = (state: States, value?: T | PromiseLike<T> | any): void => {
165+
if (this._state !== States.PENDING) {
166+
return;
167+
}
168+
169+
if (isThenable(value)) {
170+
void (value as PromiseLike<T>).then(resolve, reject);
171+
return;
172+
}
173+
174+
this._state = state;
175+
this._value = value;
176+
177+
this._executeHandlers();
178+
};
179+
180+
const resolve = (value: unknown): void => {
181+
setResult(States.RESOLVED, value);
182+
};
183+
184+
const reject = (reason: unknown): void => {
185+
setResult(States.REJECTED, reason);
186+
};
187+
188+
try {
189+
executor(resolve, reject);
190+
} catch (e) {
191+
reject(e);
192+
}
193+
}
194194
}

0 commit comments

Comments
 (0)