question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

How to test an ES7 async function

See original GitHub issue

Hey guys, I use ES7 async functions and tried to debug them. Having this method to test:

// ...
const local = new WeakMap();

export default class User {

  // ...

  async password(password) {
    if (!password) return local.get(this).get('hash'); // remove this for security reasons!
    if (password.length < 6) throw new Error('New password must be at least 6 characters long');
    if (!password.match(passwordPattern)) throw new Error(`New password must match ${passwordPattern}`);
    local.get(this).set('hash', await Password.hash(password));
  }

  // ...

}

and this test case:

import chai from 'chai';
import chaiAsPromised from 'chai-as-promised';

import User from '../../../server/User';

chai.use(chaiAsPromised);
const expect = chai.expect;

describe('.password()', () => {

  const testuser = new User({username: 'Testuser', password: '123abc'});

  // FINDME
  it(`should throw when too short`, () => {
    return expect(testuser.password('1a')).to.eventually.throw();
  });

  // ...

});

…the test case does not catch the error thrown - instead the case succeeds first and fails later (asynchronously) with an uncaught error because the method threw in the scope of the it() function not the expect().

Any suggestions or advice?

Thanks in advance!

P.S.: Also I created a stackoverflow issue for this a few days ago, but now answer so far. That’s why I am calling you guys. http://stackoverflow.com/questions/29334775/how-to-test-an-es7-async-function-using-mocha-chai-chai-as-promised

Issue Analytics

  • State:closed
  • Created 8 years ago
  • Reactions:9
  • Comments:48 (14 by maintainers)

github_iconTop GitHub Comments

83reactions
krnldecommented, Apr 4, 2015

I got the solution! Expecting async function to actually “throw” is wrong, since it returns a promise. You’ll have to expect().to.be.rejected instead.

Here’s the modified test case:

it.only(`should be rejected when too short`, () => {
  return expect(testuser.password('1a')).to.be.rejectedWith(Error);
});

// should-style
it.only(`should be rejected when too short`, () => {
  return testuser.password('1a').should.be.rejectedWith(Error);
});

The question is, does an .eventually.throw() make sense? Is it different to .rejectedWith(Error)?

36reactions
ghostcommented, Apr 23, 2017

I like @lucasfcosta’s idea of adding support for async functions in throws to core rather than delegating out to chai-as-promised.

Given the following function:

function throwsAsync() {
  return new Promise((resolve, reject) => {
    reject(new Error())
  })
}

I personally find the following syntax:

expect(async () => await throwsAsync()).to.throw()

much more expressive of intent in an async/await world than the chai-as-promised method:

expect(throwsAsync()).to.be.rejected
Read more comments on GitHub >

github_iconTop Results From Across the Web

Testing Asynchronous Code with MochaJS and ES7 async ...
Place the async word in front of the async function(done){... . This tells the system that inside of this function there may (or...
Read more >
async function - JavaScript - MDN Web Docs - Mozilla
The async function declaration declares an async function where the await keyword is permitted within the function body. The async and await ...
Read more >
Javascript ES7 Async Await Tutorial | by Habib Ridho
The async function itself is actually a Promise, so you should do something like this when using it. You could try this tutorial...
Read more >
ES7 async functions
With async functions (full proposal), you can await on a promise. This halts the function in a non-blocking way, waits for the promise...
Read more >
Testing Asynchronous Code
Be sure to return (or await ) the promise - if you omit the return / await statement, your test will complete before...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found