Mocking react custom hook

I need to mock useLogin hook, bacause it contains logic that throws an error. Later i will test it in isolationю. UseLogin returns loading flag and login function that connecting new user to firebase.

import useLogin from "../../../hooks/useLogin";

export default function Login({ register, handleSubmit }) {
  const [loading, login] = useLogin();

  return (
    <Form onSubmit={handleSubmit(login)}>
    {...other components}
    <Form>
  );
}

useLogin hook

import { useState } from "react";
import { useHistory } from "react-router";
import { useModalContext } from "../../context";

import { firebase } from "../../libs/firebase";

export default function useLogin() {
  const [loading, setLoading] = useState(false);
  const [, { showErrorModal }] = useModalContext();
  const history = useHistory();

  function login({ email, password }) {
    setLoading(true);
    firebase
      .auth()
      .signInWithEmailAndPassword(email, password)
      .then(() => {
        setLoading(false);
        history.push("/");
      })
      .catch(() => {
        setLoading(false);
        showErrorModal("User not found");
      });
  }

  return [loading, login];
}

Answer

You should avoid mocking your own components when possible, as you will need to maintain both component and mock if you change the component code. You can still test this and test the useLogin hook isolated, to test all diferent code branches and so on.

The recommendation when going to the outside world and make API requests, is to use a library that allows you to mock them without being intrusive. Libraries like nock or Mock Service Worker let you do exactly that, and this way you avoid mocking fetch.

That said, in case you need to mock this, you can mock the firebase library to return whatever is needed. You can do it with a regular Jest mock, or try this firebase-mock library in case you will need to mock more of firebase features and here you can see how it integrates with Jest.

Creating your own custom mock might be the quicker option, and if you don’t need to mock anything else, it might be the best option as well. Here you can see an example of a custom firebase mock: Mock implementation of firebase auth methods after mocking the firebase module