58

I was reading react-router-redux examples and I confused, what is the difference beetween:

import { Redirect } from 'react-router-dom'

...

<Redirect to='/login' /> 

and

import { push } from 'react-router-redux'

...

push('/login')
tandav
  • 775
  • 2
  • 9
  • 14
  • 1
    See https://reacttraining.com/react-router/web/api/Redirect : A simple redirect will add an entry to the history stack (you can go back to the previous route); if `push` with `false`, then the current url route is overritten, and you can't use the back button to return to the state you just left. – Piran Feb 05 '18 at 10:42
  • 2
    @Piran, not true. `Redirect` overrides the current history unless you specify the push prop (as per the link you supplied) – phillyslick May 08 '18 at 19:20

3 Answers3

74

Redirect

Rendering a <Redirect> will navigate to a new location. The new location will override the current location in the history stack, like server-side redirects (HTTP 3xx) do.

whereas History

push function Pushes a new entry onto the history stack

Revansiddh
  • 2,932
  • 3
  • 19
  • 33
  • 9
    Any benefits of overwriting the current history stack ? – DollarAkshay Mar 09 '21 at 00:33
  • 3
    @DollarAkshay, the user is not blocked when trying to navigate back. – Michał Pietraszko Dec 21 '21 at 10:13
  • A use case: A user tried to access their settings page, but is not logged in. By using `Redirect`, we can redirect them to the log in page and remove the "settings" from their history, so that their back button won't take them back there. Bonus: It's nice to remember where they were trying to go, so after they log in we can redirect them there; in this case, to their settings page. – Matt Kleinsmith Nov 01 '22 at 20:53
37

The <Redirect> component will, by default, replace the current location with a new location in the history stack, basically working as a server-side redirect.

But it can also be used with the property push and in this case it will push a new entry into the history stack, working the same way as history.push.

In fact the <Redirect> component uses the history push and replace methods behinds the scene. It is just a more React way of navigating.

So basically you have two ways of navigating:

  1. Use the history.push and history.replace in a component (usually wrapped with the withRouter HOC, so that you can have access to the location object without having to pass it from parent to child.

  2. Use the <Redirect> component with or without the push property, depending

Marcos Abreu
  • 2,832
  • 22
  • 18
3

I noticed a difference between the two in my use case with Redux and Typescript.

Here's a simplified version of it:

export const LandingPage = () => {
  const { history } = useHistory();
    const { viewer } = useSelector(state => state.viewer);

    // Redirect method returns another component that handles the redirect
    // without mounting any of the route components
    if (!viewer?.token) {
        return <Redirect to="/signin" />;
    }

    // History.push method mounts the route component and runs 'onload' functions
    // Which can still throw an error if there's no viewer 
    // if (!viewer?.token) {
    //  history.push('/signin');
    //    // return history.push('/signin');  // throws Typescript error
    // }

    return (
        <Switch>
            <Route path="/dashboard" component={Dashboard}/>
            <Route path="/profile" component={Profile}/>
            <Route path="/" component={Home}/>
        </Switch>
    );
};

When using history.push() method, the JSX in your return statement can still mount and run, whereas returning Redirect can block the rest of your code.

Bhavik Parmar
  • 424
  • 1
  • 6
  • 9
toomusa
  • 31
  • 1