You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React Testing Library在Next.js+React18中无法更新输入框状态

解决React18+Next.js中RTL无法更新输入框状态的问题

问题根源

  1. 错误的waitFor使用:你把同步的fireEvent.change放在了waitFor回调里,waitFor是用来等待异步操作(比如API请求、定时器)的,输入框的状态更新是同步的,这么做会干扰RTL对状态更新的跟踪,导致断言时状态还没完成同步。
  2. React18自动批处理差异:React17没有自动批处理,状态更新是同步执行的,所以错误写法碰巧能通过;但React18在非act环境下会批量更新状态,虽然RTL的render已经用act包裹了组件,错误的waitFor还是会破坏这个机制。

修正方案

方案1:移除不必要的waitFor,直接触发事件

修改测试代码,去掉waitFor包裹,直接调用fireEvent.change:

import { fireEvent } from '@testing-library/dom';
import { render } from '@testing-library/react';
import React from 'react';
import { Component } from './Component';

describe('search input', () => {
  it('should update input field', () => {
    const { getByTestId } = render(<Component />);
  
    const inputElement = getByTestId('search-text-input');
    expect(inputElement).toBeInTheDocument();
    expect(inputElement).toHaveValue('');
    
    const country = 'usa';
    fireEvent.change(inputElement, { target: { value: country } });

    expect(inputElement).toHaveValue(country);
  });
});

方案2:使用userEvent模拟真实用户输入(推荐)

userEvent更贴近真实用户的交互行为,适配React18的批处理机制,步骤如下:

  1. 安装依赖:
npm install @testing-library/user-event --save-dev
  1. 修改测试代码:
import { render } from '@testing-library/react';
import userEvent from '@testing-library/user-event';
import React from 'react';
import { Component } from './Component';

describe('search input', () => {
  it('should update input field', async () => {
    const user = userEvent.setup();
    const { getByTestId } = render(<Component />);
  
    const inputElement = getByTestId('search-text-input');
    expect(inputElement).toBeInTheDocument();
    expect(inputElement).toHaveValue('');
    
    const country = 'usa';
    await user.type(inputElement, country);

    expect(inputElement).toHaveValue(country);
  });
});

额外说明

你的组件中useCallback的依赖数组为空是没问题的,因为setSearch是useState返回的稳定函数,不会导致闭包问题;如果后续在onNameChange中用到其他变量,记得同步更新依赖数组。

内容的提问来源于stack exchange,提问作者Shuwei

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 01:45:31