firebase - Jest 测试在调用模拟的 firebase 函数之前完成,因此失败

标签 firebase react-native redux jestjs redux-thunk

我正在尝试使用 jest 来测试对 firebase 的调用。 Firebase是 Google 提供的在线数据库服务。我正在 mock firebase 模块,如下所示

'use strict';

const firebase = jest.genMockFromModule('firebase');

const ref = jest.fn(() => {
  return {
    child: jest.fn(() => {
      return ref
    }),
    update: jest.fn(() => {
      console.log('Called update')
      return Promise.resolve()
    })
  }
})

firebase.initializeApp = jest.fn()
firebase.database = jest.fn(() => {
  return {
    ref: ref
  }
})

module.exports = firebase

我只是 mock 我目前需要测试的功能。下面是我的测试用例。

it('+++ actionCreator addAlarm', () => {
    const store = mockStore(initialState)
    store.dispatch(ActionCreators.addAlarm(alarm));
    // Make sure that the scheduleNotifications API is called
    expect(scheduleNotifications).toHaveBeenCalled();
    expect(firebase.initializeApp).toHaveBeenCalled();
    expect(firebase.database().ref().update).toHaveBeenCalled();
});

测试用例中的最后一行试图确保我正在调用被模拟的 firebase update 函数。

下面是控制台输出

abcs-MBP-2:GalarmApp abc$ npm test

> <a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="f2b5939e93809fb38282b2c3dcc2dcc7c1" rel="noreferrer noopener nofollow">[email protected]</a> test /Users/abc/Projects/GalarmApp
> jest

 FAIL  __tests__/actionsSpecs.js
  ● >>>A C T I O N --- Test galarm actions:  › +++ actionCreator addAlarm

    expect(jest.fn()).toHaveBeenCalled()

    Expected mock function to have been called.

      at Object.<anonymous> (__tests__/actionsSpecs.js:58:52)
      at tryCallTwo (node_modules/promise/lib/core.js:45:5)
      at doResolve (node_modules/promise/lib/core.js:200:13)
      at new Promise (node_modules/promise/lib/core.js:66:3)
      at Promise.resolve.then.el (node_modules/p-map/index.js:42:16)
      at tryCallOne (node_modules/promise/lib/core.js:37:12)
      at node_modules/promise/lib/core.js:123:15

  >>>A C T I O N --- Test galarm actions:
    ✕ +++ actionCreator addAlarm (8ms)
    ✓ +++ actionCreator setConnectionStatus (4ms)

Test Suites: 1 failed, 1 total
Tests:       1 failed, 1 passed, 2 total
Snapshots:   1 passed, 1 total
Time:        1.989s, estimated 2s
Ran all test suites.
  console.warn node_modules/rn-host-detect/index.js:45
    [SECURITY] node-uuid: crypto not usable, falling back to insecure Math.random()

  console.log __mocks__/firebase.js:11
    Called update

测试用例在我检查 update 函数被调用的行上失败。如果您查看控制台输出,您将看到存在 Called update 控制台,这意味着更新函数被调用,但它是在测试用例失败后调用的。

这是 addAlarm 操作,它是一个 thunk 操作

const addAlarm = (alarm) =>  (dispatch, getState) => {
  if(alarm.status) {
    NotificationManager.scheduleNotifications(alarm);
  }

  const alarmObjForFirebase = this.createAlarmObjForFirebase(alarm) 
  firebaseRef.update(alarmObjForFirebase)
}

据我所知,对 firebase update 函数的调用并不是异步发生的。

如果您有关于如何解决此问题的指示,请告诉我。

最佳答案

我在我的代码中发现了问题,并将其作为解决方案发布以供其他人受益。问题是update的方式模拟被定义。按照它的定义方式,我得到了 update 的一个新实例。每次我都会调用 firebase.database().ref().update. Since this is a new instance of the mock function, it wouldn't contain any data about 时模拟函数update` 函数在过去被调用。

我需要更改代码如下

const update = jest.fn(() => {
  return Promise.resolve()
})

const ref = jest.fn(() => {
  return {
    update: update
  }
})

这样,我就不会创建 update 的新实例。模拟函数,我能够断言它已在测试用例期间被调用。

关于firebase - Jest 测试在调用模拟的 firebase 函数之前完成,因此失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45520561/

相关文章:

reactjs - React-native 不使用 Redux Action 重新渲染

javascript - 如何更新 redux 状态而不遇到错误

java - 使用 Firebase 存储文件夹中的图像填充数组

javascript - 使用 $add angularfire 生成自定义 key

javascript - react native : Passing 2 parameter to onPress event

ios - 找不到 iPhone X 模拟器。使用 --verbose 标志运行 CLI 以获取更多详细信息

ios - FirebaseUI 和 SDWebImage 在 CollectionViewControllerCell 的 for 循环中显示图像

android - 在 firebase 分析调试 View 中看不到事件

javascript - React Native 中的响应错误

javascript - `App` 组件可以在构造函数中拥有它的状态并同时从 redux 中的 store 获取数据吗?