# Promises made a bit easier

**URL:** <https://community.homey.app/t/promises-made-a-bit-easier/8965>\
**Category:** Developers\
**Tags:** programming, javascript\
**Created:** [February 9, 2019, 11:19am UTC](https://community.homey.app/t/promises-made-a-bit-easier/8965 "2019-02-09T11:19:12Z")\
**Posts on this page:** 3\
**Page:** 1

<div class="post-metadata">

**Author:** ![robertklep](https://sea1.discourse-cdn.com/flex025/user_avatar/community.homey.app/robertklep/32/160628_2.png) [@robertklep](https://community.homey.app/u/robertklep)\
**Post date:** [February 9, 2019, 11:19am UTC](https://community.homey.app/t/promises-made-a-bit-easier/8965/1 "2019-02-09T11:19:12Z")

</div>

# Promises made a bit easier

I’ve noticed that some developers, especially the ones without an extensive Javascript (JS) background, can struggle a bit with understanding promises. I decided to do a write-up that explains what they are, how they work, how you can use them, and some pitfalls and tricks.

### What’s a promise?

A promise represents the outcome of a certain asynchronous operation, even when that operation has not yet finished. It is quite literally a promise that _once_ the operation is done, a function will be called with the outcome. That outcome can either be a success (which means the promise will be _resolved_), or it can be a failure (which means the promise will be _rejected_).

Each of those outcomes will call a different function, that you pass to `.then()` or `.catch()`:

```javascript
// Method #1:
myAsynchronousFunction().then(successHandler, errorHandler)
// Method #2:
myAsynchronousFunction().then(successHandler).catch(errorHandler)

```

There are subtle differences between these two notations. Practically speaking,_“Method #2”_ is preferred.

### What’s the difference between promises and callbacks?

Before promises, Node.js relied on using callback functions to handle the results of asynchronous operations. Semantically, they work similar to promises: a function will be called when the operation has completed. Syntactically, they look very different:

```javascript
// Promise
function myDelayFunction(ms) {
  return new Promise(function(resolve, reject) {
    setTimeout(function() {
      resolve();
    }, ms);
  });
}
myDelayFunction(1000).then(function() {
  console.log('1000ms have passed!');
})

// Callback
function myDelayFunction(ms, callback) {
  setTimeout(function() {
    callback();
  }, ms);
}
myDelayFunction(1000, function() {
  console.log('1000ms have passed!');
})

```

If you have the option to choose between promises or callbacks, use promises. Especially combined with `async/await`, they will make your code much more readable and maintainable.

### `async/await`

I’m sure that you’re familiar with `async/await`, or at least have seen it used. How is that related to promises?

Actually, `async/await` is syntactic sugar to deal with promises:

- `await` waits for a promise to be resolved or rejected before continuing.  
In other words, these two examples do the same:

- a function marked `async` will _always_ implicitly return a promise:

- throwing an error inside an `async` function will return a rejected promise:

Instead of using `.then/.catch`, using `async/await` is preferred because it makes reading _and_ writing your code much easier. A typical problem with `.then/.catch` is the so-called _“Promise Pyramid of Doom”_:

```javascript
readDirectory().then(function(files) {
  readFile(files[0]).then(function(contents) {
    writeFile(files[0], contents + "EXTRA DATA").then(function() {
      verifyFile(files[0]).then(function(result) {
        console.log('all done!', result);
      })
    })
  })
})

```

Even though this can be mitigated by “promise chaining”, where instead of calling the `.then()` on the promise returned by the “next” step, you return that promise:

```javascript
readDirectory().then(function(files) {
  readFile(files[0]).then(function(contents) {
    return writeFile(files[0], contents + "EXTRA DATA");
  }).then(function() {
    return verifyFile(files[0]);
  }).then(function(result) {
    console.log('all done!', result);
  })
})

```

But still, using `async/await` makes the code much more readable:

```javascript
const files = await readDirectory();
const contents = await readFile(files[0]);

await writeFile(files[0], contents + "EXTRA DATA");

const result = await verifyFile(files[0]);
console.log('all done!', result);

```

#### Caveats

- `await` only works in functions that are marked `async`, and this does not propagate down. In certain situations, for instance when dealing with event handlers, this can be confusing:

### When to create a new promise

It’s becoming less and less common to have to create promises yourself. Most of Homey’s SDK is based on promises (with callbacks being offered for backward compatibility for existing code), and most external modules also use promises.

One example that still needs manual promise creation is to “promisify” `setTimeout`:

```javascript
function delay(ms) {
  return new Promise(function(resolve) {
    setTimeout(function() {
      resolve();
    }, ms)
  })
}

// Usage:
async function myAsynchronousFunction() {
  // delay for 5 seconds before we continue
  await delay(5000);
  ...
}

```

And another example that I sometimes use in Homey drivers (because, oddly enough, `Driver.ready` is a method that _only_ accepts a callback, and _doesn’t_ return a promise):

```javascript
class MyDriver extends Homey.Driver {
  ...
  waitForReady() {
    const driver = this;
    return new Promise(function(resolve) {
      driver.ready(resolve);
    })
  }
}

// Usage, for instance inside a device:
class MyDevice extends Homey.Device {
  async onInit() {
    // Wait for driver to become ready before we continue.
    await this.getDriver().waitForReady();
    ...
  }
}

```

### Promise caveats

- a common anti-pattern is to wrap a promise chain inside a `new Promise`:

- if an asynchronous function offers the option of using promises _or_ callbacks, pick _one_. Don’t use both:

## Various tidbits

### `try/catch`

Using `try/catch` in JS can be confusing. For instance, this doesn’t work as expected:

```javascript
try {
  myAsynchronousFunction().then(function() {
    throw Error('ohnoes');
  })
} catch(err) {
    ...
}

```

This will actually cause an `UnhandledPromiseRejectionWarning`, meaning that the exception wasn’t caught by the `catch`. So why is that?

The JS interpreter will run the statements inside of a `try` block, and if any of those statements result in an _immediate_ exception, the `catch` block gets triggered. But in the example code above, the exception isn’t thrown _immediately_: it’s thrown when the promise is resolved. But this is done asynchronously, meaning “somewhere in the future”.

It doesn’t matter if `myAsynchronousFunction` doesn’t actually do anything besides returning a promise: it is inherent to promises (and any asynchronous function) that their handling will be queued and postponed (specifically, until the call stack is empty). This is too late for the `catch` to get involved.

So `try/catch` cannot be used for asynchronous code? Well, it can, but _only_ when combined with `async/await`. So this _will_ work as expected:

```javascript
try {
  await myAsynchronousFunction();
  throw Error('ohnoes')
} catch(err) {
  ...
}

```

Rule of thumb: don’t use `try/catch` for asynchronous code, _except_ for when you’re using `async/await`.

### Arrow function notation

I have refrained from using arrow function notation in all of the examples above, for clarity reasons. This doesn’t mean that you shouldn’t use them, and, in fact, I would recommend using them.

Arrow functions are great if your code looks like this:

```javascript
function someMethod() {
  const instance = this:
  someFunction().then(function(result) {
    instance.setResult(result);
  });
}

```

The problem here is that the value of `this` inside the promise success handler is typically useless, so if you want to access the `this` from before the call to `someFunction`, you have to store it in a temporary variable `instance`.

Using arrow functions will solve this (pun intended) by making the value of `this` _inside_ the function the same as it was _outside_ the function:

```javascript
function someMethod() {
  someFunction().then(result => {
    this.setResult(result);
  });
}

```

Technically speaking, you can do the same with “regular” function expressions too, using [`Function.prototype.bind`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/bind):

```javascript
function someMethod() {
  someFunction().then(function(result) {
    instance.setResult(result);
  }.bind(this));
}

```

But it’s much more preferable to use arrow function notation.

As always, there are subtleties involved, and using arrow function notation in some situations may cause problems. Typically, this happens when you’re using external modules that specifically set `this` (much like the `.bind` example above).

### Resolving multiple promises in parallel

Sometimes you need to perform various asynchronous functions at the same time. You can, of course, use this:

```javascript
const result1 = await myAsynchronousFunction1();
const result2 = await myAsynchronousFunction2();
const result3 = await myAsynchronousFunction3();

```

This will run each asynchronous function sequentially, one after the other. This isn’t necessarily very efficient, because Node.js is very good at handling concurrent asynchronos functions. So if the functions are independent of each other (that is, the functions don’t depend on the results of the other functions), you can run them concurrently, in parallel, using [`Promise.all`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise/all):

```javascript
const [result1, result2, result3] = await Promise.all([
  await myAsynchronousFunction1(),
  await myAsynchronousFunction2(),
  await myAsynchronousFunction3()
]);

```

One caveat is that if any of the functions fails due to an exception, `Promise.all` will fail too.

---

<div class="post-metadata">

**Author:** ![Yianni](https://sea1.discourse-cdn.com/flex025/user_avatar/community.homey.app/yianni/32/9675_2.png) [@Yianni](https://community.homey.app/u/Yianni)\
**Post date:** [February 24, 2019, 7:23pm UTC](https://community.homey.app/t/promises-made-a-bit-easier/8965/2 "2019-02-24T19:23:34Z")

</div>

Superb! Thanks for taking the time to write this.

---

<div class="post-metadata">

**Author:** ![Ankit\_Lathiya](https://sea1.discourse-cdn.com/flex025/user_avatar/community.homey.app/ankit_lathiya/32/17296_2.png) [@Ankit\_Lathiya](https://community.homey.app/u/Ankit_Lathiya)\
**Post date:** [August 28, 2020, 6:34am UTC](https://community.homey.app/t/promises-made-a-bit-easier/8965/3 "2020-08-28T06:34:43Z")

</div>

Thanks for this great explanation about Promise.

But in 2020, every developer should use [async/await](https://appdividend.com/2018/01/16/javascript-es7-async-await-tutorial-example/) instead of plain promises in my opinion.

1. `async` functions return a promise.
2. `async` functions use an implicit `Promise` to return results. Even if you don’t return a promise explicitly, the `async` function makes sure that your code is passed through a promise.
3. `await` is always for a single `Promise` .
4. `Promise` creation starts the execution of asynchronous functionality.
5. `await` only blocks the code execution within the `async` function. It only makes sure that the next line is executed when the `promise` resolves. So, if an asynchronous activity has already started, `await` will not have any effect on it.

I hope this helps.
