Error message from React native testing library: "Warning: You called act(async () => ...) without await." but i didn't

696 views Asked by At
 PASS  app/components/lists/VideoCardList.test.tsx
  ● Console

    console.error
      Warning: You called act(async () => ...) without await. This could lead to unexpected testing behaviour, interleaving multiple act calls and mixing their scopes. You should - await act(async () => ...);

      at printWarning (node_modules/react-test-renderer/cjs/react-test-renderer.development.js:68:30)
      at error (node_modules/react-test-renderer/cjs/react-test-renderer.development.js:44:5)
      at node_modules/react-test-renderer/cjs/react-test-renderer.development.js:15297:13
      at tryCallOne (node_modules/react-native/node_modules/promise/lib/core.js:37:12)
      at node_modules/react-native/node_modules/promise/lib/core.js:123:15
      at flush (node_modules/asap/raw.js:50:29)

This is the entire error code. And the below is my test code that caused the error.

it("displays more data when the scroll reached end", async () => {
  let cardList = component.getByTestId("videoCardList");

  // fire onLayout event to generate initial dataset
  fireEvent(cardList, "layout", {
    nativeEvent: { layout: { width: 300 } },
  });

  cardList = await component.findByTestId("videoCardList");

  fireEvent(cardList, "endReached");

  const cardListItems = await component.findByTestId(
    "videoCardItem" + initialListLength // assigned in previous TC, if things went well, it's 5 (it's just number value)
  );

  expect(cardListItems).toBeTruthy();
});

Fortunately, my code passes the TC, but unfortunately, the message really bothers me.

Anyway, I didn't call the method: act(). I've googled, and learned the fact that some methods from library like fireEvent() actually wrapping act(), and it seems that my poor code caused a sort of side effect. But I've failed to find out the way to resolve the error.

1

There are 1 answers

3
man517 On

You call the following line of code outside of an async function:

cardList = await component.findByTestId("videoCardList");

You do it again here:

const cardListItems = await component.findByTestId(
      "videoCardItem" + initialListLength // assigned in previous TC, if things went well, it's 5 (it's just number value)
    );

You can resolve this by either wrapping these items in async functions and then calling the new async function:

const functionName = async () => {
  await asyncFunctionCall();
}

OR

You can use .then/.catch syntax instead of async/await:

asyncFunctionCall.catch(e => console.log(e));