Search code examples
react-testing-libraryuser-event

Why would fireEvent work but userEvent not work?


In short, I have a table row with an onclick event. I am getting this via

const row = screen.getByRole('row', { name: /My row/i })
await userEvent.click(row)

This does not trigger the event handler. However, if I do:

const row = screen.getByRole('row', { name: /My row/i })
fireEvent.click(row)

This works fine.

I know userEvent uses more events to simulate a row click, but the event handler works fine in the live application too. Are there any reasons why userEvent might not work?


Solution

  • Like most very strange things, the problem lied elsewhere. But for documentation purposes, this was due to the app rerendering while doing my assertions. What would happen was this:

    • App renders, making a bunch of API calls
    • My API call for my test finishes, say, get user
    • findByText('My User') passes and gets me my DOM element
    • Another API call finishes, re-rendering the component to show this data
    • The result of findByText is no longer the current active DOM element
    • click fires
    • As its no longer in the document, there's nothing to click/fire an event

    I changed my previous lines to check for ALL data loads before grabbing my row and it seems to consistently be working. This means I have to assert things unrelated to my tests, but that may be due to my app having poor UX with things popping in as they load?

    Either way, I'm not 100% confident this is the reason, but if

    • userEvent.click is not firing events, or
    • toBeInTheDocument is failing, even if findBy worked

    It may be due to your app rerendering after you've asserted everything has loaded. Hope I can save someone else 3 days of suffering like I had to to find that simple fact...