snippetjavascriptreactCritical
How can I programmatically navigate using React Router?
Viewed 0 times
howusingreactnavigatecanprogrammaticallyrouter
Problem
With React Router, I can use the
I see internally it calls
I want to do navigation. Not from a link, but from a dropdown selection (as an example). How can I do this in code? What is
I saw the
Link element to create links which are natively handled by React Router.I see internally it calls
this.context.transitionTo(...).I want to do navigation. Not from a link, but from a dropdown selection (as an example). How can I do this in code? What is
this.context?I saw the
Navigation mixin, but can I do this without mixins?Solution
React Router v6.6.1 with useNavigate
The
React Router v5.1.0 with hooks
There is a new
React Router v4
With v4 of React Router, there are three approaches that you can take to programmatic routing within components.
React Router is mostly a wrapper around the history
// This also works with react-router-native
const Button = withRouter(({ history }) => (
{ history.push('/new-location') }}
>
Click Me!
))
const Button = () => (
(
{ history.push('/new-location') }}
>
Click Me!
)} />
)
{
// context.history.push === history.push
context.history.push('/new-location')
}}
>
Click Me!
)
// You need to specify the context type so that it
// is available within the component
Button.contextTypes = {
history: React.PropTypes.shape({
push: React.PropTypes.func.isRequired
})
}
`
1 and 2 are the simplest choices to implement, so for most use cases, they are your best bets.
The
useHistory() hook is now deprecated. If you are using React Router 6, the proper way to navigate programmatically is as follows:import { useNavigate } from "react-router-dom";
function HomeButton() {
const navigate = useNavigate();
function handleClick() {
navigate("/home");
}
return (
Go home
);
}
React Router v5.1.0 with hooks
There is a new
useHistory hook in React Router higher than 5.1.0, if you are using React higher than 16.8.0 and functional components.import { useHistory } from "react-router-dom";
function HomeButton() {
const history = useHistory();
function handleClick() {
history.push("/home");
}
return (
Go home
);
}React Router v4
With v4 of React Router, there are three approaches that you can take to programmatic routing within components.
- Use the
withRouterhigher-order component.
- Use composition and render a `
- Use the context
.
React Router is mostly a wrapper around the history
library. history handles interaction with the browser's window.history for you with its browser and hash histories. It also provides a memory history which is useful for environments that don't have a global history. This is particularly useful in mobile app development (react-native) and unit testing with Node.js.
A history instance has two methods for navigating: push and replace. If you think of the history as an array of visited locations, push will add a new location to the array and replace will replace the current location in the array with the new one. Typically you will want to use the push method when you are navigating.
In earlier versions of React Router, you had to create your own history instance, but in v4 the , , and components will create a browser, hash, and memory instances for you. React Router makes the properties and methods of the history instance associated with your router available through the context, under the router object.
- Use the
withRouter higher-order component
The withRouter higher-order component will inject the history object as a prop of the component. This allows you to access the push and replace methods without having to deal with the context.
import { withRouter } from 'react-router-dom'// This also works with react-router-native
const Button = withRouter(({ history }) => (
{ history.push('/new-location') }}
>
Click Me!
))
- Use composition and render a
The component isn't just for matching locations. You can render a pathless route and it will always match the current location. The component passes the same props as withRouter, so you will be able to access the history methods through the history prop.
import { Route } from 'react-router-dom'const Button = () => (
(
{ history.push('/new-location') }}
>
Click Me!
)} />
)
- Use the context*
But you probably should not
The last option is one that you should only use if you feel comfortable working with React's context model (React's Context API is stable as of v16).
const Button = (props, context) => ({
// context.history.push === history.push
context.history.push('/new-location')
}}
>
Click Me!
)
// You need to specify the context type so that it
// is available within the component
Button.contextTypes = {
history: React.PropTypes.shape({
push: React.PropTypes.func.isRequired
})
}
`
1 and 2 are the simplest choices to implement, so for most use cases, they are your best bets.
Code Snippets
import { useHistory } from "react-router-dom";
function HomeButton() {
const history = useHistory();
function handleClick() {
history.push("/home");
}
return (
<button type="button" onClick={handleClick}>
Go home
</button>
);
}Context
Stack Overflow Q#31079081, score: 2634
Revisions (0)
No revisions yet.