我如何测试 React 中不断变化的状态?

How can I test changing states in React?

我是 React 的新手,正在尝试使用 jest & testing-library/react 测试我的代码。

我制作了一个简单的 select 框并触发了框上的更改事件。 我只想获取状态,但我仍然不知道如何获取它。

这是我的组件:

import React from "react";
import ReactDOM, { render } from "react-dom";
import NativeSelect from "@material-ui/core/NativeSelect";

const MyTest = () => {
  const [option, setOption] = React.useState("1");

  const handleChange = React.useCallback(e => {
    setOption(e.target.value);
  }, []);

  return (
    <div>
      <h3>selected : {option}</h3>
      <NativeSelect
        inputProps={{ "data-testid": "test-input" }}
        value={option}
        onChange={handleChange}
      >
        <option value="1">1</option>
        <option value="2">2</option>
        <option value="3">3</option>
      </NativeSelect>
    </div>
  );
};

export default MyTest;

这是测试:

import React from "react";
import { renderHook, act } from "@testing-library/react-hooks";
import { render, fireEvent } from "@testing-library/react";
import MyTest from "./MyTest";

test("should change state", () => {
  const { result } = renderHook(() => MyTest());

  let { getByTestId } = render(<MyTest />);
  const selectNode = getByTestId("test-input");
  expect(selectNode).not.toBeNull();

  act(() => {
    fireEvent.change(selectNode, { target: { value: "2" } });
  });

  expect(result.current.option).toBe("2");
});

codesandbox 在这里: https://codesandbox.io/s/distracted-wave-j5fed?fontsize=14

那么测试的错误信息是 : "Comparing two different types of values. Expected string but received undefined."

我想 "result.current.option" 是获取状态的错误方法... 如何获取组件的状态?

此外,根据我的搜索,可以使用 Enzyme 轻松测试 props 和 states。

如果这是正确的,我应该使用 Enzyme 而不是 react-testing-library 来测试状态吗?

提前致谢。

这两个是不同的对象:

const { result } = renderHook(() => MyTest());

let { getByTestId } = render(<MyTest />);

result.current.option 未定义,因为 result 是返回的组件而不是挂钩函数。

要么测试状态,要么测试呈现的组件。

用于测试组件:

在你的测试中它应该是:expect(selectNode.value).toBe("2") 或者你从文档中遵循这个:https://reactjs.org/docs/hooks-faq.html#how-to-test-components-that-use-hooks

用于测试挂钩的状态。你应该提取一个自定义钩子并像这样测试它。

来自https://github.com/testing-library/react-hooks-testing-library

function useCounter() {
  const [count, setCount] = useState(0)

  const increment = useCallback(() => setCount((x) => x + 1), [])

  return { count, increment }
}

test('should increment counter', () => {
  const { result } = renderHook(() => useCounter())

  act(() => {
    result.current.increment()
  })

  expect(result.current.count).toBe(1)
})