Simulate react-select events for react-testing-library
npm install react-select-event
Simulate user events on react-select elements, for use with react-testing-library.




``bash`
npm install --save-dev react-select-event
Import react-select-event in your unit tests:
`js`
import selectEvent from "react-select-event";
// or
const selectEvent = require("react-select-event");
This library is tested against all versions of react-select starting from 2.1.0.
Every helper exported by react-select-event takes a handle on the react-select input field as its first argument. For instance, this can be: getByLabelText("Your label name").
The optionOrOptions parameter can be any valid dom-testing-library TextMatch object (eg. string, regex, function, number).
Select one or more values in a react-select dropdown.
`jsx
const { getByRole, getByLabelText } = render(
);
expect(getByRole("form")).toHaveFormValues({ food: "" });
await selectEvent.select(getByLabelText("Food"), ["Strawberry", "Mango"]);
expect(getByRole("form")).toHaveFormValues({ food: ["strawberry", "mango"] });
await selectEvent.select(getByLabelText("Food"), "Chocolate");
expect(getByRole("form")).toHaveFormValues({
food: ["strawberry", "mango", "chocolate"],
});
`
This also works for async selects:
`jsx
const { getByRole, getByLabelText } = render(
);
expect(getByRole("form")).toHaveFormValues({ food: "" });
// start typing to trigger the loadOptions`
fireEvent.change(getByLabelText("Food"), { target: { value: "Choc" } });
await selectEvent.select(getByLabelText("Food"), "Chocolate");
expect(getByRole("form")).toHaveFormValues({
food: ["chocolate"],
});
select also accepts an optional config parameter.config.container can be used to specify a custom container to use when the react-select dropdown is renderedmenuPortalTarget
in a portal using :
`jsx`
const { getByRole, getByLabelText } = render(
);
await selectEvent.select(getByLabelText("Food"), ["Strawberry", "Mango"], {
container: document.body,
});
expect(getByRole("form")).toHaveFormValues({ food: ["strawberry", "mango"] });
The container can also be passed in as a function if it needs to be lazily evaluated:
`jsx`
const { getByRole, getByLabelText } = render(
);
await selectEvent.select(getByLabelText("Food"), ["Strawberry", "Mango"], {
container: () => document.body.querySelector("[class$=-menu]"),
});
expect(getByRole("form")).toHaveFormValues({ food: ["strawberry", "mango"] });
Creates and selects a new item. Only applicable to react-select Creatable elements.
`jsx`
const { getByRole, getByLabelText } = render(
);
expect(getByRole("form")).toHaveFormValues({ food: "" });
await selectEvent.create(getByLabelText("Food"), "papaya");
expect(getByRole("form")).toHaveFormValues({ food: "papaya" });
create take an optional config parameter:
- config.createOptionText can be used when creating elements with a custom label text, using the formatCreateLabel prop.config.container
- can be used when the react-select dropdown is rendered in a portal using menuPortalTarget.config.waitForElement
- Whether create should wait for new option to be populated in the select container. Defaults to true.
Clears the first value in the dropdown.
`jsx`
const { getByRole, getByLabelText } = render(
);
expect(getByRole("form")).toHaveFormValues({ food: "chocolate" });
await selectEvent.clearFirst(getByLabelText("Food"));
expect(getByRole("form")).toHaveFormValues({ food: "" });
Clears all values in the dropdown.
`jsx`
const { getByRole, getByLabelText } = render(
);
expect(getByRole("form")).toHaveFormValues({
food: ["chocolate", "vanilla", "strawberry"],
});
await selectEvent.clearAll(getByLabelText("Food"));
expect(getByRole("form")).toHaveFormValues({ food: "" });
Opens the select dropdown menu by focusing the input and simulating a down arrow keypress.
`jsx``
const { getByLabelText, queryByText } = render(
);
expect(queryByText("Pizza")).toBeNull();
selectEvent.openMenu(getByLabelText("Food"));
expect(getByText("Pizza")).toBeInTheDocument();
All the credit goes to Daniel and his StackOverflow answer: https://stackoverflow.com/a/56085734.