React-testing-library: Document/implement matchers with `getAll`

Created on 16 Dec 2019  路  7Comments  路  Source: testing-library/react-testing-library

Describe the feature you'd like:

Examples using the getAll queries.

As all the matchers work on a singular element, not arrays, i don't really know how to use the getAll queries, and in my current case i'd really love to use something like:

       expect(getAllByRole("figure")).some(tag =>
                expect(tag).toHaveTextContent(data.current_balance)
            )

But i'm not sure how, or even if it's possible, to do this.

Most helpful comment

The most common use case for "all" from what I've seen is counting or iterating over a list:

const menu = getByRole('menu')
const menuOptions = within(menu).getAllByTestId(/menu-options-/)
expect(menuOptions).toHaveLength(3)
expect(menuOptions[0]).toHaveTextContent(/share/)
expect(menuOptions[1]).toHaveTextContent(/delete/)
expect(menuOptions[2]).toHaveTextContent(/archive/)

You can also iterate over an expect block using normal JS patterns:

// add the assertion count if it is possible for iteration to skip a desired assertion
expect.assertions(3)
const figures = getAllByRole("figure")
for (const figure of figures) {
  expect(figure).toHaveTextContent(data.current_balance)
}

All 7 comments

Could you present an actual use case and we can help you know how to use the *All* queries effectively for that use case.

Granted, I don't personally use *All* queries very often.

The most common use case for "all" from what I've seen is counting or iterating over a list:

const menu = getByRole('menu')
const menuOptions = within(menu).getAllByTestId(/menu-options-/)
expect(menuOptions).toHaveLength(3)
expect(menuOptions[0]).toHaveTextContent(/share/)
expect(menuOptions[1]).toHaveTextContent(/delete/)
expect(menuOptions[2]).toHaveTextContent(/archive/)

You can also iterate over an expect block using normal JS patterns:

// add the assertion count if it is possible for iteration to skip a desired assertion
expect.assertions(3)
const figures = getAllByRole("figure")
for (const figure of figures) {
  expect(figure).toHaveTextContent(data.current_balance)
}

Related: testing-library/jest-dom#174 (also reported by @C0DK).

Iterating over the array should satisfy the use case for "all elements match an expectation". You can do the same with a try/catch for the some/any use case, but I could imagine adding asymmetric matchers so you could pass in an array of them to .arrayContaining or .toContain:

expect(getAllByRole("figure"))
  .toContain(expect.elementWithClass("xyz"))

expect(getAllByLabelText("close"))
  .toEqual(expect.arrayContaining([
    expect.elementWithRole("button"),
    expect.elementWithClass("active"),
  ])

Not sure how to implement it, I am guessing the functions return an object with a custom .toEqual method

Related: testing-library/jest-dom#174 (also reported by @C0DK).

Yep I didn't know whether it was a problem with you or them.. or both.. In their case, i found a lacking documentation, whereas with you i missed some matchers.. i guess.

Mainly i would expect it to have some functional matchers for the quite generic forAll and forAny logical questions.

I could naturally do it with a for-loop

// add the assertion count if it is possible for iteration to skip a desired assertion
expect.assertions(3)
const figures = getAllByRole("figure")
for (const figure of figures) {
  expect(figure).toHaveTextContent(data.current_balance)
}

as mentioned here. I did not think of that. I think i expected a functional interface, but this is naturally as strong, computationally.

Right now i have a dashboard, and i want to validate that atleast one of the figures contains information about each data-point.

You can solve it by using the following code snippet:

expect(getAllByRole("figure")).toEqual(
  expect.arrayContaining(
    getByText(data.current_balance)
  )
);

Hi friends,

I don't think we're going to do this. The workarounds are reasonable enough so we can't justify adding more API for this use case.

Good luck!

Was this page helpful?
0 / 5 - 0 ratings