简体   繁体   中英

Order of operations after promises

I'm pretty new to JavaScript (using Node.js) and still learning. I try to wrap around my head with promises and I got into this situation where I don't understand if there is a difference between this code:

promiseFunc().then(() => {
     anotherPromiseFunc() // I dont need .then() here, just want to save some data to DB
 });
doSmthElse()

and this code:

promiseFunc().then(async () => {
     await anotherPromiseFunc() // I dont need .then() here, just want to save some data to DB
 });
doSmthElse()

If I don't use .then() in the first case, does it mean there is a possibility that doSmthElse() will be executed before anotherPromiseFunc() is executed? So in order to prevent that, I have to add async / await ? Or all code in .then() block is being waited to execute anyway before doing something else?

Note 1: I don't want to chain those promises, because there is more code in my case, but I just simplified it here.

Note 2: I don't use catch because if error will rip through I will catch it later.

If I don't use .then() in the first case, does it mean there is a possibility that doSmthElse() will be executed before AnotherPromise() is executed?

doSmthElse() is guaranteed to be executed before anything in the fulfillment handler¹ is executed. Promise fulfillment and rejection handlers are always invoked asynchronously. That's true whether you declare the handler function using async or not.

For example:

 console.log("before"); Promise.resolve(42).then(result => { console.log("within", result); }); console.log("after");

The output of that is:

before
after
within 42

So in order to prevent that, I have to add async / await ?

Where you've added async / await in your example doesn't change when doSmthElse() is executed.

If you want doSmthElse() to wait until the promise has been fulfilled, move it into the fulfillment handler.¹

If your code were inside an async function, you could use await instead, like this:

// Inside an `async` function
await promiseFunc().then(() => {
    anotherPromiseFunc();
});
doSmthElse()

That would do this:

  1. Call promiseFunc() and get the promise it returns
  2. Hook up a fulfillment handler to that promise via then , returning a new promise; that new promise is the operand to await
  3. Wait for the promise from #1 to settle
  4. When it does, your fulfillment handler is executed and runs anothterPromiseFunc() but doesn't wait for the promise it returns to settle (because, as you said, you're not returning that promise from the fulfillment handler).
  5. At this point, the promise from #2 is fulfilled because your fulfillment handler has (effectively) returned undefined , which isn't a thenable (loosely, a promise), so that value ( undefined ) is used to fulfill the promise from #2.
  6. Since the promise from #2 has been fulfilled, await is satisfied and doSmthElse() is executed.

¹ the function you pass then as its first argument

I assume that Promise() just stands for some function call returning a Promise:

You could say that.then registers an event listener that runs as soon as the promise settles => the task is finished. It still runs asynchronously So in your example doSmthElse will still run even if the promise hasn't been settled (so if the promise doesn't settle immediately doSmthElse will be called before the function inside.then)

To let your code run "in order". You would have to use await to ensure that doSmthElse is called after the promise settled or you could put doSmthElse into the.then block.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM