简体   繁体   中英

Testing back button using react router and react testing library

I have a component which allows users to navigate back in history using react router v6's useNavigate hook. However, the test seems to fail when I call the function with navigate(-1) but passes if I pass a string url eg. navigate("/home") . Does anyone know the right way to test navigate(-1) ? Here's a codesandbox to illustrate the issue https://codesandbox.io/s/navigate-back-test-yt82g3?file=/src/navigateBack.test.tsx

import { renderWithRouter } from "./testUtils";
import { screen } from "@testing-library/react";

it("goes back", () => {
  function Home() {
    let navigate = useNavigate();

    function handleClick() {
      navigate("/about");
    }

    return (
      <div>
        <h1>Home</h1>
        <button onClick={handleClick}>about me</button>
      </div>
    );
  }

  function About() {
    let navigate = useNavigate();

    function handleClick() {
      navigate(-1); // test failed
      // navigate("/home"); // test passed
    }

    return (
      <div>
        <h1>About</h1>
        <button onClick={handleClick}>go back</button>
      </div>
    );
  }

  const { user } = renderWithRouter(
    <Routes>
      <Route path="home" element={<Home />} />
      <Route path="about" element={<About />} />
    </Routes>,
    {
      route: "/home"
    }
  );

  user.click(screen.getByText(/about me/i));

  user.click(screen.getByText(/go back/i));

  expect(window.location.pathname).toBe("/home");
});

If you just want to test the back navigation then I suggest using a MemoryRouter and supplying the initial routes. You only need one to go back from. I think there's a minor issue with the renderWithRouter renderer, so just wrap the components directly with the MemoryRouter .

Example:

import { render } from "@testing-library/react";
import user from "@testing-library/user-event";
import {
  MemoryRouter as Router,
  Route,
  Routes,
  useNavigate
} from "react-router-dom";
import { screen } from "@testing-library/react";

function Home() {
  const navigate = useNavigate();

  function handleClick() {
    navigate("/about");
  }

  return (
    <div>
      <h1>Home</h1>
      <button onClick={handleClick}>about me</button>
    </div>
  );
}

function About() {
  const navigate = useNavigate();

  function handleClick() {
    navigate(-1);
  }

  return (
    <div>
      <h1>About</h1>
      <button onClick={handleClick}>go back</button>
    </div>
  );
}

it("goes back", () => {
  render(
    <Router initialEntries={["/about"]}>
      <Routes>
        <Route path="home" element={<Home />} />
        <Route path="about" element={<About />} />
      </Routes>
    </Router>
  );

  user.click(screen.getByText(/go back/i));

  expect(window.location.pathname).toBe("/");
});

编辑 testing-back-button-using-react-router-and-react-testing-library

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM