reactjs - 如何使用 useState 挂钩设置初始状态
问题描述
我使用 useState 钩子编写了一个功能组件,该组件本身工作正常,但我在测试它时遇到了麻烦。我不明白如何在我的组件中创建初始状态。我尝试了多种模拟 useState 的方法,但都没有奏效:
describe('<Component/>', () => {
beforeEach() = > {
jest.spyOn(Readt, 'useState').mockImplementation( () => React.useState(['test']));
//Also tried this:
//React['useState'] = jest.fn().mockImplementation( () => React.useState(['test']));
}
it('should match snapshot', () => {
expect(wrapper).toMatchSnapshot()
}
}
我也看过这篇文章,但无法让它为我工作
如何在 jest 和酵素中为 useState Hook 设置初始状态?
我还读到您不应该在单元测试中模拟 useState 但是如果您不模拟它,您如何为组件设置初始状态?
谢谢。
编辑:关于下面的答案:
传入一个道具不会改变我试图测试的状态。
我有一个按钮,当单击(一种状态)时会呈现一个输入框,当用户输入(另一种状态)并按下确定按钮(另一种状态)时,会根据输入框中的内容创建一个按钮。
传递的道具有助于呈现按钮列表,但它无法控制用户在输入框中键入的内容。我正在尝试在输入框中设置一个状态,然后模拟单击确定按钮并对其进行测试。我不是想测试对本机 useState 功能的反应。我只是想使用已经具有“wrapper.setState”的酶,但是我该如何使用 useState 呢?
理想情况下,我想设置我的组件,设置用户在输入框中输入的状态,然后测试确定按钮是否完成了它应该做的事情。没有模拟之前的所有点击。
解决方案
组件的状态是它内部的,这是理解 React 组件的重要部分。一旦你“理解”了这一点,你就会明白,任何测试都不应该试图改变它。
但是你如何为你的组件设置一个初始状态呢?
您将一个值传递给您的useState
钩子,在组件内。然后,您的测试应该使用该初始状态测试您的组件......他们应该只传递道具来更改它,就像您的非测试代码一样。
事实上,即使你可以以某种方式改变你的初始状态(这是不可能的 AFAIK),你的测试代码不应该做任何非测试代码所做的事情(除了设置模拟真实环境的测试环境),因为整个制作点测试是为了验证您的非测试代码是否有效。
同样,你永远不想测试你正在测试的任何东西的内部,无论是 React 组件还是其他任何东西。
如果你这样做,你编写的每一个测试都会在这些内部结构发生变化的那一刻中断,而测试价值的很大一部分是它们让你更容易重构(如果你不测试内部结构)。相反,您希望使用测试工具来测量组件的输出(即它生成的 HTML)。
再一次,这甚至与 React 无关。对任何事物的良好软件测试都不会试图弄乱该事物的内部结构,以改变或衡量它们。相反,好的测试侧重于外部,因为这又是所有非测试代码都可以使用,并且因为从概念上讲,您测试的所有内容都应该是您的测试代码的“黑匣子”。
编辑:回复评论/问题编辑
老实说,您的编辑并没有真正改变我的答案,只是它提醒我酶确实有办法改变测试中的状态(我自己从来没有使用过,我忘记了它的存在)。
但同样,仅仅因为某些事情是可能的并不意味着它是一个好主意,并且再次,你想测试你测试的任何东西的外部(不仅仅是 React 组件)。React 组件的状态就像函数内部的变量:它在该函数/组件内部,您应该避免直接测试。
相反,您要测试的是外部部分,并且(根据您的编辑)似乎不是props
……但它仍然是外部的:DOM。
所以我建议做的是(再次)非测试代码正在做的事情:“点击”你的按钮。Enzyme 使用其“模拟”方法 ( https://airbnb.io/enzyme/docs/api/ReactWrapper/simulate.html ) 使这变得非常容易。
如果您只是模拟创建所需状态的按钮序列,您将只测试外部(即以与生产中使用相同的方式测试您的代码),但您将能够测试您想要的任何环境。
推荐阅读
- python-3.x - python多处理锁和队列不适用于较旧的Linux内核
- haproxy - 如何平衡 Haproxy 后面的 DNS 服务器
- python - AttributeError - 'numpy.ndarray' 对象没有属性 'drop'
- wordpress - Wordpress 常规查询不考虑粘性帖子
- android - 等待服务器返回消息 - Kotlin 协程
- python - 如何将数据框列中的值替换为另一个数据框列。就像图片一样
- c# - 如何根据另一列的值更改 DataGrid 中按钮的前景色?WPF C#
- python - 如何在python中的二维数组中找到多少个值可以被整除
- python - 如何在 tkinter 画布的某些区域嵌入 matplotlib 图?
- arduino - 信号矢量幅度 - 加速度计 MPU6050