DEV Community

All about Promises and async / await

Arden de Raaij on January 20, 2018

Recently I revisited Wes Bos his ES6 for everyone course and made some notes on the Promise and async / await modules. These notes got a little out...
Collapse
 
nickytonline profile image
Nick Taylor

Arden, thanks for the writeup.

In regards to the section “Awaiting multiple promises”, I would reword “Adding an await statement before your promises makes your code truly synchronous,” as it’s not correct. The await keyword allows you to write asynchronous code in a synchronous fashion, but the code running is still asynchronous. When there’s two awaits in a row, all that’s happening is the first asynchronous action is executed and when it’s complete (provided there's no error), only then does the next awaitable action run asynchronously as well.

When using Promise.all I prefer to destructure the results. I find it reads better, e.g. const [dog1Result, dog2Result] = await Promise.all([dog1, dog2]);

For those new to Promises, to complement the resource list in this post, I highly recommend practicing ES6 Katas over at es6katas.org. They have a great section on Promises.

Collapse
 
ardennl profile image
Arden de Raaij

Oh thank you so much, that's great feedback which I'll implement ASAP. Those katas are awesome by the way. I've been going at them for 30 minutes now and am just devouring them. I feel confident now 💪

Collapse
 
jjjjcccjjf profile image
endan • Edited

I have been struggling with Promises for about a week (or two?) now. Last night, I just read your blog post before I sleep and I can't sleep! Because I know I have already fixed the problem in my head. And now, it's 6:26am here. I opened my laptop, made some tea, applied what I learned and BAM! It worked on the first try! I knew it! 😊 I knew this post would be enlightening! Btw, here's my code! ✨

exports.register = function (req, res) {
  var user = new Users(req.body)

  const hash = Users.hashPassword(user.password)
  const activationCode = Users.generateActivationCode() // REVIEW: Refactor?? hmmm

  Promise.all([activationCode, hash])
  .then(function ([activationCode, hash]) {
    user.activationCode = activationCode
    user.password = hash
    save()
  })
  .catch((err) => console.error(err))

  function save () {
    user.save(function (err, doc) {
      if (err) {
        res.send(err)
      } else {
        user.sendActivationCode()
        res.json(doc)
      }
    })
  }
}

Many many thanks! I have read this blog earlier and it turns out your post was a very nice addition reading to this!

Collapse
 
ardennl profile image
Arden de Raaij

Seriously this the best way to start my week with, thank you!! I'm so glad to hear you fixed your problem with my article 🙌. The code is looking good, what are you working on?

Collapse
 
jjjjcccjjf profile image
endan • Edited

Thank you! 😁 Your article is really good!

Ah, I've been working on a REST API side project (to be consumed by a React app, which I have yet to learn 😆). My weapon of choice is really PHP, but I started to learn Node intermittently since December. My main reason of doing so is Electron and React Native and as well as React. It's blows me away to use just one language across all stacks! And as well as PWAs (service workers operating on JS).

I have one last question though. In Javascript for Dummies blog, there's a code snippet that I'll paste below:

/* ES6 */
const isMomHappy = true;

// Promise
const willIGetNewPhone = new Promise(
    (resolve, reject) => { // fat arrow
        if (isMomHappy) {
            const phone = {
                brand: 'Samsung',
                color: 'black'
            };
            resolve(phone);
        } else {
            const reason = new Error('mom is not happy');
            reject(reason);
        }

    }
);

const showOff = function (phone) {
    const message = 'Hey friend, I have a new ' +
                phone.color + ' ' + phone.brand + ' phone';
    return Promise.resolve(message);
};

// call our promise
const askMom = function () {
    willIGetNewPhone
        .then(showOff)
        .then(fulfilled => console.log(fulfilled)) // fat arrow
        .catch(error => console.log(error.message)); // fat arrow
};

askMom();

As you can notice here, the author used 2 different syntax in returning a promise. The first one is the (resolve, reject) => arrow function style, and the second one is Promise.resolve(message). My question is, is there a "right" way of doing promises? Should one just keep it consistent or let it adjust based on one's code?

Or is it not important at all?

Also, if you noticed in my code, I didn't use fat arrow functions because I'm not too comfortable with them (yet). Is it "okay" to do this or it's really just preference and consistency?

Sorry for many questions, and thanks again! ☺

Thread Thread
 
ardennl profile image
Arden de Raaij

Cool!! Don't hesitate to blog about your progress, I've yet to make an API in node but I'm sure I will need to do something like that soon.

I totally agree, JavaScript at both the client and server side is pretty damn amazing isn't it.

About the different Promise syntax examples, that is actually a really good question! The difference between the two are not that big, besides that the first one offers a clear way to reject a promise, and the second one does not. If you'd return undefined in showOff, that would probably throw a wrench in the process. Apparently there's another subtle difference but I have yet to understand this: stackoverflow.com/questions/267112... 😂

Personally I'm all for consistency. I like the fat arrow function and got used to how they work with this, but if you're not totally comfortable with them yet, a normal function calls is just as good!!

Thread Thread
 
jjjjcccjjf profile image
endan

Thanks a lot!! 😁

Collapse
 
aravindballa profile image
Aravind Balla • Edited

An amazing line from @wesbos podcast syntaxfm

await(await(fetch('https://api.github.com/users/wesbos'))).json();
Enter fullscreen mode Exit fullscreen mode
Collapse
 
jrop profile image
Jonathan Apodaca

I personally prefer the following form:

await fetch('https://api.github.com/users/wesbos').then(r => r.json())
Collapse
 
ardennl profile image
Arden de Raaij

That's a gem! I do feel like not everyone would get what's going on here on first glance though!

Collapse
 
jjjjcccjjf profile image
endan

I appreciate your effort to write something like this. It's really helpful for beginners like me. Thank you! I love how you write as well. 😁

Collapse
 
jjjjcccjjf profile image
endan • Edited

Sorry to ask @ardennl but can you talk about Transpilers (Babel, etc) next? 😊

Collapse
 
ardennl profile image
Arden de Raaij

Thanks for the kind words! And definitely, that is a great idea! I was thinking about topics for my next blog post, this just might be it.

Thread Thread
 
jjjjcccjjf profile image
endan

Alright! I'm super excited! Thank you so much!

Collapse
 
developius profile image
Finnian Anderson

This is awesome! I've learnt a few different tricks here, my favourite being using .catch() on an async function, I didn't know you could do that. Thanks 💯

Collapse
 
ardennl profile image
Arden de Raaij • Edited

Thank you! There's so much written about promises I wasn't sure I should publish this, but I'm glat I did! Also got so much info out of it myself 🙌

Collapse
 
rajeshroyal profile image
Rajesh Royal

Danger, Will Robinson, danger! waiting for next season

Collapse
 
n13 profile image
Nik

Very good and very clear, thank you

Collapse
 
ardennl profile image
Arden de Raaij

Thank you, appreciate the feedback!