Description
@testing-library/react
version: 11.2.3- Testing Framework and version: jest 26.6.3
- DOM Environment: jsdom 16.4.0
Relevant code or config:
This is directly copypasta'd from:
https://testing-library.com/docs/example-react-router/
// app.test.js
import {render, screen} from '@testing-library/react'
import userEvent from '@testing-library/user-event'
import {createMemoryHistory} from 'history'
import React from 'react'
import {Router} from 'react-router-dom'
import '@testing-library/jest-dom/extend-expect'
import {Link, Route, Switch, useLocation} from 'react-router-dom'
const About = () => <div>You are on the about page</div>
const Home = () => <div>You are home</div>
const NoMatch = () => <div>No match</div>
export const LocationDisplay = () => {
const location = useLocation()
return <div data-testid="location-display">{location.pathname}</div>
}
export const App = () => (
<div>
<Link to="/">Home</Link>
<Link to="/about">About</Link>
<Switch>
<Route exact path="/">
<Home />
</Route>
<Route path="/about">
<About />
</Route>
<Route>
<NoMatch />
</Route>
</Switch>
<LocationDisplay />
</div>
)
test('full app rendering/navigating', () => {
const history = createMemoryHistory()
render(
<Router history={history}>
<App />
</Router>,
)
// verify page content for expected route
// often you'd use a data-testid or role query, but this is also possible
expect(screen.getByText(/you are home/i)).toBeInTheDocument()
const leftClick = {button: 0}
userEvent.click(screen.getByText(/about/i), leftClick)
// check that the content changed to the new page
expect(screen.getByText(/you are on the about page/i)).toBeInTheDocument()
})
test('landing on a bad page', () => {
const history = createMemoryHistory()
history.push('/some/bad/route')
render(
<Router history={history}>
<App />
</Router>,
)
expect(screen.getByText(/no match/i)).toBeInTheDocument()
})
test('rendering a component that uses useLocation', () => {
const history = createMemoryHistory()
const route = '/some-route'
history.push(route)
render(
<Router history={history}>
<LocationDisplay />
</Router>,
)
expect(screen.getByTestId('location-display')).toHaveTextContent(route)
})
What you did:
Using React Testing Library to test react-router rendering after route change. Per docs, I provide a Router
context with my own history object from createMemoryHistory
.
After changing the route by clicking a link with userEvent
I expect the corresponding Route to be rendered.
What happened:
The route change is reflected by the original page
subscribing components (eg. location retrieved by useLocation
). However code inside the newly-matching route is not rendered. In this use case, the "You are on the about page" text never appears.
Unable to find an element with the text: /you are on the about page/i. This could be because the text is broken up by multiple elements. In this case, you can provide a function for your text matcher to make your matcher more flexible.
<body>
<div>
<div>
<a
href="/"
>
Home
</a>
<a
href="/https/github.com/about"
>
About
</a>
<div>
No match
</div>
<div
data-testid="location-display"
/>
</div>
</div>
</body>
Reproduction:
https://codesandbox.io/s/musing-http-rohnt?file=/src/docs.test.js
Problem description:
Cannot test full-app routing using testing library. Examples on the documentation site appear to be broken.
Suggested solution:
None at this point, but willing to work on a fix if someone can isolate the issue.