Learn

In the previous exercise you learned how to redirect declaratively by rendering a Redirect component that updates the browser’s current location. Though this approach follows React Router’s declarative coding style, it does introduce a few extra steps in the React rendering lifecycle:

  1. The Redirect component must be returned
  2. The Redirect is then rendered
  3. The URL is then updated
  4. And finally the appropriate route is rendered.

React Router also provides a mechanism for updating the browser’s location imperatively: the Router‘s history object which is accessible via the useHistory() hook.

import { useHistory } from 'react-router-dom';

The history object that useHistory() returns has a number of methods for imperatively redirecting users. The first and most straightforward is history.push(location) which redirects the user to the provided location.

Consider this example which immediately triggers a redirect back to the / page after a user successfully submits a <form>:

import { useHistory } from `react-router-dom` export const ExampleForm = () => { const history = useHistory() const handleSubmit = e => { e.preventDefault(); history.push('/') } return ( <form onSubmit={handleSubmit}> {/* form elements */ } </form> ) }

By enabling imperative updates to the browser location, the history object allows you to respond immediately to user input without having to wait.

You might be wondering how the history object works. Internally, the BrowserRouter‘s history object uses the html5 history API. In brief, browser history is a stack that stores the URLs visited by the user and maintains a pointer to the user’s current location. This history API allows you to navigate through a user’s session history and alter the history stack if necessary.

In addition to history.push(), the history object has a few more useful methods for navigating through the browser’s history:

  • history.goBack() which navigates to the previous URL in the history stack
  • history.goForward() which navigates to the next URL in the history stack
  • history.go(n) which navigates n entries (where positive n values are forward and negative n values are backward) through the history stack

Below, we can see how the .goBack() method is used to create a “Go Back” button:

import { useHistory } from `react-router-dom` export const BackButton = () => { const history = useHistory() return ( <button onClick={() => history.goBack()}> Go Back </button> ) }

Instructions

Task 1

So far, you may have noticed the “Back” and “Forward” buttons in the Footer component. However, if you try clicking on them, nothing will happen. Let’s fix that using the history object and its methods!

First, navigate to Footer.js and import the useHistory hook.

Hint

Use the named import syntax to import the useHistory method from 'react-router-dom':

import { value } from 'package-name';

Task 2

Next, inside the Footer component, call useHistory() to get the history object.

Hint

Your code should look like this:

const history = useHistory();

Task 3

Finally, modify the goBack and goForward click handlers such that they imperatively redirect the user.

Verify your work by navigating to a few URLs and then using the “Back” and “Forward” buttons in the footer.

Hint

Call the history object’s .goBack() method inside the goBack handler. Call the history object’s .goForward() method inside the goForward handler.


Task 4

Lastly, let’s add an imperative redirect to the SignUp component such that after a user submits their username they are redirected to the /profile page.

Navigate to SignUp.js and import the useHistory hook.

Then, use the appropriate history method to redirect the user to '/profile' at the end of the handleSubmit method.

Test that your code works by signing up and ensuring that you are redirected to the profile page (which you can now view since loggedIn is now true).

Hint

Import the useHistory hook from react-router-dom, call it to get a history object, and use the history object’s push function to redirect the user to '/profile'.

Take this course for free

By signing up for Codecademy, you agree to Codecademy's Terms of Service & Privacy Policy.
Already have an account?