ค้นหาเว็บไซต์

reactjs - วิธีทดสอบคอมโพเนนต์ที่กำลังใช้ Custom TypeScript React Hook?


ตอนนี้ฉันกำลังเขียนคอมโพเนนต์ React ใน Typescript ซึ่งใช้ hook ของ axios-hooks ที่เรียกว่า useAxios ตัวอย่างการใช้งาน hook นี้มีดังนี้:

 export const App = () => {
  const [{ data, loading, error }, refetch] = useAxios(
    "https://api.myjson.com/bins/820fc"
  );

  if (loading) return <p>Loading...</p>;
  if (error) return <p>Error!</p>;

  return (
    <div>
      <button onClick={e => refetch()}>refetch</button>
      <pre>{JSON.stringify(data, null, 2)}</pre>
    </div>
  );
};

const rootElement = document.getElementById("root");
render(<App />, rootElement);

ฉันพยายามหาวิธีเขียนการทดสอบที่ฉันสามารถทำการจำลอง hook useAxios ได้ ฉันได้ลองสร้าง mock ของคอมโพเนนต์ axios ที่อยู่เบื้องหลังแล้วแต่ก็ไม่สามารถทำให้มันใช้งานได้:

import React from "react"
import { render } from "@testing-library/react"
import { Test } from "../test"
import useAxios from "axios-hooks"

jest.mock("axios-hooks")
const mockedAxios = useAxios as jest.Mocked<typeof useAxios>

it("Displays loading", () => {
  // How to mock the return values in the following line?
  // mockedAxios.

  const { getByText } = render(<Test />)

  expect(getByText("Loading...")).toBeDefined()
})

ฉันรู้ว่าฉันไม่ควรจะต้องเลียนแบบ axios ซึ่งเป็น dependency พื้นฐาน ฉันควรจะสามารถเลียนแบบ useAxios ได้ แต่ฉันก็คิดว่าจะลองดูบ้าง

ฉันตระหนักว่าคำถามนี้ถูกพูดถึงหลายครั้งใน SO แต่ฉันไม่สามารถหาวิธีแก้ปัญหาสำหรับกรณีการใช้งานเฉพาะนี้ได้

ยินดีอย่างยิ่งสำหรับความช่วยเหลือใด ๆ!

คำตอบ #1

ฉันคิดออกเองว่าจะทำสิ่งนี้ได้อย่างไร เพื่อทดสอบ custom hook ฉันทำดังต่อไปนี้:

import * as useAxios from "axios-hooks"
jest.mock("axios-hooks")
const mockedAxios = useAxios as jest.Mocked<typeof useAxios>

it("Displays loading message", async () => {

  // Explicitly define what should be returned
  mockedAxios.default.mockImplementation(() => [
      {
        data: [],
        loading: true,
        error: undefined
      },
      () => undefined
    ])

  const { getByText } = render(<Test />)

  expect(getByText("Loading...")).toBeDefined()
})

คำตอบ #2

จำลองโมดูลและตั้งค่าผลลัพธ์ที่คาดว่าจะเกิดขึ้นของ useAxios ต่อการทดสอบ เช่น

jest.mock('axios-hooks');

import useAxios from 'axios-hooks';

test('App displays loading when request is fetching', () => {
  useAxios.mockReturnValue(Promise.resolve({ loading: true }));
  // mount component
  // Verify "Loading" message is rendered
});