Skip to content

Instantly share code, notes, and snippets.

@threepointone
Last active August 4, 2020 19:09
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save threepointone/8844925a868ca88c77057034b775f3c1 to your computer and use it in GitHub Desktop.
Save threepointone/8844925a868ca88c77057034b775f3c1 to your computer and use it in GitHub Desktop.
Ember's settled() test helper, for React

settled

Stealing an idea from ember's settled test helper.

Assuming these conditions are true in your unit tests -

  • you're using Jest
  • and Jest's fake timers
  • and all your data requests are happening via fetch

You can call await settled() before making any assertions to make sure that -

  • all of React's updates are applied
  • all requests made have been resolved
  • all timers have run their course

(This has not been tested at all, buyer beware)

import { act } from "react-dom/test-utils";

let _fetchImpl = global.fetch;

let fetches = new Set();

global.fetch = async (...args) => {
  const promise = _fetchImpl(...args);
  fetches.add(promise);
  return promise.then(x => {
    fetches.delete(promise);
    return x;
  });
};

async function settled() {
  while (fetches.size > 0 && jest.getTimerCount() > 0) {
    await act(async () => {
      jest.runAllTimers();
      await Promise.all(fetches);
    });
  }
}

Usage

it('renders the page', async () => {
  render(<App/>);
  await settled();
  expect(queryByRole('button')).toExist(); // or your favourite assertions
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment