Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Jest test React Router Prompt

I have a component which contains a React Router <prompt> in it and now I want to jest test if this is shown when the user navigates away from the component and the needed preconditions are satisfied. How can I simulate this navigate away and see if the 'Prompt' being triggered in Jest?

like image 395
Milindu Sanoj Kumarage Avatar asked Mar 09 '26 16:03

Milindu Sanoj Kumarage


1 Answers

Maybe someone would need a solution for this case:

import React from "react";
import { render } from "@testing-library/react";
import { Prompt, Route, Router, Switch, useHistory } from "react-router-dom";
import { PromptProps } from "react-router";
import { createMemoryHistory } from "history";

const promptResult = jest.fn(); // jest function which holds "when" value of prompt

jest.mock("react-router-dom", () => {
  const PromptMock: React.FC<PromptProps> = (props: PromptProps) => {
    const history = useHistory();
    if (props.when) {
      history.block(); //simulation of prompt behavior
    }
    promptResult.mockReturnValue(props.when);
    return <div />;
  };

  const originalModule = jest.requireActual("react-router-dom");
  return {
    __esModule: true,
    ...originalModule,
    Prompt: PromptMock,
  };
});

test("Shows prompt on navigation away", () => {
  const history = createMemoryHistory({ initialEntries: ["/path1"] });

  render(
    <Router history={history}>
      <Switch>
        <Route path="/path1">
          <div>
            <Prompt when={true} message={"You have unsaved changes."} />
            <div>Should prevent user from navigation</div>
          </div>
        </Route>
        <Route path="/path2">
          <div>Some other page</div>
        </Route>
      </Switch>
    </Router>
  );

  history.push("path2");

  expect(promptResult()).toBeTruthy();
});

test("Doesn't show prompt on navigation away", () => {
  const history = createMemoryHistory({ initialEntries: ["/path2"] });

  render(
    <Router history={history}>
      <Switch>
        <Route path="/path1">
          <div>
            <Prompt when={true} message={"You have unsaved changes."} />
            <div>Should prevent user from navigation</div>
          </div>
        </Route>
        <Route path="/path2">
          <div>Some other page</div>
        </Route>
      </Switch>
    </Router>
  );

  history.push("path2");

  expect(promptResult()).toBeFalsy();
});
like image 112
Alex Avatar answered Mar 12 '26 12:03

Alex