You need to enable JavaScript to run this app. Jest测试React Native时mock react-native-firebase报credential读取错误
优惠活动
大模型
产品
解决方案
定价
更多

Jest测试React Native时mock react-native-firebase报credential读取错误

问题根因

抛出TypeError: Cannot read property 'credential' of undefined的核心原因是mock结构和@react-native-firebase/auth的真实导出结构完全错位:

  • 你在jest.mock('@react-native-firebase/auth', ...)里返回的工厂值是一个独立箭头函数() => mocks.auth,这个函数才是业务代码通过import auth from '@react-native-firebase/auth'拿到的默认导出对象。
  • 你把GoogleAuthProvider静态属性挂在了mocks.auth(一个jest.fn实例)上,根本没挂到那个作为模块导出的箭头函数上。业务代码执行auth.GoogleAuthProvider时,拿到的是没有任何自定义属性的裸箭头函数,访问结果自然是undefined,后续读取.credential就会触发类型错误。
  • 存在隐性配置错误:当前GoogleSignin的mock返回的是字符串'123',但业务代码对signIn的返回值做了{idToken}解构,字符串无法解构出该属性,就算解决了credential的报错,这里也会抛出新的异常。
修正方案

调整两处核心配置:

  1. 严格对齐auth模块的真实结构:将GoogleAuthProvider这类静态属性直接挂到auth模块的默认导出(即可调用的mock函数本身)上,不要挂到函数调用后返回的实例对象上。
  2. 修正GoogleSignin的返回值结构,匹配业务代码的解构逻辑。

修正后的完整测试代码:

import {GoogleLogin} from './GoogleLogin';

// 定义实例方法mock
const mockSignInWithCredential = jest.fn();
// 定义credential生成方法mock
const mockCredentialFn = jest.fn().mockReturnValue({
  providerId: 'google.com',
  token: 'mock-id-token',
  secret: 'mock-secret'
});

// 定义auth模块的默认导出:本身是可调用函数,同时挂载静态属性
const mockAuth = jest.fn(() => ({
  signInWithCredential: mockSignInWithCredential
}));
// 把GoogleAuthProvider静态属性直接挂到导出的auth函数上,和真实库结构保持一致
mockAuth.GoogleAuthProvider = {
  credential: mockCredentialFn
};

// 配置auth模块的jest mock
jest.mock('@react-native-firebase/auth', () => ({
  __esModule: true,
  default: mockAuth
}));

// 修正GoogleSignin的返回值结构,匹配业务代码的解构逻辑
jest.mock('@react-native-community/google-signin', () => ({
  GoogleSignin: {
    signIn: jest.fn().mockResolvedValue({
      idToken: 'mock-google-id-token'
    })
  }
}));

describe('navigation > auth > GoogleLogin', () => {
  it('calls signInWithCredential', async () => {
    await GoogleLogin();
    // 验证Google credential生成逻辑触发正确
    expect(mockCredentialFn).toHaveBeenCalledWith('mock-google-id-token');
    // 验证firebase凭证登录方法触发正确
    expect(mockSignInWithCredential).toHaveBeenCalled();
  });
});
配置注意事项
  • react-native-firebase/auth的真实导出逻辑是:可调用的函数本身携带静态属性(如GoogleAuthProvider),执行函数后返回带实例方法(如signInWithCredential)的auth实例。编写mock时必须严格对齐这个层级关系,不能混淆静态属性和实例方法的挂载位置。
  • 之前的写法错误在于把静态属性挂到了函数返回的实例对象上,而业务代码访问静态属性时根本没有执行函数,自然拿不到对应属性。
  • 涉及异步逻辑的mock方法必须返回Promise对象,不能直接返回静态值,否则业务代码执行await时会拿到undefined,触发解构错误。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.11.01 19:36:07