preface

Promise, ES6 brings the best gift to front-end developers, saving the masses from the hell of async + callback, before the birth of async/await syntax sugar, as if a man of god, now, today, the flood of await, but has been a lot of pale. Today, I read an article by Siv ENOW’s big front end. When the interviewer asked Promise, he wanted to know what mentioned three shortcomings of Promise.

Perhaps it is the shortcomings of this and that, so that once as a magic weapon it is not as powerful as grammar sugar.

Insufficient optimization

So? When an interviewer asks you a question like, What’s wrong with Promise? Maybe you can talk for a long time. Maybe you can talk for a long time. But at this time, if they were to be shot back, and turn against one another, how to solve these shortcomings? At this time may be afraid, do not know why.

The author meditates and uses higher-order functions for abstraction, which can improve the above deficiencies a little.

Logic is separated from Promise

First, we completely separate promises from internal side effects (delayed scripts/Ajax requests, etc.) logic, leaving only the interface (RES, REJ) part.

function timeoutLog(res, rej) { setTimeout(() => { res('look at me !!!! , i am here'); }, 5000); }Copy the code

The timeoutLog returns a result with a 5 second delay, and the entire function/logic is completely decoupled from the promise. This is very similar to some Node Server middleware such as Express/Egg, where only the parameters (RES, rej) interface is retained.

Higher-order functions

The principle is simple: function returns function

const useStatusInPromise = f => <T extends any>():[Promise<T>, {value: 'pending' | 'done' | 'rejected' = > {}] / / front can add some checks to the health of the f / / store the promise of state internal const status = {value: 'pending'}; const promise = new Promise(f).then(res => { status.value = 'done'; return res; }).catch(err => { status.value = 'rejected'; return err; }).finally(() => { Object.freeze(status); // freeze status to prevent rewriting status}); return [promise as Promise<T>, status as any]; }Copy the code

The results of

MakeStatusPromiseLog const makeStatusPromiseLog = if you want to cancel the promise, you don't need to call makeStatusPromiseLog useStatusInPromise(timeoutLog); // Execute makeStatusPromiseLog and get the Promise instance and state object; // The promise result type returned by the generic constraint const [promise, statusObj] = makeStatusPromiseLog<string>(); Const interval = setInterval (() = > {/ / execution environment can access the state of the promise the if (statusObj. Value = = = 'done' | | statusObj. Value = = = 'rejected') { clearInterval(interval); promise.then(res => { console.log('timeoutLog end, the result is -> ', }). Catch (console.error); Value = 'pending'} else {console.log(' Continue to check promise status ', statusobj.value); }}, 1000);Copy the code

Exception handling

For the second deficiency, the author also did not think of any good solution. For this scenario you have to try catch yourself in the internal logic of the promise

function timeoutLog(res, Rej) {setTimeout(() => {// To prevent internal errors from being reported to the external try catch // try {// throw new Error('happen Error ') //  } catch (err) { // rej(err) // } res('look at me! I am here'); }, 5000); }Copy the code

conclusion

Higher-order functions are a very useful weapon, especially in functional programming, and can be used to solve many problems in general business. For example, some shortcomings of Promise can also be improved