Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to test Material-UI Checkbox is checked with react-testing-library?

Seems like the way Material UI works is it renders a different SVG when the checkbox is clicked, and not changing the attributes or anything on the actual input element. So how do I actually test that the element is checked in line with the react-testing-library philosophy?

Here's a rough example of the

Checkbox component usage

export const CheckBoxContainer = () => (
  <Checkbox inputProps={{ 'data-testid': `clickable-checkbox-1234` }} data-testid={`checkbox-1234`} />
);

Test

test('check the box', async () => {
  const { getByTestId } = render(<CheckBoxContainer />);
  await waitForElement(() => getByTestId(`checkbox-1234`));
  const checkbox = getByTestId(`checkbox-1234`);
  fireEvent.click(getByTestId(`clickable-checkbox-1234`));
  expect(checkbox).toHaveAttribute('checked');
});

Generated HTML by Material UI

<span
  class="MuiButtonBase-root-54 MuiIconButton-root-48 MuiSwitchBase-root-231 MuiCheckbox-root-225 MuiCheckbox-colorSecondary-230 MuiSwitchBase-checked-232 MuiCheckbox-checked-226"
  data-testid="checkbox-1234"
>
  <span class="MuiIconButton-label-53">
    <svg
      class="MuiSvgIcon-root-57"
      focusable="false"
      viewBox="0 0 24 24"
      aria-hidden="true"
      role="presentation"
    >
      <path
        d="M19 3H5c-1.11 0-2 .9-2 2v14c0 1.1.89 2 2 2h14c1.11 0 2-.9 2-2V5c0-1.1-.89-2-2-2zm-9 14l-5-5 1.41-1.41L10 14.17l7.59-7.59L19 8l-9 9z"
      ></path>
    </svg>
    <input
      class="MuiSwitchBase-input-234"
      type="checkbox"
      data-indeterminate="false"
      data-testid="clickable-checkbox-1234"
      value=""
    />
  </span>
  <span class="MuiTouchRipple-root-66"> </span>
</span>

like image 394
Dale Race Avatar asked Nov 12 '18 23:11

Dale Race


People also ask

How do I use the material UI checkbox in react?

Using the Material UI Checkbox is essentially the same as native React inputs. You have a checked prop, a boolean set to either true or false, which determines whether the Checkbox is checked or not. You use the onChange prop and React hooks to set and maintain the state of the checkbox.

How to check or uncheck the checkbox using React-testing-library?

To check or uncheck the checkbox using react-testing-library, you simply want to fireEvent.click the checkbox. There was a discussion about this on react-testing-library Issue #175.

How to test MUI without the React component tree?

By not relying on the React component tree you make your test more robust against internal changes in MUI or, if you need snapshot testing, adding additional wrapper components such as context providers. We don't recommend snapshot testing though.

How to handle multiple checkboxes in a react event?

In the event handler, we can look at event.target.checked to know what the new state value should be set to. For handling multiple checkboxes, we can look at the target.name to identify which checkbox we touched and then store that as a key in our React state.


1 Answers

The easiest way I have found to locate a checkbox is by adding a label to it

<FormControlLabel
  htmlFor="first-checkBox"
  label="First Checkbox"
  control={ <Checkbox
        checked={checked}
        onChange={handleChange}
        inputProps={{ 'aria-label': 'primary checkbox' }}
      />
  }
/>

later in test case

const checkboxEl = screen.getByLabelText('First Checkbox') as HTMLInputElement
expect(checkboxEl).toBeChecked()

if the test fails because doesn't recognize toBeChecked as part of the available assertions is because you need to import

import '@testing-library/jest-dom/extend-expect'

like image 119
VRedondo Avatar answered Oct 20 '22 05:10

VRedondo