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

如何使用react-testing-library和jest mock自定义useAuth hook?

问题根因与解决方案

你的报错由两个核心问题导致,按优先级修复即可:

1. 修复jest.mock路径不匹配问题

你导入AuthProvider和组件内导入useAuth用的是别名路径helpers/auth,但jest.mock时用了相对路径../../../helpers/auth,如果jest没有正确配置别名路径映射,会导致你mock的模块和实际项目引用的不是同一个模块,useAuth未被正确mock,返回undefined。
修改mock代码为统一别名路径,同时补全useAuth返回的isLoggingIn字段,且因为组件内用await调用login,将login改为异步mock:

jest.mock('helpers/auth', () => ({
  ...jest.requireActual('helpers/auth'),
  useAuth: jest.fn(() => ({
    login: jest.fn().mockResolvedValue(true),
    isLoggingIn: false,
  })),
}));

2. 移除测试中冗余的AuthProvider包裹

你已经直接mock了useAuth hook,它不会再读取AuthProvider的上下文值,外层包裹真实的AuthProvider反而可能和mock逻辑冲突,修改setup函数的render代码:

const setup = () => {
  const loginRender = render(
    <MemoryRouter>
      <ReactQueryProvider>
        <LoginForm />
      </ReactQueryProvider>
    </MemoryRouter>
  );
  // 原有逻辑保持不变
};

3. 修复测试用例的变量未定义问题

你在第二个、第三个测试用例中使用了form变量,但没有从setup返回值中解构,补充解构即可:

test('Inputs should accept email and password strings', async () => {
  const { emailField, passwordField, form } = setup();
  // 原有逻辑保持不变
});

可选扩展用法

如果需要在不同测试用例模拟不同的登录状态(比如登录中、登录失败),可以单独覆盖useAuth的返回值:

// 测试登录失败场景
test('should show error when login failed', async () => {
  // 导入useAuth后重置mock返回值
  (useAuth as jest.Mock).mockReturnValue({
    login: jest.fn().mockRejectedValue(new Error('账号或密码错误')),
    isLoggingIn: false,
  });
  const { getByTestId } = setup();
  // 提交表单后校验错误提示展示逻辑
});

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.25 14:54:02