We saw in part 1 of this post on how to test a route component in react using the object containing key as pathname of route and value as the component name. We will look into another way of testing the same component using the memory router. We will be using MemoryRouter from react-router and passing the initialEntries
to it.
Let see the component we are going to test. This is the same component we saw in part 1 of the post.
import React, { Component } from 'react';
import { BrowserRouter as Router, Route, Link } from 'react-router-dom'
class Home extends Component{
render(){
return(
<div>Home Page</div>
)
}
}
class News extends Component{
render(){
return(
return <div>News Feed {this.props.location.pathname}</div>
)
}
}
class NoMatch extends Component{
render(){
return(
<div>404 page</div>
)
}
}
class Routes extends Component{
render(){
return(
<div>
<Router>
<div>
<Route exact path="/" component={Home} />
<Route exact path="/news" component={News} />
<Route exact path="/news/techdomain" component={News} />
<Route component={NoMatch} />
<Link to="/">Home page</Link><br/>
<Link to="/news">News page</Link><br/>
<Link to="/news/techdomain">News page for techdomain</Link>
</div>
</Router>
</div>
)
}
}
export default Routes;
In the above component, we have four components
Out of these four components, the routes component is the main component which contains the routes logic. The Routes
component is loaded at the start of the application.
In the main app, we have links to different apps.
<Link to="/">Home page</Link><br/>
<Link to="/news">News page</Link><br/>
<Link to="/news/techdomain">News page for techdomain</Link>
Testing the Routes
component with memory router is really simple. We just have to wrap the Routes
component with the MemoryRouter and pass some initial entries as the path we want to test. So if we want to test if the News
component is loaded for the /news
route, pass the prop value as ['/news']
to the MemoryRouter component.
Here is the test file
routes.test.js
import React from 'react';
import { shallow, mount } from 'enzyme';
import Routes, { Home, News, NoMatch } from './Routes';
import { MemoryRouter } from 'react-router';
import { Route } from 'react-router-dom';
describe('routes using memory router', () => {
it('should show Home component for / router (using memory router)', () => {
const component = mount(<MemoryRouter initialentries="{['/']}">
<Routes/>
</Memoryrouter>
);
expect(component.find(Home)).toHaveLength(1);
})
it('should show No match component for route not defined', () => {
const component = mount(<Memoryrouter initialEntries="{['/unknown']}">
<Routes/>
</MemoryRouter>
);
expect(component.find(NoMatch)).toHaveLength(1);
})
})
In order to test whether the home component is shown at the route "/", we pass the initial entry as ['/']
as the prop initialentries
to MemoryRouter
it('should show Home component for / router (using memory router)', () => {
const component = mount(<MemoryRouter initialentries="{['/']}">
<Routes/>
</Memoryrouter>
);
expect(component.find(Home)).toHaveLength(1);
})
Then we assert it by checking that the component Home
is present
it('should show Home component for / router (using memory router)', () => {
const component = mount(<MemoryRouter initialentries="{['/']}">
<Routes/>
</Memoryrouter>
);
expect(component.find(Home)).toHaveLength(1);
})
One advantage is that we can test the 404 route easily by passing a pathname in initial entry array which is not handled by any component, and assert that the NoMatch
is present.
const component = mount( <MemoryRouter initialEntries="{['/unknown']}">
<Routes />
</MemoryRouter>
);
expect(component.find(NoMatch)).toHaveLength(1);
So we saw both the ways to test the routes in react using jest - mapping the routes and creating the object, or using the memory router.