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

React-Query依赖查询单元测试及useUpdateTodo无Mock测试问题

问题1:React-Query依赖查询场景的单元测试写法

依赖查询的核心是前置查询完成后,后续逻辑才能基于其返回值执行,测试时要重点模拟前置查询的返回,并等待依赖值就绪:

  • 先为测试搭建React-Query环境:用QueryClientProvider包裹测试钩子,创建带默认配置的QueryClient(比如关闭重试、设置缓存时间为0)
  • 模拟前置查询的queryFn,返回预期的测试数据
  • 使用waitFor或waitForNextUpdate等待前置查询完成,确保依赖值已生成
  • 执行后续逻辑(比如触发mutation、检查依赖查询的状态),验证行为是否符合预期
问题2:不Mock useGetUserId时测试useUpdateTodo的方案

针对你提供的代码,核心是让useGetUserId内部的useQuery能正常返回用户ID,而非直接Mock这个钩子本身。以下是具体测试步骤和代码:

步骤说明

  1. 搭建React-Query测试上下文,确保useQuery和useMutation能正常工作
  2. 模拟getUserByEmail函数,让它返回包含有效ID的用户数据
  3. 使用waitFor等待useGetUserId拿到userId后,再触发mutation
  4. 验证axios的post请求是否携带了正确的userId

测试代码示例

import { renderHook, waitFor } from '@testing-library/react-hooks';
import { QueryClient, QueryClientProvider } from '@tanstack/react-query';
import axios from 'axios';
import { useUpdateTodo } from './your-file-path';
import { getUserByEmail } from './your-user-service';

// Mock 依赖函数
jest.mock('./your-user-service', () => ({
  getUserByEmail: jest.fn().mockResolvedValue({ id: 'test-user-123' })
}));
jest.mock('axios');

describe('useUpdateTodo', () => {
  let queryClient;
  let wrapper;

  beforeEach(() => {
    // 创建测试用QueryClient
    queryClient = new QueryClient({
      defaultOptions: {
        queries: {
          retry: false,
          cacheTime: 0
        }
      }
    });
    // 上下文包裹组件
    wrapper = ({ children }) => (
      <QueryClientProvider client={queryClient}>{children}</QueryClientProvider>
    );
  });

  it('should call axios.post with correct userId from useGetUserId', async () => {
    // 渲染钩子
    const { result } = renderHook(() => useUpdateTodo(), { wrapper });
    
    // 等待useGetUserId内部的useQuery完成,拿到userId
    await waitFor(() => {
      // 这里的queryKey要和useGetUserId中的一致,若email来自上下文需额外模拟
      return queryClient.getQueryData(['user', 'test-email']) !== undefined;
    });

    // 触发mutation
    const newTodo = { title: 'Test Todo' };
    await result.current.mutateAsync(newTodo);

    // 验证请求参数
    expect(axios.post).toHaveBeenCalledWith(
      '/todos',
      newTodo,
      'test-user-123'
    );
  });
});

关键注意点

  • 若useGetUserId中的email来自上下文(比如AuthContext),测试时需额外模拟该上下文,提供测试用的email值,否则queryKey不匹配会导致查询无法返回数据
  • waitFor是核心,确保userId就绪后再执行mutation,避免因异步未完成导致的测试失败
  • 不MockuseGetUserId,而是Mock它依赖的getUserByEmail,能真实测试钩子的依赖逻辑

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.13 21:23:17