react-toastify icon indicating copy to clipboard operation
react-toastify copied to clipboard

autoClose not working when testing using @testing-library/react

Open shehan-mark opened this issue 1 year ago • 5 comments

Do you want to request a feature or report a bug?

  • Bug

What is the current behavior? I am testing toast que functionality in my project. I have a requirement where I want to display only one toast at a time. For that I have limited the toast count from the ToastContainer. but in order to test this I want first test each toast's open and close feature so that I can check on the next consecutive toast's that is in the que.
But I am unable move further after the first toast. Meaning first toast won't disappear after the timeout. For better understanding I have provided a CodeSandbox below. also I noticed that animation-play-state: is always set to paused when I log the DOM structure using screen.debug() image

CodeSandbox

What is the expected behavior? Toast to disappear after the specified timeout in Unit testing.

Which versions of React, and which browser / OS are affected by this issue? Did this work in previous versions of React? These are the exact local versions that I use. They may differ from the versions used in the sandbox. But the issue was reproducable.

react - 17.0.2 react-toastify - 9.1.3 jest-environment-jsdom - 29.6.1

It seemed like a bug in the library but please let me know if this is on my side.

shehan-mark avatar Oct 10 '23 18:10 shehan-mark

Pinging here to keep this active.

shehan-mark avatar Oct 16 '23 06:10 shehan-mark

Have you tried adding this at the beginning of your tests

jest.useFakeTimers();

beforeEach(() => {
  jest.spyOn(window, 'requestAnimationFrame').mockImplementation((callback) => {
    callback(1);
    return 1;
  });
});

afterEach(() => {
  (window.requestAnimationFrame as jest.Mock).mockRestore();
});

and

fireEvent.animationEnd(...)
jest.runAllTimers();

before your expect(within(toastOneSeconQ).getByText("ToastMessage - 1")).not.toBeVisible(); ?

davidgonzalezfx avatar Nov 21 '23 20:11 davidgonzalezfx

Have you tried adding this at the beginning of your tests

jest.useFakeTimers();

beforeEach(() => {
  jest.spyOn(window, 'requestAnimationFrame').mockImplementation((callback) => {
    callback(1);
    return 1;
  });
});

afterEach(() => {
  (window.requestAnimationFrame as jest.Mock).mockRestore();
});

and

fireEvent.animationEnd(...)
jest.runAllTimers();

before your expect(within(toastOneSeconQ).getByText("ToastMessage - 1")).not.toBeVisible(); ?

Hi, I wanted to verify that the toast would be removed (auto-closed) after 5000ms, but it never disappeared. I followed the steps you described, yet the toast still remains in the DOM within my jest unit-tests using react-testing-library. Any new update on this issue? It's simple to test that it appears, but not disappear.😊

framitdavid avatar Jun 24 '24 10:06 framitdavid

Encountering the same issue. A solution would be appreciated.

gillesbouvier-qz avatar Jul 15 '24 17:07 gillesbouvier-qz

This is what works for me:

      await screen.findByText('text displayed on toast');

      const progressBar = screen.getByLabelText('notification timer');
      fireEvent.animationEnd(progressBar);

      const toastContainer =
        container.getElementsByClassName('Toastify__toast')[0];
      fireEvent.animationEnd(toastContainer);

      expect(
        screen.queryByText('text displayed on toast')
      ).not.toBeInTheDocument();

gillesbouvier-qz avatar Jul 15 '24 21:07 gillesbouvier-qz